2011-12-31 13 views
0

私は、次のフィールドを持つテーブルがある:SQLiteテーブルのツリーをどのようにインデックスできますか?

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

親が同じテーブルを参照する外部キーです。この構造体はツリーを生成します。このツリーは、ファイルシステムツリーを複製することになっています。問題は、パスから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 

私は現在、インデックスを構築するために、手動でのからのインサートのシリーズを実行している一時テーブルを使用して、コードで考えています。 (私が一時的にするのは、このdbにWindowsシステムからアクセスすると、パスにはバックスラッシュが必要であるのに対し、* nixではスラッシュが必要なためです。これに代わる方法はありますか?

答えて

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を確保していますか?)によって異なります。