«Библиотечная процедура выбрана из последовательности» sqlite3_prepare_v2 (CREATE TABLE) - PullRequest
8 голосов
/ 04 декабря 2011

Знаете ли вы, почему я получаю «библиотечную подпрограмму, вызванную из последовательности», когда я вызываю sqlite3_prepare_v2(CREATE TABLE) для пустой базы данных?

Я создаю пустую базу данных, а затем открываю ее.Позже я сохраняю всю информацию, которая должна быть записана в базу данных в ОЗУ (мне нужно сохранить эту информацию в ОЗУ и сбросить ее в постоянное хранилище в конце выполнения), но я получаю это сообщение об ошибке при вызове sqlite3_prepare_v2(CREATE TABLE).Он возвращает «Библиотечная рутина, вызванная вне последовательности» в виде сообщения об ошибке.

Я правильно открываю свою базу данных и (я думал, что это может быть проблемой, поэтому я сделал close() мою БД и затем open() прямо перед вызовом sqlite3_prepare_v2(CREATE TABLE)).Я думал, что это может быть из-за параллелизма потоков, но использование критического раздела тоже не помогло.

Ответы [ 3 ]

12 голосов
/ 04 декабря 2011

Вот что документация говорит о причинах вашей ошибки:

  1. Вызов любой подпрограммы API с указателем sqlite3 *, который не был полученный из sqlite3_open () или sqlite3_open16 () или который имеет уже был закрыт sqlite3_close ().
  2. Попытка использовать одно и то же соединение с базой данных в одно и то же время в время из двух или более потоков.
  3. Вызов sqlite3_step () с указателем оператора sqlite3_stmt *, который не был получен из sqlite3_prepare () или sqlite3_prepare16 () или это уже было уничтожено sqlite3_finalize ().
  4. Попытка связать значения с оператором (используя sqlite3_bind _... ()) во время выполнения этого оператора.

Вы упомянули попытку критического раздела, так что я думаю, мы можем исключить # 2. Ваша ошибка является результатом вызова sqlite3_prepare_v2 (...), а не sqlite3_step () или или sqlite3_bind (), поэтому я предполагаю, что остается только номер 1? Можете ли вы дважды проверить, что ваш указатель БД хорош? Отследить его до sqlite3_open (), который его возвратил, и убедиться, что ничто не закрыло его перед тем, как вызывается ваша подготовка?

Это работает для меня:

#include <stdio.h>
#include <sqlite3.h>

int main(int argc, char **argv){

    sqlite3 *db;
    int rc;

    char *db_name= ":memory:";

    rc = sqlite3_open(db_name, &db);

    if (rc != SQLITE_OK) {
        fprintf(stderr, "failed to open in memory database: %s\n", 
                sqlite3_errmsg(db));
        sqlite3_close(db);
        return(1);
    }

    const char *create_sql = "CREATE TABLE foo(bar TEXT)";
    sqlite3_stmt *statement;

    rc = sqlite3_prepare_v2(db, create_sql, -1, &statement, NULL);

    if (rc != SQLITE_OK) {
        fprintf(stderr, "failed to prepare statement: %s\n",
                sqlite3_errmsg(db));
        sqlite3_close(db);
        return(1);
    }

    rc = sqlite3_step(statement);

    if (rc == SQLITE_ERROR) {
        fprintf(stderr, 
                "failed to execute statement: %s\n", 
                sqlite3_errmsg(db));
    }

    sqlite3_close(db);

}
1 голос
/ 16 декабря 2016

В моем случае это была строка, содержащая некоторые специальные символы, как это было (') одиночное двоеточие, я заменил его на ("") пробел, и он начал работать.[yourString stringByReplacingOccurferencesOfString: @ "'" withString: @ ""]

1 голос
/ 06 октября 2016

Все вышеприведенные решения верны.

Однако, возможно, вы написали неверное имя столбца или ошибка неверное имя столбца, введенное в ваш запрос, который вы хотите выполнять.

Потому что в моем случае я много раз получал ошибку, после чего проверял код построчно и обнаруживал свою ошибку

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...