如何索引SQLite表中的树?

时间:2011-12-31 07:15:12

标签: c++ c sqlite

我有一个包含以下字段的表:

id      VARCHAR(32) PRIMARY KEY,
parent  VARCHAR(32),
name    VARCHAR(32)

parent是引用同一个表的外键。该结构生成树。该树应该复制文件系统树。问题是从路径中查找id是懒散的。因此我想建立一个索引。这样做的最佳方式是什么?

示例数据:

   id          parent        name
--------    -----------    ----------
   1            NULL          root
   2             1            foo
   3             1            bar
   4             3            baz
   5             4            aii

索引到:

   id          parent        name
--------    -----------    ----------
   1            NULL          root
   2             1            root/foo
   3             1            root/bar
   4             3            root/bar/baz
   5             4            root/bar/baz/aii

我目前正在考虑使用临时表并在代码中手动运行一系列插入来构建索引。 (我将其设为临时的原因是,如果从Windows系统访问此数据库,则路径需要反斜杠,而从* nix需要正斜杠)。有替代方案吗?

1 个答案:

答案 0 :(得分:0)

所以,你有一个像这样的函数(伪代码):

int getId(char **path) {
    int id = 0;
    int i;
    char query[1000];

    for (i = 0; path[i] != NULL; i++) {
        sprintf(query, "select id from table where parent = %d and name = '%s'", id, name);
        id = QuerySimple(query);
        if (id < 0)
           break;
    }
    return id;
}

查看查询,您需要列(父,名称)上的(非唯一)索引,但也许您已经拥有它。

一个(临时)表可以像你说的那样使用,注意你可以改变程序中的路径分隔符,避免使用不同的windows和unix表。您还需要使附加表与主服务器保持同步。如果更新/删除/插入很少,而不是表,您只需保留已查找数据的内存缓存,并在更新发生时清除缓存(如果需要,还可以对缓存执行部分删除操作) )。在这种情况下,您还可以读取更多数据(例如,父级读取所有子级)以更快地填充缓存。在极端情况下,您可以在内存中读取整个表格并在那里工作!这取决于您拥有的数据量,典型的访问模式(读取次数,写入次数)以及部署环境(您是否有备用RAM?)。