MCPcopy Create free account
hub / github.com/RedisGraph/RedisGraph / BuildQueryGraph

Function BuildQueryGraph

src/graph/query_graph.c:371–440  ·  view source on GitHub ↗

build a query graph from AST

Source from the content-addressed store, hash-verified

369
370// build a query graph from AST
371QueryGraph *BuildQueryGraph
372(
373 const AST *ast
374) {
375 uint node_count;
376 uint edge_count;
377
378 // AST clauses containing path objects
379 cypher_astnode_type_t clause_types [2] = {CYPHER_AST_MATCH, CYPHER_AST_MERGE};
380
381 // the initial node and edge arrays will be large enough to accommodate
382 // all AST entities (which is overkill, consider reducing)
383 node_count = edge_count = raxSize(ast->referenced_entities);
384 QueryGraph *qg = QueryGraph_New(node_count, edge_count);
385
386 // for each relevant clause type
387 for(int i = 0; i < 2; i ++) {
388 const uint8_t clause_type = clause_types[i];
389 // collect all path objects
390 const cypher_astnode_t **clauses = AST_GetTypedNodes(ast->root,
391 clause_type);
392 uint clause_count = array_len(clauses);
393
394 // for each clause of the current type
395 for(uint j = 0; j < clause_count; j ++) {
396 const cypher_astnode_t *clause = clauses[j];
397 // collect path objects
398 const cypher_astnode_t **paths =
399 AST_GetTypedNodes(clause, CYPHER_AST_PATTERN_PATH);
400 const cypher_astnode_t **shortest_paths =
401 AST_GetTypedNodes(clause, CYPHER_AST_SHORTEST_PATH);
402
403 // differentiate between regular paths and shortest paths
404 // as a path can be marked as shortest
405 uint path_count = array_len(paths);
406 uint shortest_path_count = array_len(shortest_paths);
407 bool only_shortest[path_count];
408 memset(only_shortest, 0, path_count*sizeof(bool));
409
410 uint l = 0; // index to paths array
411 uint k = 0; // index to shortest paths array
412 for (; k < shortest_path_count; k++) {
413 const cypher_astnode_t *shortest = shortest_paths[k];
414 // single shortest paths are handled by a procedure
415 if(cypher_ast_shortest_path_is_single(shortest)) continue;
416
417 const cypher_astnode_t *path =
418 cypher_ast_shortest_path_get_path(shortest);
419
420 // seek the matching path in the paths array
421 while(paths[l] != path) l++;
422 ASSERT(l < path_count);
423
424 // each shortest must find its counterpart path
425 only_shortest[l] = true;
426 l++; // advance for next match
427 }
428 array_free(shortest_paths);

Callers 2

Calls 5

QueryGraph_NewFunction · 0.85
AST_GetTypedNodesFunction · 0.85
array_lenFunction · 0.85
array_freeFunction · 0.85
QueryGraph_AddPathFunction · 0.85

Tested by 1