0

アプリケーション データベースの作業を最適化してみてください。

データベースの同期中に、アプリケーションは 1 つのトランザクション内で「削除」コマンドと「挿入」コマンドの大きなパッケージを実行します。トランザクション「COMMIT」アプリケーションの後、「VACUUM」コマンドを実行します。VACUUM は正常に動作しますが、時間がかかる場合があります。そこで、「VACUUM」の実行を並列スレッドに移動することにしました。そして、ここで何かがうまくいかない。他のスレッドでは、「データベースがロックされています」と表示されます。

私がやること:

1.「COMMIT」が成功した後、データベースを閉じます。

2.「VACUUM」でデータベースを再度開いて閉じる別のメソッドを開始します。

「COMMIT」の同じスレッドでは「VACUUM」は正常に動作しますが、別のスレッドでは同じメソッドが「データベースがロックされています」というエラーを取得します。データベースの同期は論理的に別のアプリケーション プロセスであるため、クローズド データベースで動作するプロセスは他にないと断言できます。

私は何を間違っていますか?

    [connection closeDb];
    [connection release];

    if(!rollBackTransaction && commitSuccess){
// The commented code block doesn't work - "database is locked" error
//        NSThread *thread=[[NSThread alloc] initWithTarget:self selector:@selector(runVacuumForDataBase:) object:_dbFileName];
//        [thread start];
        [self runVacuumForDataBase:_dbFileName]; // <-- This works fine
    }
4

1 に答える 1

0

同時に 1 つのスレッドからのみ SQLite データベースにアクセスできます。あなたのケースでは、別のスレッドで VACUUM を実行しても機能しません。最初のトランザクションが終了するまで待つ必要があります。幸運を!

編集マルチスレッド環境を使用している場合、私はあなたと同じ問題に遭遇しました。最終的に、SQLite db のディスパッチ キューを使用することになりました。ここでは、db へのすべてのトランザクションが同期的に実行されます。データベースへのすべてのリクエストを別のスレッド(メインではなくセカンダリ)に移動することを強くお勧めします。

于 2013-10-17T11:17:28.437 に答える