2

私は3つのテーブルを持つsqlite3データベースを持っています:

CREATE TABLE document (
  id Int PRIMARY KEY NOT NULL,
  root_id Int,
  name Varchar(100),
  active Tinyint
);
CREATE INDEX IDX_documentId ON document (id);
CREATE INDEX IDX_documentName ON document (name);

CREATE TABLE dictionary (
  id Int PRIMARY KEY NOT NULL,
  word Varchar(100) NOT NULL
);
CREATE INDEX IDX_dictionaryId ON dictionary (id);
CREATE UNIQUE INDEX IDX_dictionaryWord ON dictionary (word ASC);

CREATE TABLE document_index (
  id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
  document_id Int NOT NULL,
  word_id Int NOT NULL,
  FOREIGN KEY(document_id) REFERENCES document(id),
  FOREIGN KEY(word_id) REFERENCES dictionary(id)
);
CREATE INDEX IDX_documentIndexId ON document_index (id);
CREATE INDEX IDX_documentIndexDocId ON document_index (document_id);
CREATE INDEX IDX_documentIndexWordId ON document_index (word_id);

そして、辞書から単語を含むすべてのドキュメントを選択するSQLスクリプトがあります。

SELECT document.id, document.name
FROM document
     INNER JOIN document_index on document_index.document_id=document.id
     INNER JOIN dictionary on dictionary.id=document_index.word_id
WHERE dictionary.word LIKE @pQuery
   AND document.active = 1
   AND document.root_id in (@pRoot1, @pRoot2, @pRoot3, @pRoot4, @pRoot5, @pRoot6, @pRoot7)

ディクショナリに ~= 400,000 レコード、ドキュメント ~= 1000 レコード、および document_index ~= 500,000 レコードが含まれている場合、クエリは iPad 2 で約 30 秒実行されます。

クエリを最適化する方法、またはデータベースの構造を変更する方法 (インデックスを追加するなど) を使用して、クエリ時間を短縮するにはどうすればよいですか?

4

4 に答える 4

2

SQLite Full Text Search extensionを使用する以外に、クエリを高速化する実用的な方法はないと思います。

FTS ではMATCH、本質的に slow ではなく、高速バージョンの節を使用できますLIKE

残念ながら、iOS では FTS はデフォルトで有効になっていませんが、独自のアプリを構築し、FTS が有効になっている SQLite の独自のコピーを含めると、それを行うことができるようです。

于 2013-01-04T09:02:51.913 に答える
2

ボトルネックはおそらく部品WHERE dictionary.word LIKE @pQueryです。

  1. Dictionary.word にインデックスがないため、SQLite は完全なテーブルをスキャンする必要があります。
  2. ほとんどの場合、インデックスを使用できない LIKE 演算子を使用しています。

文字列の等価性をチェックするだけでなく、ユースケースで LIKE クエリを使用することが本当に必要ですか?

于 2013-01-04T09:08:13.430 に答える
0

dictionary.word = @pQuery代わりに使用してみてくださいdictionary.word LIKE @pQuery

「分析」を実行します

于 2013-01-04T09:11:56.117 に答える
0

解決策を見つけました。このソリューションにより、60 でクエリの実行速度が向上しました。回。私はそれを見つけましたhereおよびより詳細な - here。それは簡単です、私は >= と < を比較するために LIKE 式を置き換えました:

年:

dictionary.word LIKE 'prezident%'

新着:

dictionary.word >= 'prezident' AND dictionary.word < 'prezidentz' /* Added z to the second string*/ 

このソリューションには 1 つの制限があります。文字列の一部で探すことができますが、文字列の最後にあるのは 'expr%' だけです。

助けてくれてありがとう!

于 2013-01-06T19:01:26.300 に答える