From 58cd893dea2b3dd6e576bd9d93fd12ec3e0c2feb Mon Sep 17 00:00:00 2001 From: c9s Date: Sun, 18 May 2014 12:28:12 +0800 Subject: [PATCH] insert conditions at endpoints --- include/r3.h | 26 +++++++++++------------ src/node.c | 50 ++++++++++++++++++++++++++------------------- tests/bench_str.csv | 6 ++++++ tests/check_tree.c | 28 ++++++++++++------------- 4 files changed, 62 insertions(+), 48 deletions(-) diff --git a/include/r3.h b/include/r3.h index 2dc99e7..5bc76e1 100644 --- a/include/r3.h +++ b/include/r3.h @@ -25,14 +25,14 @@ struct _node; struct _route; typedef struct _edge edge; typedef struct _node node; -typedef struct _route route; +typedef struct _route condition; struct _node { edge ** edges; int edge_len; int edge_cap; - route ** conditions; + condition ** conditions; int condition_len; int condition_cap; @@ -48,7 +48,7 @@ struct _node { int * ov; /** - * the pointer of route data + * the pointer of condition data */ void * data; @@ -68,7 +68,7 @@ typedef struct { int path_len; // the length of the current path int request_method; // current request method - void * data; // route ptr + void * data; // condition ptr char * host; // the request host int host_len; @@ -105,9 +105,9 @@ edge * r3_node_find_edge(node * n, char * pat); void r3_node_append_edge(node *n, edge *child); -node * r3_tree_insert_path(node *tree, char *path, route * route, void * data); +node * r3_tree_insert_path(node *tree, char *path, condition * condition, void * data); -node * r3_tree_insert_pathl(node *tree, char *path, int path_len, route * route, void * data); +node * r3_tree_insert_pathl(node *tree, char *path, int path_len, condition * condition, void * data); void r3_tree_dump(node * n, int level); @@ -133,7 +133,7 @@ void r3_edge_branch(edge *e, int dl); void r3_edge_free(edge * edge); -node * r3_tree_insert_route(node *tree, route * route, void * data); +node * r3_tree_insert_route(node *tree, condition * condition, void * data); match_entry * match_entry_createl(char * path, int path_len); @@ -142,17 +142,17 @@ match_entry * match_entry_createl(char * path, int path_len); void match_entry_free(match_entry * entry); -route * route_create(char * path); +condition * condition_create(char * path); -route * route_createl(char * path, int path_len); +condition * condition_createl(char * path, int path_len); -int route_cmp(route *r1, route *r2); +int condition_cmp(condition *r1, condition *r2); -edge * r3_edge_route_create(route * route, node * child); +edge * r3_edge_route_create(condition * condition, node * child); -node * r3_node_append_condition(node * n, route * route, void * data); +void r3_node_append_condition(node * n, condition * condition, void * data); -void route_free(route * route); +void condition_free(condition * condition); #define METHOD_GET 2 #define METHOD_POST 2<<1 diff --git a/src/node.c b/src/node.c index 38f20af..58789b2 100644 --- a/src/node.c +++ b/src/node.c @@ -333,16 +333,16 @@ node * r3_node_create() { } -route * route_create(char * path) { - return route_createl(path, strlen(path)); +condition * condition_create(char * path) { + return condition_createl(path, strlen(path)); } -void route_free(route * route) { - free(route); +void condition_free(condition * condition) { + free(condition); } -route * route_createl(char * path, int path_len) { - route * info = malloc(sizeof(route)); +condition * condition_createl(char * path, int path_len) { + condition * info = malloc(sizeof(condition)); info->path = path; info->path_len = path_len; info->request_method = 0; // can be (GET || POST) @@ -355,20 +355,20 @@ route * route_createl(char * path, int path_len) { return info; } -node * r3_tree_insert_route(node *tree, route * route, void * data) { - return r3_tree_insert_pathl(tree, route->path, route->path_len, route, data); +node * r3_tree_insert_route(node *tree, condition * condition, void * data) { + return r3_tree_insert_pathl(tree, condition->path, condition->path_len, condition, data); } -node * r3_tree_insert_path(node *tree, char *path, route * route, void * data) +node * r3_tree_insert_path(node *tree, char *path, condition * condition, void * data) { - return r3_tree_insert_pathl(tree, path, strlen(path) , route , data); + return r3_tree_insert_pathl(tree, path, strlen(path) , condition , data); } /** * Return the last inserted node. */ -node * r3_tree_insert_pathl(node *tree, char *path, int path_len, route * route, void * data) +node * r3_tree_insert_pathl(node *tree, char *path, int path_len, condition * condition, void * data) { node * n = tree; edge * e = NULL; @@ -404,6 +404,10 @@ node * r3_tree_insert_pathl(node *tree, char *path, int path_len, route * route, info("edge not found, insert one: %s\n", path); child->data = data; child->endpoint++; + + if (condition) { + r3_node_append_condition(child, condition, data); + } return child; } else if ( offset == e->pattern_len ) { // fully-equal to the pattern of the edge @@ -412,11 +416,14 @@ node * r3_tree_insert_pathl(node *tree, char *path, int path_len, route * route, // there are something more we can insert if ( subpath_len > 0 ) { - return r3_tree_insert_pathl(e->child, subpath, subpath_len, route, data); + return r3_tree_insert_pathl(e->child, subpath, subpath_len, condition, data); } else { // no more path to insert e->child->endpoint++; // make it as an endpoint e->child->data = data; + if (condition) { + r3_node_append_condition(e->child, condition, data); + } return e->child; } @@ -451,6 +458,10 @@ node * r3_tree_insert_pathl(node *tree, char *path, int path_len, route * route, // move n->edges to c1 c2->endpoint++; c2->data = data; + + if (condition) { + r3_node_append_condition(c2, condition, data); + } return c2; } else { printf("unexpected condition."); @@ -503,9 +514,9 @@ void r3_tree_dump(node * n, int level) { /** * return 0 == equal * - * -1 == different route + * -1 == different condition */ -int route_cmp(route *r1, route *r2) { +int condition_cmp(condition *r1, condition *r2) { if ( r1 == r2 ) { return 0; } @@ -550,8 +561,7 @@ int route_cmp(route *r1, route *r2) { /** * Create a data only node. */ -node * r3_node_append_condition(node * n, route * route, void * data) { - /* +void r3_node_append_condition(node * n, condition * condition, void * data) { if (!n->conditions) { n->condition_cap = 3; n->conditions = malloc(sizeof(condition) * n->condition_cap); @@ -561,20 +571,18 @@ node * r3_node_append_condition(node * n, route * route, void * data) { n->conditions = realloc(n->conditions, sizeof(condition) * n->condition_cap); } n->conditions[ n->condition_len++ ] = condition; - */ - return n; } /** - * Create a route-only edge. (without pattern) + * Create a condition-only edge. (without pattern) */ -edge * r3_edge_route_create(route * route, node * child) { +edge * r3_edge_route_create(condition * condition, node * child) { edge * e = (edge*) malloc( sizeof(edge) ); /* e->pattern = NULL; e->pattern_len = 0; e->child = child; - // e->route = NULL; + // e->condition = NULL; */ return e; } diff --git a/tests/bench_str.csv b/tests/bench_str.csv index ec0d2f5..91637b4 100644 --- a/tests/bench_str.csv +++ b/tests/bench_str.csv @@ -115,3 +115,9 @@ 1400386505,11172976.25 1400386731,11184613.82 1400387044,10760384.75 +1400387138,10813584.63 +1400387154,10825571.07 +1400387176,9958256.23 +1400387232,11035725.37 +1400387264,11006703.61 +1400387291,11123431.08 diff --git a/tests/check_tree.c b/tests/check_tree.c index 7d0b2da..5123940 100644 --- a/tests/check_tree.c +++ b/tests/check_tree.c @@ -224,22 +224,22 @@ END_TEST START_TEST(test_route_cmp) { - route *r1 = route_create("/blog/post"); - route *r2 = route_create("/blog/post"); + condition *r1 = condition_create("/blog/post"); + condition *r2 = condition_create("/blog/post"); - fail_if( route_cmp(r1, r2) == -1, "should be the same"); + fail_if( condition_cmp(r1, r2) == -1, "should be the same"); r1->request_method = METHOD_GET; r2->request_method = METHOD_GET; - fail_if( route_cmp(r1, r2) == -1, "should be the same"); + fail_if( condition_cmp(r1, r2) == -1, "should be the same"); r1->request_method = METHOD_GET; r2->request_method = METHOD_POST; - fail_if( route_cmp(r1, r2) == 0, "should be different"); + fail_if( condition_cmp(r1, r2) == 0, "should be different"); - route_free(r1); - route_free(r2); + condition_free(r1); + condition_free(r2); } END_TEST @@ -249,11 +249,11 @@ START_TEST(test_insert_route) { int var1 = 22; int var2 = 33; - route *r1 = route_create("/blog/post"); - route *r2 = route_create("/blog/post"); + condition *r1 = condition_create("/blog/post"); + condition *r2 = condition_create("/blog/post"); r1->request_method = METHOD_GET; r2->request_method = METHOD_POST; - fail_if( route_cmp(r1, r2) == 0, "should be different"); + fail_if( condition_cmp(r1, r2) == 0, "should be different"); match_entry * entry = match_entry_create("/blog/post"); @@ -262,8 +262,8 @@ START_TEST(test_insert_route) r3_tree_insert_route(n, r2, &var2); match_entry_free(entry); - route_free(r1); - route_free(r2); + condition_free(r1); + condition_free(r2); } END_TEST @@ -275,7 +275,7 @@ START_TEST(benchmark_str) node * n = r3_tree_create(1); - int route_data = 999; + int condition_data = 999; r3_tree_insert_path(n, "/foo/bar/baz", NULL, NULL); r3_tree_insert_path(n, "/foo/bar/qux", NULL, NULL); @@ -412,7 +412,7 @@ r3_tree_insert_path(n, "/qux/foo/garply", NULL, NULL); r3_tree_insert_path(n, "/qux/bar/foo", NULL, NULL); r3_tree_insert_path(n, "/qux/bar/baz", NULL, NULL); r3_tree_insert_path(n, "/qux/bar/quux", NULL, NULL); -r3_tree_insert_path(n, "/qux/bar/corge", NULL, &route_data); +r3_tree_insert_path(n, "/qux/bar/corge", NULL, &condition_data); r3_tree_insert_path(n, "/qux/bar/grault", NULL, NULL); r3_tree_insert_path(n, "/qux/bar/garply", NULL, NULL); r3_tree_insert_path(n, "/qux/baz/foo", NULL, NULL);