Advertisement
Guest User

Untitled

a guest
Apr 26th, 2018
69
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 7.47 KB | None | 0 0
  1. #include <string.h>
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4.  
  5. #include "index.h"
  6.  
  7. struct index
  8. {
  9. map_t *map;
  10. };
  11. /*
  12. * Creates a new, empty index.
  13. */
  14. index_t *index_create()
  15. {
  16. index_t *index = malloc(sizeof(index_t));
  17. if (index == NULL)
  18. fatal_error("out of memory");
  19.  
  20. index->map = map_create(compare_strings, hash_string);
  21.  
  22. return index;
  23. }
  24.  
  25. /*
  26. * Destroys the given index. Subsequently accessing the index will
  27. * lead to undefined behavior.
  28. */
  29. void index_destroy(index_t *index)
  30. {
  31. map_destroy(index->map, NULL, NULL);
  32. free(index);
  33. }
  34.  
  35. /*
  36. * Adds the given path to the given index, and index the given
  37. * list of words under that path.
  38. * NOTE: It is the responsibility of index_addpath() to deallocate (free)
  39. * 'path' and the contents of the 'words' list.
  40. */
  41. void index_addpath(index_t *index, char *path, list_t *words)
  42. {
  43. list_iter_t *iter = list_createiter(words);
  44.  
  45. while(list_hasnext(iter))
  46. {
  47. char *setwords = list_next(iter);
  48.  
  49. if (!map_haskey(index->map, setwords))
  50. {
  51. set_t *new = set_create(compare_strings);
  52. set_add(new, path);
  53. map_put(index->map, setwords, new);
  54. }
  55.  
  56. else
  57. {
  58. set_t *new = map_get(index->map, setwords);
  59. set_add(new, path);
  60. }
  61.  
  62. }
  63.  
  64. list_destroyiter(iter);
  65. }
  66.  
  67. typedef enum{
  68. ANDNOT, AND, OR, P_WORD
  69. }node_type;
  70.  
  71. typedef struct parser parser_t;
  72.  
  73. struct parser{
  74. node_type type;
  75. char *word;
  76. parser_t *left;
  77. parser_t *right;
  78. };
  79.  
  80. static parser_t *newnode(node_type type, char *word, parser_t *left, parser_t *right)
  81. {
  82. parser_t *parser = malloc(sizeof(parser_t));
  83. if (parser == NULL)
  84. fatal_error("out of memory");
  85.  
  86. parser->type = type;
  87. parser->word = word;
  88. parser->left = left;
  89. parser->right = right;
  90.  
  91. return parser;
  92. }
  93.  
  94. static parser_t *handle_query(list_t *query);
  95. static parser_t *handle_query_and(list_t *query);
  96. static parser_t *handle_query_or(list_t *query);
  97. static parser_t *handle_query_term(list_t *query);
  98. static parser_t *handle_query_word(list_t *query);
  99. /*
  100. static parser_t *handle_query(list_t *query)
  101. {
  102. if(list_size(query) == 0)
  103. return NULL;
  104.  
  105. parser_t *b;
  106. parser_t *a = handle_query_and(query);
  107.  
  108. if (list_size(query) > 0)
  109. {
  110. char *word = list_popfirst(query);
  111.  
  112. if(!strcmp(word, "ANDNOT"))
  113. {
  114. b = handle_query(query);
  115. return newnode(ANDNOT, NULL, a, b);
  116. }
  117. else
  118. {
  119. printf("kjører dette? ANDNOT\n");
  120.  
  121. list_addfirst(query, word);
  122. }
  123. }
  124. else
  125. {
  126. printf("returner a ANDNOT\n");
  127. return a;
  128. }
  129. }
  130. */
  131.  
  132. static parser_t *handle_query(list_t *query)
  133. {
  134. {
  135. if(list_size(query) == 0)
  136. return NULL;
  137.  
  138.  
  139. parser_t *b, *a = handle_query_and(query);
  140.  
  141. if(list_size(query) > 0)
  142. {
  143. char *word = list_popfirst(query);
  144.  
  145. if (!strcmp(word, "ANDNOT"))
  146. {
  147. b = handle_query(query);
  148.  
  149. return newnode(ANDNOT, NULL, a, b);
  150. }
  151. else
  152. {
  153. printf("kjører dette? ANDNOT\n");
  154. list_addfirst(query, word);
  155. return a;
  156. }
  157. }
  158. else
  159. {
  160. printf("returner a ANDNOT\n");
  161.  
  162. return a;
  163. }
  164. }
  165. }
  166.  
  167.  
  168. /*
  169. static parser_t *handle_query_and(list_t *query)
  170. {
  171. if(list_size(query) == 0)
  172. return NULL;
  173.  
  174. parser_t *b;
  175. parser_t *a = handle_query_or(query);
  176.  
  177. if(list_size(query) > 0)
  178. {
  179. char *word = list_popfirst(query);
  180.  
  181. if (!strcmp(word, "AND"))
  182. {
  183. b = handle_query_and(query);
  184. printf("Inne i AND\n");
  185. if (a == NULL)
  186. printf("a failet\n");
  187. if (b == NULL)
  188. printf("b failet\n");
  189.  
  190. if (a == b)
  191. printf("a og b er det samme\n");
  192.  
  193. return newnode(AND, NULL, a, b);
  194. }
  195. else{
  196.  
  197. printf("kjører dette? AND\n");
  198. list_addfirst(query, word);
  199. }
  200. }
  201. else
  202. {
  203. printf("returner a AND\n");
  204.  
  205. return a;
  206. }
  207. }
  208.  
  209. */
  210.  
  211. static parser_t *handle_query_and(list_t *query)
  212. {
  213. {
  214. if(list_size(query) == 0)
  215. return NULL;
  216.  
  217. parser_t *b, *a = handle_query_or(query);
  218.  
  219. if(list_size(query) > 0)
  220. {
  221. char *word = list_popfirst(query);
  222.  
  223. if (!strcmp(word, "AND"))
  224. {
  225. b = handle_query_and(query);
  226.  
  227. return newnode(AND, NULL, a, b);
  228. }
  229. else
  230. {
  231. printf("kjører dette? AND\n");
  232. list_addfirst(query, word);
  233. return a;
  234. }
  235. }
  236. else
  237. {
  238. printf("returner a AND\n");
  239. return a;
  240. }
  241. }
  242. }
  243. static parser_t *handle_query_or(list_t *query)
  244. {
  245. if(list_size(query) == 0)
  246. return NULL;
  247.  
  248. parser_t *b, *a = handle_query_term(query);
  249.  
  250. if(list_size(query) > 0)
  251. {
  252. char *word = list_popfirst(query);
  253.  
  254. if (!strcmp(word, "OR"))
  255. {
  256. b = handle_query_or(query);
  257.  
  258. return newnode(OR, NULL, a, b);
  259. }
  260. else
  261. {
  262. printf("kjører dette? OR\n");
  263. list_addfirst(query, word);
  264. return a;
  265. }
  266. }
  267. else
  268. {
  269. printf("returner a OR\n");
  270.  
  271. return a;
  272. }
  273. }
  274. static parser_t *handle_query_term(list_t *query)
  275. {
  276. if (list_size(query) == 0)
  277. return NULL;
  278.  
  279. parser_t *a;
  280.  
  281. if(list_size(query) > 0)
  282. {
  283. char *word = list_popfirst(query);
  284.  
  285. if(!strcmp(word, "("))
  286. {
  287. a = handle_query(query);
  288. if(!strcmp(word, ")"))
  289. a = handle_query(query);
  290. else
  291. fatal_error("missing )");
  292. }
  293. else
  294. {
  295. printf("kjører dette? TERM\n");
  296.  
  297. list_addfirst(query, word);
  298.  
  299. return handle_query_word(query);
  300. }
  301. }
  302. else
  303. {
  304. printf("returener word\n");
  305. return handle_query_word(query);
  306. }
  307. }
  308.  
  309. static parser_t *handle_query_word(list_t *query)
  310. {
  311. if(list_size(query) == 0)
  312. return NULL;
  313.  
  314. if (list_size(query) > 0)
  315. {
  316. printf("Kjører WORD\n");
  317. char *word = list_popfirst(query);
  318. return newnode(P_WORD, word, NULL, NULL);
  319. }
  320. }
  321.  
  322.  
  323.  
  324. static set_t *evaluate(parser_t *node, index_t *index)
  325. {
  326. set_t *left;
  327. set_t *right;
  328.  
  329. switch(node->type)
  330. {
  331. case ANDNOT:
  332. left = map_get(index->map, node->left->word);
  333. right = map_get(index->map, node->right->word);
  334. return set_difference(left, right);
  335.  
  336. case AND:
  337. left = map_get(index->map, node->left->word);
  338. right = map_get(index->map, node->right->word);
  339. return set_intersection(left, right);
  340.  
  341. case OR:
  342. left = map_get(index->map, node->left->word);
  343. right = map_get(index->map, node->right->word);
  344. return set_union(left, right);
  345.  
  346.  
  347. case P_WORD:
  348. left = map_get(index->map, node->word);
  349. return left;
  350. }
  351. fatal_error("Unknown node type");
  352. return NULL;
  353. }
  354. /*
  355. * Performs the given query on the given index. If the query
  356. * succeeds, the return value will be a list of paths. If there
  357. * is an error (e.g. a syntax error in the query), an error message
  358. * is assigned to the given errmsg pointer and the return value
  359. * will be NULL.
  360. */
  361. list_t *index_query(index_t *index, list_t *query, char **errmsg)
  362. {
  363. list_t *new = list_create(compare_strings);
  364. query_result_t *final_result;
  365. parser_t *result = handle_query(query);
  366.  
  367. set_t *set = evaluate(result, index);
  368. set_iter_t *set_iter = set_createiter(set);
  369. while (set_hasnext(set_iter))
  370. {
  371. final_result = malloc(sizeof(query_result_t));
  372. if (final_result == NULL)
  373. fatal_error("out of memory");
  374. final_result->path = set_next(set_iter);
  375. final_result->score = 0;
  376. list_addlast(new, final_result);
  377. }
  378. return new;
  379. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement