2009-03-28 4 views

ответ

19

Явно вставьте value-1 в таблицу, а затем удалите строку.

Edit: следующий комментарий вниз, в котором обсуждается редактирование SQLITE_SEQUENCE таблицы непосредственно, вероятно, предпочтительнее: https://stackoverflow.com/a/692871/10093

+8

Я полагаю, что это лучший способ сделать это, но это некрасиво. –

+0

Это не работает для меня. Если у меня есть таблица «Пользователи» с только 1 записью (id 1), в то время как автоинкремент равен 3, тогда другой пользователь вставлен с идентификатором -1, затем удаляется, следующий вставленный пользователь все еще id 4 (расширение администратора SQLite для Firefox , если это имеет значение) – Assimilater

+1

кажется обходным путем. я предпочитаю обращаться к записи таблицы sqlite_sequence для рассматриваемой таблицы. –

6

Один из способов сделать это, чтобы вставить первую строку , указав явно идентификатор строки вы хотите начать с , Затем SQLite вставляет идентификаторы строк, которые выше предыдущего.

76

От SQLite web site:

SQLite отслеживает крупнейшие ROWID'ый, таблица была когда-либо проводившееся с помощью специальной SQLITE_SEQUENCE таблицы. Таблица SQLITE_SEQUENCE создается и инициализируется автоматически, когда создается нормальная таблица, содержащая столбец AUTOINCREMENT. Содержимое таблицы SQLITE_SEQUENCE может быть изменено с использованием обычных операторов UPDATE, INSERT и DELETE. Но внесение изменений в эту таблицу, вероятно, нарушит алгоритм генерации ключа AUTOINCREMENT. Убедитесь, что вы знаете, что делаете, прежде чем предпринимать такие изменения.

Я попробовал это, и это работает:

UPDATE SQLITE_SEQUENCE SET seq = <n> WHERE name = '<table>' 

Где п +1 это следующий ROWID вы хотите и таблица это имя таблицы.

+0

Не уверен, так как я не уверен, как работают внутренние элементы sqlite. Стоит отметить, что jle и мои предложения, приведенные выше, - это то, как библиотека PHP MDB2 поддерживает изменение идентификатора. Взгляните на их источник драйверов sqlite: http://cvs.php.net/viewvc.cgi/pear/MDB2/MDB2/Driver/sqlite.php?view=markup –

+0

Целостность не проблема (я думаю, не эксперт или что-то еще).Проблема, о которой я думаю, что они предупреждают о том, что вы удаляете строку с идентификатором меньше MAX (ID) и пытаетесь автоматически установить автоинкремент вручную. Вы будете застревать после первой вставленной строки из-за нарушения первичного ключа. – Assimilater

+0

Точный алгоритм документирован на связанной странице и не будет изменен ни в какой версии 3.x, чтобы сохранить совместимость. –

4

В решении с таблицей SQLITE_SEQUENCE запись в эту таблицу добавляется после добавления первой вставки в таблицу с добавлением столбца автоинкремента. В некоторых случаях это может вызвать проблемы (например, автоинкремент все же начинается с 1, а не из желаемого значения).

7

Я использую следующий запрос, который решает проблему, когда sqlite_sequence не имеет записи для таблицы (т. Е. Первая запись еще не добавлена ​​к таблице), в противном случае она обновляет последовательность.

BEGIN TRANSACTION; 

UPDATE sqlite_sequence SET seq = <n> WHERE name = '<table>'; 

INSERT INTO sqlite_sequence (name,seq) SELECT '<table>', <n> WHERE NOT EXISTS 
      (SELECT changes() AS change FROM sqlite_sequence WHERE change <> 0); 
COMMIT; 
+0

Это единственно верное решение. Изменения в вуду делают мои глаза водой, хотя;) – w00t

1

Теперь я использовал это как мое решение:

REPLACE INTO sqlite_sequence (name, seq) VALUES ('<table>', <n>) 

Эта работа для меня. Спасибо за ответ выше.

Смежные вопросы