Удалить столбец из таблицы SQLite

У меня проблема: мне нужно удалить столбец из моей базы данных SQLite. Я написал этот запрос

alter table table_name drop column column_name 

Но это не работает. Пожалуйста, помогите мне.

От: http://www.sqlite.org/faq.html :

(11) Как добавить или удалить столбцы из существующей таблицы в SQLite.

SQLite имеет ограниченную поддержку ALTER TABLE, которую можно использовать для добавления столбца в конец таблицы или для изменения имени таблицы. Если вы хотите внести более сложные изменения в структуру таблицы, вам придется воссоздать таблицу. Вы можете сохранить существующие данные во временную таблицу, удалить старую таблицу, создать новую таблицу и затем скопировать данные из временной таблицы.

Например, предположим, что у вас есть таблица с именем «t1» с именами столбцов «a», «b» и «c» и что вы хотите удалить столбец «c» из этой таблицы. Следующие шаги иллюстрируют, как это можно сделать:

 BEGIN TRANSACTION; CREATE TEMPORARY TABLE t1_backup(a,b); INSERT INTO t1_backup SELECT a,b FROM t1; DROP TABLE t1; CREATE TABLE t1(a,b); INSERT INTO t1 SELECT a,b FROM t1_backup; DROP TABLE t1_backup; COMMIT; 

Вместо того, чтобы отбрасывать резервную таблицу, просто переименуйте ее …

 BEGIN TRANSACTION; CREATE TABLE t1_backup(a,b); INSERT INTO t1_backup SELECT a,b FROM t1; DROP TABLE t1; ALTER TABLE t1_backup RENAME TO t1; COMMIT; 

Для простоты почему бы не создать таблицу резервного копирования из оператора select?

 CREATE TABLE t1_backup AS SELECT a, b FROM t1; DROP TABLE t1; ALTER TABLE t1_backup RENAME TO t1; 

http://lists.osgeo.org/pipermail/grass-user/2006-January/031981.html

Существует также инструмент под названием Sqliteman, который предоставляет визуальный вариант для удаления столбцов.

Спасибо, Jignesh

=> Создать новую таблицу непосредственно со следующим запросом:

 CREATE TABLE Table_name (Column_1 text,Column_2 text); 

=> Теперь вставьте данные в table_name из Existing_table со следующим запросом:

 insert into Table_name (Column_1,Column_2) FROM Existing_Table; 

=> Теперь отмените Existing_table следующим запросом:

 DROP Existing_Table; 

Для SQLite3 c ++:

 void GetTableColNames( tstring sTableName , std::vector<tstring> *pvsCols ) { UASSERT(pvsCols); CppSQLite3Table table1; tstring sDML = StringOps::std_sprintf(_T("SELECT * FROM %s") , sTableName.c_str() ); table1 = getTable( StringOps::tstringToUTF8string(sDML).c_str() ); for ( int nCol = 0 ; nCol < table1.numFields() ; nCol++ ) { const char* pch1 = table1.fieldName(nCol); pvsCols->push_back( StringOps::UTF8charTo_tstring(pch1)); } } bool ColExists( tstring sColName ) { bool bColExists = true; try { tstring sQuery = StringOps::std_sprintf(_T("SELECT %s FROM MyOriginalTable LIMIT 1;") , sColName.c_str() ); ShowVerbalMessages(false); CppSQLite3Query q = execQuery( StringOps::tstringTo_stdString(sQuery).c_str() ); ShowVerbalMessages(true); } catch (CppSQLite3Exception& e) { bColExists = false; } return bColExists; } void DeleteColumns( std::vector<tstring> *pvsColsToDelete ) { UASSERT(pvsColsToDelete); execDML( StringOps::tstringTo_stdString(_T("begin transaction;")).c_str() ); std::vector<tstring> vsCols; GetTableColNames( _T("MyOriginalTable") , &vsCols ); CreateFields( _T("TempTable1") , false ); tstring sFieldNamesSeperatedByCommas; for ( int nCol = 0 ; nCol < vsCols.size() ; nCol++ ) { tstring sColNameCurr = vsCols.at(nCol); bool bUseCol = true; for ( int nColsToDelete = 0; nColsToDelete < pvsColsToDelete->size() ; nColsToDelete++ ) { if ( pvsColsToDelete->at(nColsToDelete) == sColNameCurr ) { bUseCol = false; break; } } if ( bUseCol ) sFieldNamesSeperatedByCommas+= (sColNameCurr + _T(",")); } if ( sFieldNamesSeperatedByCommas.at( int(sFieldNamesSeperatedByCommas.size()) - 1) == _T(',')) sFieldNamesSeperatedByCommas.erase( int(sFieldNamesSeperatedByCommas.size()) - 1 ); tstring sDML; sDML = StringOps::std_sprintf(_T("insert into TempTable1 SELECT %s FROM MyOriginalTable;\n") , sFieldNamesSeperatedByCommas.c_str() ); execDML( StringOps::tstringTo_stdString(sDML).c_str() ); sDML = StringOps::std_sprintf(_T("ALTER TABLE MyOriginalTable RENAME TO MyOriginalTable_old\n") ); execDML( StringOps::tstringTo_stdString(sDML).c_str() ); sDML = StringOps::std_sprintf(_T("ALTER TABLE TempTable1 RENAME TO MyOriginalTable\n") ); execDML( StringOps::tstringTo_stdString(sDML).c_str() ); sDML = ( _T("DROP TABLE MyOriginalTable_old;") ); execDML( StringOps::tstringTo_stdString(sDML).c_str() ); execDML( StringOps::tstringTo_stdString(_T("commit transaction;")).c_str() ); } 

Если кому-то нужна (почти) готовая к использованию функция PHP, на основе этого ответа будет построено следующее :

 /** * Remove a column from a table. * * @param string $tableName The table to remove the column from. * @param string $columnName The column to remove from the table. */ public function DropTableColumn($tableName, $columnName) { // -- // Determine all columns except the one to remove. $columnNames = array(); $statement = $pdo->prepare("PRAGMA table_info($tableName);"); $statement->execute(array()); $rows = $statement->fetchAll(PDO::FETCH_OBJ); $hasColumn = false; foreach ($rows as $row) { if(strtolower($row->name) !== strtolower($columnName)) { array_push($columnNames, $row->name); } else { $hasColumn = true; } } // Column does not exist in table, no need to do anything. if ( !$hasColumn ) return; // -- // Actually execute the SQL. $columns = implode('`,`', $columnNames); $statement = $pdo->exec( "CREATE TABLE `t1_backup` AS SELECT `$columns` FROM `$tableName`; DROP TABLE `$tableName`; ALTER TABLE `t1_backup` RENAME TO `$tableName`;"); } 

В отличие от других ответов, SQL, используемый в этом подходе, по-видимому, сохраняет типы данных столбцов, тогда как что-то вроде принятого ответа, по-видимому, приводит ко всем столбцам типа TEXT .

Обновление 1:

Используемый SQL имеет недостаток, что столбцы autoincrement не сохраняются.

Эта опция работает только в том случае, если вы можете открыть БД в браузере БД, таком как Браузер БД для SQLite .

В DB Browser для SQLite:

  1. Перейдите на вкладку «Структура базы данных»
  2. Выбор таблицы Выберите таблицу Изменить (только под вкладками)
  3. Выберите столбец, который вы хотите удалить.
  4. Нажмите «Удалить» и нажмите «ОК».