home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 35 Internet / 35-Internet.zip / quot210s.zip / src / asearch.c < prev    next >
C/C++ Source or Header  |  1998-09-07  |  7KB  |  275 lines

  1. /*
  2.  * asearch.c
  3.  *
  4.  * Functions for searching an author database. Note that the use of the
  5.  * GENERIC macro here is not because the #ifndef'd sections won't compile
  6.  * in the generic build; it's so that the GNU Rx library isn't required
  7.  * for the generic build, since the generic build doesn't use these
  8.  * functions.
  9.  *
  10.  *      Created: 27th January, 1997
  11.  * Version 1.00: 19th March, 1997
  12.  * Version 2.00: 24th November, 1997
  13.  * Version 2.10: 7th September, 1998
  14.  *
  15.  * (C) 1997 Nicholas Paul Sheppard
  16.  *
  17.  * This file is distributed under the GNU General Public License. See the
  18.  * file copying.txt for details.
  19.  */
  20.  
  21. #include <stdlib.h>
  22. #include <string.h>
  23. #include <gnu/gdbm.h>
  24. #ifndef GENERIC
  25. # include <gnu/rxposix.h>
  26. # include <gnu/rxall.h>
  27. #endif
  28. #include "authors.h"
  29. #include "html.h"
  30.  
  31.  
  32. int AuthorFullSearchInit(AUTHORDB *padb, AUTHORSEARCH *pas)
  33. /*
  34.  * Find the first author in a database, and initialise a structure to be used
  35.  * in finding the rest. The first key is returned in the szLastCode field of
  36.  * the AUTHORSEARCH structure.
  37.  *
  38.  * AUTHORDB *padb    - the author database to search
  39.  * AUTHORSEARCH *pas    - the structure to be initialised for further searching
  40.  *
  41.  * Returns:        - 0 if the database is empty
  42.  *              1 otherwise
  43.  */
  44. {
  45.     datum first;
  46.  
  47.     first = gdbm_firstkey(padb->dbfInfo);
  48.     if (first.dptr == NULL)
  49.         return (0);
  50.  
  51.     pas->padb = padb;
  52.     strcpy(pas->szLastCode, first.dptr);
  53.     free(first.dptr);
  54.  
  55.     return (1);
  56. }
  57.  
  58.  
  59. int AuthorFullSearchNext(AUTHORSEARCH *pas)
  60. /*
  61.  * Find the next author in a database and update the structure to be used for
  62.  * finding the rest. The next key is returned in the szLastCode field of the
  63.  * AUTHORSEARCH structure.
  64.  *
  65.  * AUTHORSEARCH *as    - the search structure
  66.  *
  67.  * Returns:        - 0 if there are no more authors in the database
  68.  *              1 otherwise
  69.  */
  70. {
  71.     datum current, next;
  72.  
  73.     current.dptr = pas->szLastCode;
  74.     current.dsize = strlen(pas->szLastCode) + 1;
  75.     next = gdbm_nextkey(pas->padb->dbfInfo, current);
  76.     if (next.dptr == NULL)
  77.         return (0);
  78.  
  79.     strcpy(pas->szLastCode, next.dptr);
  80.     free(next.dptr);
  81.  
  82.     return (1);
  83. }
  84.  
  85. void AuthorFullSearchEnd(AUTHORSEARCH *pas)
  86. /*
  87.  * Clean up after finishing a full search of the database. Currently, this
  88.  * function does nothing and only exists to make a full search look the
  89.  * same as other searches.
  90.  */
  91. {
  92. }
  93.  
  94. #ifndef GENERIC
  95. int AuthorNameSearchInit(AUTHORDB *padb, char *pszName, AUTHORSEARCH *pas)
  96. /*
  97.  * Find the first author in a database with the specified name (whether it
  98.  * is their first or last name), and initialise a structure to be used for
  99.  * finding the rest. The first key is returned in the szLastCode field of
  100.  * the AUTHORSEARCH structure.
  101.  *
  102.  * AUTHORDB *padb    - the quote database to search
  103.  * char *pszName    - the name to search for
  104.  * AUTHORSEARCH *pas    - the structure to be initialised for further searching
  105.  *
  106.  * Returns:        - -1 if the regular expression is invalid
  107.  *               0 if there are no matching quotes in the database
  108.  *               1 otherwise
  109.  */
  110. {
  111.     AUTHORINFO *pai;
  112.     int bDone, bFound;
  113.  
  114.     /* fill the AUTHORSEARCH structure */
  115.     strcpy(pas->szSearch, pszName);
  116.     pas->padb = padb;
  117.     if (regcomp(&(pas->rxSearch), pszName, REG_NOSUB | REG_EXTENDED | REG_ICASE))
  118.         return (-1);
  119.  
  120.     /* find the first quote with a matching keyword */
  121.     bFound = 0;
  122.     bDone = !AuthorFullSearchInit(padb, pas);
  123.     while (!bDone) {
  124.         AuthorGetAuthor(padb, pas->szLastCode, &pai, NULL);
  125.         if (!regexec(&(pas->rxSearch), pai->szGivenName, 0, NULL, 0))
  126.             bFound = 1;
  127.         if (!regexec(&(pas->rxSearch), pai->szSurname, 0, NULL, 0))
  128.             bFound = 1;
  129.         AuthorFreeAuthor(&pai, NULL);
  130.         if (bFound)
  131.             bDone = 1;
  132.         else
  133.             bDone = !AuthorFullSearchNext(pas);
  134.     }
  135.  
  136.     return (bFound);
  137. }
  138. #endif
  139.  
  140.  
  141. #ifndef GENERIC
  142. int AuthorNameSearchNext(AUTHORSEARCH *pas)
  143. /*
  144.  * Find the next author in a database having the specified name.
  145.  *
  146.  * AUTHORSEARCH *pas    - the structure containing the search information
  147.  *
  148.  * Returns:        - 0 if there are no more matching authors in the database
  149.  *              1 otherwise
  150.  */
  151. {
  152.     AUTHORINFO *pai;
  153.     int bDone, bFound;
  154.  
  155.     bFound = 0;
  156.     bDone = !AuthorFullSearchNext(pas);
  157.     while (!bDone) {
  158.         AuthorGetAuthor(pas->padb, pas->szLastCode, &pai, NULL);
  159.         if (!regexec(&(pas->rxSearch), pai->szGivenName, 0, NULL, 0))
  160.             bFound = 1;
  161.         if (!regexec(&(pas->rxSearch), pai->szSurname, 0, NULL, 0))
  162.             bFound = 1;
  163.         AuthorFreeAuthor(&pai, NULL);
  164.         if (bFound)
  165.             bDone = 1;
  166.         else
  167.             bDone = !AuthorFullSearchNext(pas);
  168.     }
  169.  
  170.     return (bFound);
  171. }
  172. #endif
  173.  
  174.  
  175. #ifndef GENERIC
  176. void AuthorNameSearchEnd(AUTHORSEARCH *pas)
  177. /*
  178.  * Clean up after completing a description search.
  179.  */
  180. {
  181.     regfree(&(pas->rxSearch));
  182. }
  183. #endif
  184.  
  185.  
  186. #ifndef GENERIC
  187. int AuthorDescSearchInit(AUTHORDB *padb, char *pszDesc, AUTHORSEARCH *pas)
  188. /*
  189.  * Find the first author in a database containing the specified text in
  190.  * their description, and initialise a structure to be used for finding
  191.  * the rest. The first key is returned in the szLastCode field of the
  192.  * AUTHORSEARCH structure.
  193.  *
  194.  * AUTHORDB *padb    - the quote database to search
  195.  * char *pszDesc    - the text to search for
  196.  * AUTHORSEARCH *pas    - the structure to be initialised for further searching
  197.  *
  198.  * Returns:        - -1 if the regular expression is invalid
  199.  *               0 if there are no matching quotes in the database
  200.  *               1 otherwise
  201.  */
  202. {
  203.     char *pszAuthorDesc;
  204.     int bDone, bFound;
  205.  
  206.     /* fill the AUTHORSEARCH structure */
  207.     strcpy(pas->szSearch, pszDesc);
  208.     pas->padb = padb;
  209.     if (regcomp(&(pas->rxSearch), pszDesc, REG_NOSUB | REG_EXTENDED | REG_ICASE))
  210.         return (-1);
  211.  
  212.     /* find the first quote with a matching keyword */
  213.     bFound = 0;
  214.     bDone = !AuthorFullSearchInit(padb, pas);
  215.     while (!bDone) {
  216.         AuthorGetAuthor(padb, pas->szLastCode, NULL, &pszAuthorDesc);
  217.         HTMLMakePlain(pszAuthorDesc);
  218.         if (!regexec(&(pas->rxSearch), pszAuthorDesc, 0, NULL, 0))
  219.             bFound = 1;
  220.         AuthorFreeAuthor(NULL, &pszAuthorDesc);
  221.         if (bFound)
  222.             bDone = 1;
  223.         else
  224.             bDone = !AuthorFullSearchNext(pas);
  225.     }
  226.  
  227.     return (bFound);
  228. }
  229. #endif
  230.  
  231.  
  232. #ifndef GENERIC
  233. int AuthorDescSearchNext(AUTHORSEARCH *pas)
  234. /*
  235.  * Find the next author in a database containing the specified text in their
  236.  * description.
  237.  *
  238.  * AUTHORSEARCH *pas    - the structure containing the search information
  239.  *
  240.  * Returns:        - 0 if there are no more matching authors in the database
  241.  *              1 otherwise
  242.  */
  243. {
  244.     char *pszAuthorDesc;
  245.     int bDone, bFound;
  246.  
  247.     bFound = 0;
  248.     bDone = !AuthorFullSearchNext(pas);
  249.     while (!bDone) {
  250.         AuthorGetAuthor(pas->padb, pas->szLastCode, NULL, &pszAuthorDesc);
  251.         HTMLMakePlain(pszAuthorDesc);
  252.         if (!regexec(&(pas->rxSearch), pszAuthorDesc, 0, NULL, 0))
  253.             bFound = 1;
  254.         AuthorFreeAuthor(NULL, &pszAuthorDesc);
  255.         if (bFound)
  256.             bDone = 1;
  257.         else
  258.             bDone = !AuthorFullSearchNext(pas);
  259.     }
  260.  
  261.     return (bFound);
  262. }
  263. #endif
  264.  
  265.  
  266. #ifndef GENERIC
  267. void AuthorDescSearchEnd(AUTHORSEARCH *pas)
  268. /*
  269.  * Clean up after completing a description search.
  270.  */
  271. {
  272.     regfree(&(pas->rxSearch));
  273. }
  274. #endif
  275.