[Groonga-commit] groonga/groonga at 25fbc26 [master] select: support selectors that use index in slices

アーカイブの一覧に戻る

Kouhei Sutou null+****@clear*****
Fri Nov 11 17:31:28 JST 2016


Kouhei Sutou	2016-11-11 17:31:28 +0900 (Fri, 11 Nov 2016)

  New Revision: 25fbc269b1bf69ea113f1578bc4d9becaa6d17b6
  https://github.com/groonga/groonga/commit/25fbc269b1bf69ea113f1578bc4d9becaa6d17b6

  Message:
    select: support selectors that use index in slices
    
    Here are selectors supported by this change:
    
      * geo_in_circle()
      * geo_in_rectangle()
      * in_values()

  Added files:
    test/command/suite/select/slices/filtered/selector/geo_in_circle.expected
    test/command/suite/select/slices/filtered/selector/geo_in_circle.test
    test/command/suite/select/slices/filtered/selector/geo_in_rectangle.expected
    test/command/suite/select/slices/filtered/selector/geo_in_rectangle.test
    test/command/suite/select/slices/filtered/selector/in_values.expected
    test/command/suite/select/slices/filtered/selector/in_values.test
  Modified files:
    lib/expr.c
    lib/proc.c

  Modified: lib/expr.c (+98 -25)
===================================================================
--- lib/expr.c    2016-11-11 16:17:45 +0900 (0be94a9)
+++ lib/expr.c    2016-11-11 17:31:28 +0900 (13a6067)
@@ -6429,6 +6429,98 @@ grn_table_select_index_range_accessor(grn_ctx *ctx,
 }
 
 static inline grn_bool
+grn_table_select_index_call_selector(grn_ctx *ctx,
+                                     grn_obj *table,
+                                     grn_obj *index,
+                                     scan_info *si,
+                                     grn_obj *selector,
+                                     grn_obj *res)
+{
+  grn_bool processed = GRN_FALSE;
+  grn_proc *proc = (grn_proc *)selector;
+  grn_rc rc;
+
+  if (grn_logger_pass(ctx, GRN_REPORT_INDEX_LOG_LEVEL)) {
+    char name[GRN_TABLE_MAX_KEY_SIZE];
+    int name_size;
+    char tag[GRN_TABLE_MAX_KEY_SIZE];
+    name_size = grn_obj_name(ctx,
+                             (grn_obj *)selector,
+                             name,
+                             GRN_TABLE_MAX_KEY_SIZE);
+    grn_snprintf(tag, GRN_TABLE_MAX_KEY_SIZE, GRN_TABLE_MAX_KEY_SIZE,
+                 "[selector][%.*s]",
+                 name_size, name);
+    grn_table_select_index_report(ctx, tag, index);
+  }
+
+  if (index && index->header.type == GRN_ACCESSOR) {
+    grn_operator selector_op;
+    grn_obj *accessor = index;
+    unsigned int accessor_deep = 0;
+    grn_obj *base_table = NULL;
+    grn_obj *base_index = NULL;
+    grn_obj *base_res = NULL;
+    grn_accessor *a;
+
+    selector_op = grn_proc_get_selector_operator(ctx, selector);
+    for (a = (grn_accessor *)accessor; a; a = a->next) {
+      if (a->next) {
+        accessor_deep++;
+      } else {
+        grn_index_datum index_data;
+        unsigned int n_index_datum;
+
+        base_table = grn_ctx_at(ctx, a->obj->header.domain);
+        n_index_datum = grn_column_find_index_data(ctx,
+                                                   a->obj,
+                                                   selector_op,
+                                                   &index_data,
+                                                   1);
+        if (n_index_datum > 0) {
+          base_index = index_data.index;
+        }
+        base_res = grn_table_create(ctx, NULL, 0, NULL,
+                                    GRN_TABLE_HASH_KEY|GRN_OBJ_WITH_SUBREC,
+                                    base_table, NULL);
+      }
+    }
+    rc = proc->callbacks.function.selector(ctx,
+                                           base_table,
+                                           base_index,
+                                           si->nargs,
+                                           si->args,
+                                           base_res,
+                                           GRN_OP_OR);
+    if (rc == GRN_SUCCESS) {
+      grn_accessor_resolve(ctx,
+                           accessor,
+                           accessor_deep,
+                           base_res,
+                           res,
+                           si->logical_op);
+    }
+    grn_obj_close(ctx, base_res);
+  } else {
+    rc = proc->callbacks.function.selector(ctx,
+                                           table,
+                                           index,
+                                           si->nargs,
+                                           si->args,
+                                           res,
+                                           si->logical_op);
+  }
+
+  if (rc) {
+    /* TODO: report error */
+  } else {
+    processed = GRN_TRUE;
+  }
+
+  return processed;
+}
+
+static inline grn_bool
 grn_table_select_index_range(grn_ctx *ctx, grn_obj *table, grn_obj *index,
                              scan_info *si, grn_obj *res)
 {
@@ -6656,31 +6748,12 @@ grn_table_select_index(grn_ctx *ctx, grn_obj *table, scan_info *si,
       break;
     case GRN_OP_CALL :
       if (grn_obj_is_selector_proc(ctx, si->args[0])) {
-        grn_rc rc;
-        grn_proc *proc = (grn_proc *)(si->args[0]);
-        if (grn_logger_pass(ctx, GRN_REPORT_INDEX_LOG_LEVEL)) {
-          char proc_name[GRN_TABLE_MAX_KEY_SIZE];
-          int proc_name_size;
-          char tag[GRN_TABLE_MAX_KEY_SIZE];
-          proc_name_size = grn_obj_name(ctx, (grn_obj *)proc,
-                                        proc_name, GRN_TABLE_MAX_KEY_SIZE);
-          proc_name[proc_name_size] = '\0';
-          grn_snprintf(tag, GRN_TABLE_MAX_KEY_SIZE, GRN_TABLE_MAX_KEY_SIZE,
-                       "[selector][%s]", proc_name);
-          grn_table_select_index_report(ctx, tag, index);
-        }
-        rc = proc->callbacks.function.selector(ctx,
-                                               table,
-                                               index,
-                                               si->nargs,
-                                               si->args,
-                                               res,
-                                               si->logical_op);
-        if (rc) {
-          /* TODO: report error */
-        } else {
-          processed = GRN_TRUE;
-        }
+        processed = grn_table_select_index_call_selector(ctx,
+                                                         table,
+                                                         index,
+                                                         si,
+                                                         si->args[0],
+                                                         res);
       }
       break;
     case GRN_OP_LESS :

  Modified: lib/proc.c (+7 -71)
===================================================================
--- lib/proc.c    2016-11-11 16:17:45 +0900 (74e22c1)
+++ lib/proc.c    2016-11-11 17:31:28 +0900 (496ab9e)
@@ -2461,13 +2461,13 @@ selector_between_sequential_search(grn_ctx *ctx,
 }
 
 static grn_rc
-selector_between_no_accessor(grn_ctx *ctx,
-                             grn_obj *table,
-                             grn_obj *index,
-                             int nargs,
-                             grn_obj **args,
-                             grn_obj *res,
-                             grn_operator op)
+selector_between(grn_ctx *ctx,
+                 grn_obj *table,
+                 grn_obj *index,
+                 int nargs,
+                 grn_obj **args,
+                 grn_obj *res,
+                 grn_operator op)
 {
   grn_rc rc = GRN_SUCCESS;
   int offset = 0;
@@ -2538,70 +2538,6 @@ exit :
   return rc;
 }
 
-static grn_rc
-selector_between(grn_ctx *ctx,
-                 grn_obj *table,
-                 grn_obj *index,
-                 int nargs,
-                 grn_obj **args,
-                 grn_obj *res,
-                 grn_operator op)
-{
-  grn_rc rc = GRN_SUCCESS;
-
-  if (index && index->header.type == GRN_ACCESSOR) {
-    grn_obj *accessor = index;
-    unsigned int accessor_deep = 0;
-    grn_obj *base_table = NULL;
-    grn_obj *base_index = NULL;
-    grn_obj *base_res = NULL;
-    grn_accessor *a;
-
-    for (a = (grn_accessor *)accessor; a; a = a->next) {
-      if (a->next) {
-        accessor_deep++;
-      } else {
-        grn_index_datum index_data;
-        unsigned int n_index_datum;
-
-        base_table = grn_ctx_at(ctx, a->obj->header.domain);
-        n_index_datum = grn_column_find_index_data(ctx,
-                                                   a->obj,
-                                                   GRN_OP_LESS,
-                                                   &index_data,
-                                                   1);
-        if (n_index_datum > 0) {
-          base_index = index_data.index;
-        }
-        base_res = grn_table_create(ctx, NULL, 0, NULL,
-                                    GRN_TABLE_HASH_KEY|GRN_OBJ_WITH_SUBREC,
-                                    base_table, NULL);
-      }
-    }
-    rc = selector_between_no_accessor(ctx,
-                                      base_table,
-                                      base_index,
-                                      nargs,
-                                      args,
-                                      base_res,
-                                      GRN_OP_OR);
-    if (rc == GRN_SUCCESS) {
-      grn_accessor_resolve(ctx, accessor, accessor_deep, base_res, res, op);
-    }
-    grn_obj_close(ctx, base_res);
-  } else {
-    rc = selector_between_no_accessor(ctx,
-                                      table,
-                                      index,
-                                      nargs,
-                                      args,
-                                      res,
-                                      op);
-  }
-
-  return rc;
-}
-
 static grn_obj *
 func_in_values(grn_ctx *ctx, int nargs, grn_obj **args, grn_user_data *user_data)
 {

  Added: test/command/suite/select/slices/filtered/selector/geo_in_circle.expected (+154 -0) 100644
===================================================================
--- /dev/null
+++ test/command/suite/select/slices/filtered/selector/geo_in_circle.expected    2016-11-11 17:31:28 +0900 (470e7b0)
@@ -0,0 +1,154 @@
+log_level --level info
+[[0,0.0,0.0],true]
+select LandMarks   --limit 0   --filter '_id > 1'   --slices[point].filter 'geo_in_circle(point, "11x11", "11x8")'   --slices[point].sort_keys _id   --slices[point].limit -1
+[
+  [
+    0,
+    0.0,
+    0.0
+  ],
+  [
+    [
+      [
+        624
+      ],
+      [
+        [
+          "_id",
+          "UInt32"
+        ],
+        [
+          "point",
+          "WGS84GeoPoint"
+        ]
+      ]
+    ],
+    {
+      "point": [
+        [
+          27
+        ],
+        [
+          [
+            "_id",
+            "UInt32"
+          ],
+          [
+            "point",
+            "WGS84GeoPoint"
+          ]
+        ],
+        [
+          235,
+          "9x9"
+        ],
+        [
+          236,
+          "9x10"
+        ],
+        [
+          237,
+          "9x11"
+        ],
+        [
+          238,
+          "9x12"
+        ],
+        [
+          239,
+          "9x13"
+        ],
+        [
+          260,
+          "10x9"
+        ],
+        [
+          261,
+          "10x10"
+        ],
+        [
+          262,
+          "10x11"
+        ],
+        [
+          263,
+          "10x12"
+        ],
+        [
+          264,
+          "10x13"
+        ],
+        [
+          284,
+          "11x8"
+        ],
+        [
+          285,
+          "11x9"
+        ],
+        [
+          286,
+          "11x10"
+        ],
+        [
+          287,
+          "11x11"
+        ],
+        [
+          288,
+          "11x12"
+        ],
+        [
+          289,
+          "11x13"
+        ],
+        [
+          290,
+          "11x14"
+        ],
+        [
+          310,
+          "12x9"
+        ],
+        [
+          311,
+          "12x10"
+        ],
+        [
+          312,
+          "12x11"
+        ],
+        [
+          313,
+          "12x12"
+        ],
+        [
+          314,
+          "12x13"
+        ],
+        [
+          335,
+          "13x9"
+        ],
+        [
+          336,
+          "13x10"
+        ],
+        [
+          337,
+          "13x11"
+        ],
+        [
+          338,
+          "13x12"
+        ],
+        [
+          339,
+          "13x13"
+        ]
+      ]
+    }
+  ]
+]
+#|i| [table][select][index][selector][geo_in_circle] <>
+#|i| [accessor][resolve][table] (temporary) -> <LandMarks>

  Added: test/command/suite/select/slices/filtered/selector/geo_in_circle.test (+10 -0) 100644
===================================================================
--- /dev/null
+++ test/command/suite/select/slices/filtered/selector/geo_in_circle.test    2016-11-11 17:31:28 +0900 (d057dac)
@@ -0,0 +1,10 @@
+#@include fixture/geo/in_circle/north_east.grn
+
+log_level --level info
+#@add-important-log-levels info
+select LandMarks \
+  --limit 0 \
+  --filter '_id > 1' \
+  --slices[point].filter 'geo_in_circle(point, "11x11", "11x8")' \
+  --slices[point].sort_keys _id \
+  --slices[point].limit -1

  Added: test/command/suite/select/slices/filtered/selector/geo_in_rectangle.expected (+190 -0) 100644
===================================================================
--- /dev/null
+++ test/command/suite/select/slices/filtered/selector/geo_in_rectangle.expected    2016-11-11 17:31:28 +0900 (cd571b7)
@@ -0,0 +1,190 @@
+log_level --level info
+[[0,0.0,0.0],true]
+select LandMarks   --limit 0   --filter '_id > 1'   --slices[point].filter 'geo_in_rectangle(point, "13x8", "8x13")'   --slices[point].sort_keys _id   --slices[point].limit -1
+[
+  [
+    0,
+    0.0,
+    0.0
+  ],
+  [
+    [
+      [
+        624
+      ],
+      [
+        [
+          "_id",
+          "UInt32"
+        ],
+        [
+          "point",
+          "WGS84GeoPoint"
+        ]
+      ]
+    ],
+    {
+      "point": [
+        [
+          36
+        ],
+        [
+          [
+            "_id",
+            "UInt32"
+          ],
+          [
+            "point",
+            "WGS84GeoPoint"
+          ]
+        ],
+        [
+          209,
+          "8x8"
+        ],
+        [
+          210,
+          "8x9"
+        ],
+        [
+          211,
+          "8x10"
+        ],
+        [
+          212,
+          "8x11"
+        ],
+        [
+          213,
+          "8x12"
+        ],
+        [
+          214,
+          "8x13"
+        ],
+        [
+          234,
+          "9x8"
+        ],
+        [
+          235,
+          "9x9"
+        ],
+        [
+          236,
+          "9x10"
+        ],
+        [
+          237,
+          "9x11"
+        ],
+        [
+          238,
+          "9x12"
+        ],
+        [
+          239,
+          "9x13"
+        ],
+        [
+          259,
+          "10x8"
+        ],
+        [
+          260,
+          "10x9"
+        ],
+        [
+          261,
+          "10x10"
+        ],
+        [
+          262,
+          "10x11"
+        ],
+        [
+          263,
+          "10x12"
+        ],
+        [
+          264,
+          "10x13"
+        ],
+        [
+          284,
+          "11x8"
+        ],
+        [
+          285,
+          "11x9"
+        ],
+        [
+          286,
+          "11x10"
+        ],
+        [
+          287,
+          "11x11"
+        ],
+        [
+          288,
+          "11x12"
+        ],
+        [
+          289,
+          "11x13"
+        ],
+        [
+          309,
+          "12x8"
+        ],
+        [
+          310,
+          "12x9"
+        ],
+        [
+          311,
+          "12x10"
+        ],
+        [
+          312,
+          "12x11"
+        ],
+        [
+          313,
+          "12x12"
+        ],
+        [
+          314,
+          "12x13"
+        ],
+        [
+          334,
+          "13x8"
+        ],
+        [
+          335,
+          "13x9"
+        ],
+        [
+          336,
+          "13x10"
+        ],
+        [
+          337,
+          "13x11"
+        ],
+        [
+          338,
+          "13x12"
+        ],
+        [
+          339,
+          "13x13"
+        ]
+      ]
+    }
+  ]
+]
+#|i| [table][select][index][selector][geo_in_rectangle] <>
+#|i| [accessor][resolve][table] (temporary) -> <LandMarks>

  Added: test/command/suite/select/slices/filtered/selector/geo_in_rectangle.test (+10 -0) 100644
===================================================================
--- /dev/null
+++ test/command/suite/select/slices/filtered/selector/geo_in_rectangle.test    2016-11-11 17:31:28 +0900 (8f3b7f4)
@@ -0,0 +1,10 @@
+#@include fixture/geo/in_circle/north_east.grn
+
+log_level --level info
+#@add-important-log-levels info
+select LandMarks \
+  --limit 0 \
+  --filter '_id > 1' \
+  --slices[point].filter 'geo_in_rectangle(point, "13x8", "8x13")' \
+  --slices[point].sort_keys _id \
+  --slices[point].limit -1

  Added: test/command/suite/select/slices/filtered/selector/in_values.expected (+108 -0) 100644
===================================================================
--- /dev/null
+++ test/command/suite/select/slices/filtered/selector/in_values.expected    2016-11-11 17:31:28 +0900 (352894d)
@@ -0,0 +1,110 @@
+table_create Memos TABLE_HASH_KEY ShortText
+[[0,0.0,0.0],true]
+column_create Memos date COLUMN_SCALAR Time
+[[0,0.0,0.0],true]
+table_create Times TABLE_PAT_KEY Time
+[[0,0.0,0.0],true]
+column_create Times memos_date COLUMN_INDEX Memos date
+[[0,0.0,0.0],true]
+load --table Memos
+[
+{"_key": "Groonga is fast!", "date": "2016-05-19 12:00:00"},
+{"_key": "Mroonga is fast!", "date": "2016-05-19 12:00:01"},
+{"_key": "Groonga sticker!", "date": "2016-05-19 12:00:02"},
+{"_key": "Rroonga is fast!", "date": "2016-05-19 12:00:03"}
+]
+[[0,0.0,0.0],4]
+log_level --level info
+[[0,0.0,0.0],true]
+select Memos   --filter '_id > 1'   --slices[groonga].filter 'in_values(date,                                       "2016-05-19 12:00:00",                                       "2016-05-19 12:00:01",                                       "2016-05-19 12:00:03")'
+[
+  [
+    0,
+    0.0,
+    0.0
+  ],
+  [
+    [
+      [
+        3
+      ],
+      [
+        [
+          "_id",
+          "UInt32"
+        ],
+        [
+          "_key",
+          "ShortText"
+        ],
+        [
+          "date",
+          "Time"
+        ]
+      ],
+      [
+        2,
+        "Mroonga is fast!",
+        1463626801.0
+      ],
+      [
+        3,
+        "Groonga sticker!",
+        1463626802.0
+      ],
+      [
+        4,
+        "Rroonga is fast!",
+        1463626803.0
+      ]
+    ],
+    {
+      "groonga": [
+        [
+          2
+        ],
+        [
+          [
+            "_id",
+            "UInt32"
+          ],
+          [
+            "_key",
+            "ShortText"
+          ],
+          [
+            "date",
+            "Time"
+          ]
+        ],
+        [
+          2,
+          "Mroonga is fast!",
+          1463626801.0
+        ],
+        [
+          4,
+          "Rroonga is fast!",
+          1463626803.0
+        ]
+      ]
+    }
+  ]
+]
+#|i| [table][select][index][selector][in_values] <>
+#|i| [object][search][index][key][exact] <Times.memos_date>
+#|i| grn_ii_sel > ()
+#|i| n=1 ()
+#|i| exact: 1
+#|i| hits=1
+#|i| [object][search][index][key][exact] <Times.memos_date>
(binary line)
(binary line)
+#|i| exact: 2
+#|i| hits=2
+#|i| [object][search][index][key][exact] <Times.memos_date>
+#|i| grn_ii_sel > (タ2ュ+)3)
+#|i| n=1 (タ2ュ+)3)
+#|i| exact: 3
+#|i| hits=3
+#|i| [accessor][resolve][table] (temporary) -> <Memos> -> <ShortText>

  Added: test/command/suite/select/slices/filtered/selector/in_values.test (+22 -0) 100644
===================================================================
--- /dev/null
+++ test/command/suite/select/slices/filtered/selector/in_values.test    2016-11-11 17:31:28 +0900 (d701fa1)
@@ -0,0 +1,22 @@
+table_create Memos TABLE_HASH_KEY ShortText
+column_create Memos date COLUMN_SCALAR Time
+
+table_create Times TABLE_PAT_KEY Time
+column_create Times memos_date COLUMN_INDEX Memos date
+
+load --table Memos
+[
+{"_key": "Groonga is fast!", "date": "2016-05-19 12:00:00"},
+{"_key": "Mroonga is fast!", "date": "2016-05-19 12:00:01"},
+{"_key": "Groonga sticker!", "date": "2016-05-19 12:00:02"},
+{"_key": "Rroonga is fast!", "date": "2016-05-19 12:00:03"}
+]
+
+log_level --level info
+#@add-important-log-levels info
+select Memos \
+  --filter '_id > 1' \
+  --slices[groonga].filter 'in_values(date, \
+                                      "2016-05-19 12:00:00", \
+                                      "2016-05-19 12:00:01", \
+                                      "2016-05-19 12:00:03")'
-------------- next part --------------
HTML����������������������������...
ダウンロード 



More information about the Groonga-commit mailing list
アーカイブの一覧に戻る