From e681255d9d97d3533049ec2d8cc836a72a03ebb0 Mon Sep 17 00:00:00 2001 From: Adam Dickmeiss Date: Fri, 17 May 2002 08:46:01 +0000 Subject: [PATCH] Attributes from multifields may be OR'ed rather than merged --- ccl/bib1 | 3 +- ccl/cclfind.c | 146 ++++++++++++++++++++++++++++++++++++++++----------------- 2 files changed, 106 insertions(+), 43 deletions(-) diff --git a/ccl/bib1 b/ccl/bib1 index d5f44ff..41a46cf 100644 --- a/ccl/bib1 +++ b/ccl/bib1 @@ -1,4 +1,4 @@ -# $Id: bib1,v 1.10 2002-04-01 12:27:15 adam Exp $ +# $Id: bib1,v 1.11 2002-05-17 08:46:01 adam Exp $ # CCL qualifiers and their mappings # # Each line takes the form: @@ -105,6 +105,7 @@ exp:category exp1,1=1 @set s set @case 0 # case insenstive (1 for case sensitive) @truncation * ? +@field or # Aliases # diff --git a/ccl/cclfind.c b/ccl/cclfind.c index 579491e..60a6577 100644 --- a/ccl/cclfind.c +++ b/ccl/cclfind.c @@ -44,7 +44,7 @@ /* CCL find (to rpn conversion) * Europagate, 1995 * - * $Id: cclfind.c,v 1.29 2002-03-18 18:14:34 adam Exp $ + * $Id: cclfind.c,v 1.30 2002-05-17 08:46:01 adam Exp $ * * Old Europagate log: * @@ -627,22 +627,24 @@ static struct ccl_rpn_node *qualifiers2 (CCL_parser cclp, } /* - * qualifiers: Parse CCL qualifiers and search terms. + * qualifiers1: Parse CCL qualifiers and search terms. * cclp: CCL Parser * la: Token pointer to RELATION token. * qa: Qualifier attributes already applied. * return: pointer to node(s); NULL on error. */ -static struct ccl_rpn_node *qualifiers (CCL_parser cclp, struct ccl_token *la, - struct ccl_rpn_attr **qa) +static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, + struct ccl_rpn_attr **qa) { struct ccl_token *lookahead = cclp->look_token; struct ccl_token *look_start = cclp->look_token; struct ccl_rpn_attr **ap; struct ccl_rpn_node *node = 0; + const char *field_str; int no = 0; int seq = 0; int i; + int mode_merge = 1; #if 0 if (qa) { @@ -656,24 +658,50 @@ static struct ccl_rpn_node *qualifiers (CCL_parser cclp, struct ccl_token *la, if (qa) for (i=0; qa[i]; i++) no++; - ap = (struct ccl_rpn_attr **)malloc ((no+1) * sizeof(*ap)); + ap = (struct ccl_rpn_attr **)malloc ((no ? (no+1) : 2) * sizeof(*ap)); ccl_assert (ap); - while (1) + field_str = ccl_qual_search_special(cclp->bibset, "field"); + if (field_str) + { + if (!strcmp (field_str, "or")) + mode_merge = 0; + else if (!strcmp (field_str, "merge")) + mode_merge = 1; + } + if (!mode_merge) { - struct ccl_rpn_node *node_sub; - int found = 0; + /* consider each field separately and OR */ lookahead = look_start; - for (i = 0; lookahead != la; i++) + while (lookahead != la) { - ap[i] = ccl_qual_search (cclp, lookahead->name, - lookahead->len, seq); - if (ap[i]) - found++; - if (!ap[i] && seq > 0) - ap[i] = ccl_qual_search (cclp, lookahead->name, - lookahead->len, 0); - if (!ap[i]) + ap[1] = 0; + seq = 0; + while ((ap[0] = ccl_qual_search (cclp, lookahead->name, + lookahead->len, seq)) != 0) + { + struct ccl_rpn_node *node_sub; + cclp->look_token = la; + + node_sub = qualifiers2(cclp, ap); + if (!node_sub) + { + ccl_rpn_delete (node); + free (ap); + return 0; + } + if (node) + { + struct ccl_rpn_node *node_this = mk_node(CCL_RPN_OR); + node_this->u.p[0] = node; + node_this->u.p[1] = node_sub; + node = node_this; + } + else + node = node_sub; + seq++; + } + if (seq == 0) { cclp->look_token = lookahead; cclp->error_code = CCL_ERR_UNKNOWN_QUAL; @@ -684,32 +712,66 @@ static struct ccl_rpn_node *qualifiers (CCL_parser cclp, struct ccl_token *la, if (lookahead->kind == CCL_TOK_COMMA) lookahead = lookahead->next; } - if (qa) - while (*qa) - ap[i++] = *qa++; - ap[i] = NULL; - - if (!found) - break; - - cclp->look_token = lookahead; - - node_sub = qualifiers2(cclp, ap); - if (!node_sub) - { - ccl_rpn_delete (node); - break; - } - if (node) + } + else + { + /* merge attributes from ALL fields - including inherited ones */ + while (1) { - struct ccl_rpn_node *node_this = mk_node(CCL_RPN_OR); - node_this->u.p[0] = node; - node_this->u.p[1] = node_sub; - node = node_this; + struct ccl_rpn_node *node_sub; + int found = 0; + lookahead = look_start; + for (i = 0; lookahead != la; i++) + { + ap[i] = ccl_qual_search (cclp, lookahead->name, + lookahead->len, seq); + if (ap[i]) + found++; + if (!ap[i] && seq > 0) + ap[i] = ccl_qual_search (cclp, lookahead->name, + lookahead->len, 0); + if (!ap[i]) + { + cclp->look_token = lookahead; + cclp->error_code = CCL_ERR_UNKNOWN_QUAL; + free (ap); + return NULL; + } + lookahead = lookahead->next; + if (lookahead->kind == CCL_TOK_COMMA) + lookahead = lookahead->next; + } + if (qa) + { + struct ccl_rpn_attr **qa0 = qa; + + while (*qa0) + ap[i++] = *qa0++; + } + ap[i] = NULL; + + if (!found) + break; + + cclp->look_token = lookahead; + + node_sub = qualifiers2(cclp, ap); + if (!node_sub) + { + ccl_rpn_delete (node); + break; + } + if (node) + { + struct ccl_rpn_node *node_this = mk_node(CCL_RPN_OR); + node_this->u.p[0] = node; + node_this->u.p[1] = node_sub; + node = node_this; + } + else + node = node_sub; + seq++; } - else - node = node_sub; - seq++; } free (ap); return node; @@ -813,7 +875,7 @@ static struct ccl_rpn_node *search_elements (CCL_parser cclp, { lookahead = lookahead->next; if (lookahead->kind == CCL_TOK_REL || lookahead->kind == CCL_TOK_EQ) - return qualifiers (cclp, lookahead, qa); + return qualifiers1 (cclp, lookahead, qa); if (lookahead->kind != CCL_TOK_COMMA) break; lookahead = lookahead->next; -- 1.7.10.4