1. 程式人生 > >Sqlite中判斷表、欄位是否存在的方法

Sqlite中判斷表、欄位是否存在的方法

  sqlite會自動維護一個系統表sqlite_master,該表儲存了我們所建立的各個table, view, trigger等等資訊。

sqlite_master表資料欄位:

type:  型別,取值一般為table, view name:     tbl_name:   表名 rootpage:

sql:建立表或者檢視的sql語句,可以從該sql語句中判斷某欄位是否存在


sqlite_master表結構如下:

[sql] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. CREATE TABLE sqlite_master (     
  2. type TEXT,     
  3. name TEXT,     
  4. tbl_name TEXT,     
  5. rootpage INTEGER,     
  6. sql TEXT     
  7. );   
CREATE TABLE sqlite_master (   
type TEXT,   
name TEXT,   
tbl_name TEXT,   
rootpage INTEGER,   
sql TEXT   
); 
例如: [sql] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. select * from sqlite_master where type = 'table' and name = 't_cmpt_cp'
      
select * from sqlite_master where type = 'table' and name = 't_cmpt_cp'
sql執行結果是:



1.   查詢與判斷

查詢sqlite中所有表,可用如下sql語句。

[sql] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. select name from sqlite_master where type='table' order by name;  
select name from sqlite_master where type='table' order by name;

我們可以通過如下語句檢視這個內建表的所有記錄:

[sql] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. select * from sqlite_master  
select * from sqlite_master

執行結果:


由此可以進一步引申:判斷指定的表是否存在,可以用如下語句:

[sql] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. select count(*)  from sqlite_master where type='table' and name = 'yourtablename';  
select count(*)  from sqlite_master where type='table' and name = 'yourtablename';

或者

其中yourtablename表示你要判斷的表名,如果查詢結果大於0,表示該表存在於資料庫中,否則不存在。

2.   查詢與判斷

通過以下語句可查詢出某個表的所有欄位資訊

PRAGMA  table_info([tablename])

比如:我想查看錶catalog的所有列資訊,可以用下述程式碼,結果如圖所示:

PRAGMA  table_info(t_cmpt_cp)


判斷某列是否存在的方法:

方法1:

[java] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. /** 
  2. * 檢查表中某列是否存在 
  3. * @param db 
  4. * @param tableName 表名 
  5. * @param columnName 列名 
  6. * @return 
  7. */  
  8. private boolean checkColumnExists2(SQLiteDatabase db, String tableName  
  9.        , String columnName) {  
  10.     boolean result = false ;  
  11.     Cursor cursor = null ;  
  12.     try{  
  13.         cursor = db.rawQuery( "select * from sqlite_master where name = ? and sql like ?"  
  14.            , new String[]{tableName , "%" + columnName + "%"} );  
  15.         result = null != cursor && cursor.moveToFirst() ;  
  16.     }catch (Exception e){  
  17.         Log.e(TAG,"checkColumnExists2..." + e.getMessage()) ;  
  18.     }finally{  
  19.         if(null != cursor && !cursor.isClosed()){  
  20.             cursor.close() ;  
  21.         }  
  22.     }  
  23.     return result ;  
  24. }  
/**
* 檢查表中某列是否存在
* @param db
* @param tableName 表名
* @param columnName 列名
* @return
*/
private boolean checkColumnExists2(SQLiteDatabase db, String tableName
       , String columnName) {
    boolean result = false ;
    Cursor cursor = null ;

    try{
        cursor = db.rawQuery( "select * from sqlite_master where name = ? and sql like ?"
           , new String[]{tableName , "%" + columnName + "%"} );
        result = null != cursor && cursor.moveToFirst() ;
    }catch (Exception e){
        Log.e(TAG,"checkColumnExists2..." + e.getMessage()) ;
    }finally{
        if(null != cursor && !cursor.isClosed()){
            cursor.close() ;
        }
    }

    return result ;
}

方法2:

[java] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. /**  
  2.  * 判斷某表裡某欄位是否存在  
  3.  *   
  4.  * @param db  
  5.  * @param tableName  
  6.  * @param fieldName  
  7.  * @return  
  8.  */    
  9. private boolean isFieldExist(SQLiteDatabase db, String tableName, String fieldName) {    
  10.     String queryStr = "select sql from sqlite_master where type = 'table' and name = '%s'";    
  11.     queryStr = String.format(queryStr, tableName);    
  12.     Cursor c = db.rawQuery(queryStr, null);    
  13.     String tableCreateSql = null;    
  14.     try {    
  15.         if (c != null && c.moveToFirst()) {    
  16.             tableCreateSql = c.getString(c.getColumnIndex("sql"));    
  17.         }    
  18.     } finally {    
  19.         if (c != null)    
  20.             c.close();    
  21.     }    
  22.     if (tableCreateSql != null && tableCreateSql.contains(fieldName))    
  23.         return true;    
  24.     return false;    
  25. }    
/** 
 * 判斷某表裡某欄位是否存在 
 *  
 * @param db 
 * @param tableName 
 * @param fieldName 
 * @return 
 */  
private boolean isFieldExist(SQLiteDatabase db, String tableName, String fieldName) {  
    String queryStr = "select sql from sqlite_master where type = 'table' and name = '%s'";  
    queryStr = String.format(queryStr, tableName);  
    Cursor c = db.rawQuery(queryStr, null);  
    String tableCreateSql = null;  
    try {  
        if (c != null && c.moveToFirst()) {  
            tableCreateSql = c.getString(c.getColumnIndex("sql"));  
        }  
    } finally {  
        if (c != null)  
            c.close();  
    }  
    if (tableCreateSql != null && tableCreateSql.contains(fieldName))  
        return true;  
    return false;  
}  
方法3:

根據 cursor.getColumnIndex(String columnName) 的返回值判斷,如果為-1表示表中無此欄位

[java] view plain copy print?在CODE上檢視程式碼片派生到我的程式碼片
  1. /** 
  2. * 檢查某表列是否存在 
  3. * @param db 
  4. * @param tableName 表名 
  5. * @param columnName 列名 
  6. * @return 
  7. */  
  8. private boolean checkColumnExist1(SQLiteDatabase db, String tableName  
  9.         , String columnName) {  
  10.     boolean result = false ;  
  11.     Cursor cursor = null ;  
  12.     try{  
  13.         //查詢一行  
  14.         cursor = db.rawQuery( "SELECT * FROM " + tableName + " LIMIT 0"  
  15.             , null );  
  16.         result = cursor != null && cursor.getColumnIndex(columnName) != -1 ;  
  17.     }catch (Exception e){  
  18.          Log.e(TAG,"checkColumnExists1..." + e.getMessage()) ;  
  19.     }finally{  
  20.         if(null != cursor && !cursor.isClosed()){  
  21.             cursor.close() ;  
  22.         }  
  23.     }  
  24.     return result ;  
  25. }  
/**
* 檢查某表列是否存在
* @param db
* @param tableName 表名
* @param columnName 列名
* @return
*/
private boolean checkColumnExist1(SQLiteDatabase db, String tableName
        , String columnName) {
    boolean result = false ;
    Cursor cursor = null ;
    try{
        //查詢一行
        cursor = db.rawQuery( "SELECT * FROM " + tableName + " LIMIT 0"
            , null );
        result = cursor != null && cursor.getColumnIndex(columnName) != -1 ;
    }catch (Exception e){
         Log.e(TAG,"checkColumnExists1..." + e.getMessage()) ;
    }finally{
        if(null != cursor && !cursor.isClosed()){
            cursor.close() ;
        }
    }

    return result ;
}


3.   Sqlite中新增、刪除、重新命名列

3.1   新增一列

方法:使用sql命令

命令:ALTER  TABLE   table-name ADD COLUMN  column-name column-type

例如:在student表中新增一列名為name,型別為varchar:

alter table student add column name varchar;

 alter table catalog add column xxx1 char(20) default '';

3.2   刪除一列

方法:由於drop命令在sqlite中不可用於刪除列,

alter table student drop column name // 該行在SQlite中不能用,SQlite不支援drop

可採用如下思路,類似於swap()函式的過程。

比如我有表A,A中有x、y、z三列。我要將表A中的x列刪掉。那麼,

第1步,新建一個表B,B中含有y、z兩個欄位,且型別與A中的y、z型別相同。

第2步,將A中的所有y、z兩列的值拷貝到B中。

上面兩步使用一句命令即可完成

create table B as select y,z from A

注意,如果A中y的型別為char,則上面create命令會在B中建立型別為TEXT的y列。即char型別會被改變。

第3步,將A表刪除

drop table if exists A

第4步,將B重新命名為A

alter table B rename to A

3.3   重新命名一列

方法:與刪除一列相同,在sqlite中alter同樣無法重新命名一列。如果想重新命名,那麼思路與刪除一列相同。

4.   Sqlite中新增、刪除、重命名錶


Sql語句在3.2中已有。整理如下。

4.1   新增表

create table A(id char(20),channeltext,name text,primary key (id))

create table B as select y,z from A

4.2   刪除表

drop table if exists A

4.3   重命名錶

alter table B rename to A