zoukankan      html  css  js  c++  java
  • Android SQLite数据库升级,怎么做(事物更改)

    SQLiteOpenHelper
    1 // 如果数据库文件不存在,只有onCreate()被调用(该方法在创建数据库时被调用一次)
    2 public abstract void onCreate(SQLiteDatabase db);
    3 // 如果数据库文件存在,会调用onUpgrade()方法升级数据库,并更新版本号。
    4 public abstract void onUpgrade(SQLiteDatabase db,int oldVersion,int newVersion);

    OnCreate : 如果数据库文件不存在,SQLiteOpenHelper在创建数据库文件,打开数据库这个数据库后,调用onCreate()方法,在该方法中一般需要创建表、视图等组件。在创建前数据库一般是空的,因此不需要先删除数据库中相关的组件。

    OnUpgrade : 当系统在构造SQLiteOpenHelper类的对象时,如果发现版本号不一样,就会自动调用onUpgrade函数,让你在这里对数据库进行升级。

    新版本号和老版本号都会作为onUpgrade函数的参数传进来,便于开发者知道数据库应该从哪个版本升级到哪个版本。

    升级完成后,数据库会自动存储最新的版本号为当前数据库版本号。

    需要对SQLite数据库的结构进行升级:

    SQLite提供了ALTER TABLE命令,允许用户重命名或添加新的字段到已有表中,但是不能从表中删除字段。
    并且只能在表的末尾添加字段,比如,为 Student添加两个字段:
    1 ALTER TABLE Student ADD COLUMN UserPhone VARCHAR;
    2 ALTER TABLE Student ADD COLUMN UserNickName VARCHAR;

    如果遇到复杂的修改操作,比如在修改的同时,需要进行数据的转移,那么可以采取在一个事务中执行如下语句来实现修改表的需求。
    1. 将表名改为临时表
             ALTER TABLE Student RENAME TO __temp__Student;

    2. 创建新表
            CREATE TABLE Student (UserId VARCHAR(32PRIMARY KEY ,UserName VARCHAR(32NOT NULL ,UserAddress VARCHAR(16NOT NULL);
      
    3. 导入数据  
             INSERT INTO Student  SELECT UserId, “”, UserAddress FROM __temp__Student;
    或者  
            INSERT INTO Student()  SELECT UserId, “”, UserAddress FROM __temp__Student;
    * 注意 双引号”” 是用来补充原来不存在的数据的
      
    4. 删除临时表  
            DROP TABLE __temp__Student;

      通过以上四个步骤,就可以完成旧数据库结构向新数据库结构的迁移,并且其中还可以保证数据不会应为升级而流失。
      当然,如果遇到减少字段的情况,也可以通过创建临时表的方式来实现。

    获取表中字段:

     1 // 获取升级前表中的字段
     2 protected String getColumnNames(SQLiteDatabase db, String tableName)
     3 {
     4   StringBuffer columnNameBuffer = null;
     5   Cursor c = null;
     6   try
     7   {
     8     c = db.rawQuery( "PRAGMA table_info(" + tableName + ")", null);
     9     if (null != c) {
    11       int columnIndex = c.getColumnIndex("name");
    12       if (-1 == columnIndex) {
    14         return null;
    15       }
    16 
    17       int index = 0;
    18       columnNameBuffer = new StringBuffer(c.getCount());
    19       for ( c.moveToFirst(); !c.isAfterLast(); c.moveToNext()) {
    21         columnNameBuffer.append(c.getString( columnIndex ));
    22         columnNameBuffer.append(",");
    23         index++;
    24       }
    25     }
    26   }
    27   catch (Exception e) {
    29     e.printStackTrace();
    30   }
    31   finally {
    33     if (c != null) {
    35       c.close();
    36     }
    37   }
    38   return columnNameBuffer.toString();40 }

    加上事物控制:

     1 // update table
     2 private void updateTable(SQLiteDatabase db, String tableName, String columns)
     3 {
     4     try
     5     {
     6        db.beginTransaction();
     7        String oldColumns = columns.substring(0, columns.length() - 1);
     8        // rename the table
     9        String tempTable = tableName + "texp_temptable";
    10        String renameTableSql = "alter table " + tableName + " rename to " + tempTable;
    11        db.execSQL(renameTableSql);
    12 
    14     // drop the oldtable
    15     String dropTableSql = "drop table if exists " + tableName;
    16     db.execSQL(dropTableSql);
    17     // creat table
    18     String createTableSql = "create table if not exists " + tableName + "(name text, pwd text, tel text)";
    19     db.execSQL(createTableSql);
    20     // load data
    21     String newColume = "tel";
    22     String newColumns = oldColumns + "," + newColumn;
    23     String insertSql = "insert into " + tableName + " (" + newColumns + ") " + "select " + oldColumns + "" + " " + " from " + tempTable;
    25     db.execSql(insertSql);
    26     db.setTransactionSuccessful();
    27   }
    28   catch (Exception e)
    29   {
    30     // TODO: handle exception
    31     Log.i( "tag", e.getMessage() );
    32   }
    33   finally
    34   {
    35     db.endTransaction();
    36   }
    39 }    

    //DBHelper: 

     1 public class DBHelper extends SQLiteOpenHelper {
     2  
     3     private static final String DATABASE_NAME = "student.db"; 
     4     private static final int DATABASE_VERSION = 1002;
     5  
     6     private static DBHelper instance = null;
     7  
     8  
     9     public DBHelper(Context context) {
    10         super(context, DATABASE_NAME, null, DATABASE_VERSION);
    11     }
    12      
    13     public synchronized static DBHelper getInstance(Context context) {
    14         if (instance == null) {
    15             instance = new DBHelper(context);
    16         }
    17         return instance;
    18     }
    19  
    20     @Override
    21     public void onCreate(SQLiteDatabase db) {
    22         db.execSQL(SQL.CREATE_TABLE_FAVORITE);
    23          
    24         // 若不是第一个版本安装,直接执行数据库升级
    25         // 请不要修改FIRST_DATABASE_VERSION的值,其为第一个数据库版本大小
    26         final int FIRST_DATABASE_VERSION = 1000;
    27         onUpgrade(db, FIRST_DATABASE_VERSION, DATABASE_VERSION);
    28     }
    29  
    30     @Override
    31     public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    32         // 使用for实现跨版本升级数据库
    33         for (int i = oldVersion; i < newVersion; i++) {
    34             switch (i) {
    35             case 1000:
    36                 upgradeToVersion1001(db);
    37                 break;
    38             case 1001:
    39                 upgradeToVersion1002(db);
    40                 break;
    41                  
    42             default:
    43                 break;
    44             }
    45         }
    46     }
    47      
    48     private void upgradeToVersion1001(SQLiteDatabase db){
    49         // student 表新增1个字段
    50         String sql1 = "ALTER TABLE Student ADD COLUMN age VARCHAR";
    51         db.execSQL(sql1);
    52     }
    53 private void upgradeToVersion1002(SQLiteDatabase db){ 54 // student 表新增2个字段, 添加新字段只能一个字段一个字段加,sqlite有限制不予许一条语句加多个字段 55 String sql1 = "ALTER TABLE Student ADD COLUMN tel VARCHAR"; 56 String sql2 = "ALTER TABLE Student ADD COLUMN address VARCHAR"; 57 db.execSQL(sql1); 58 db.execSQL(sql2); 59 } 60 }
  • 相关阅读:
    Atitit. visual studio vs2003 vs2005 vs2008  VS2010 vs2012 vs2015新特性 新功能.doc
    Atitit. C#.net clr 2.0  4.0新特性
    Atitit. C#.net clr 2.0  4.0新特性
    Atitit.通过null 参数 反射  动态反推方法调用
    Atitit.通过null 参数 反射  动态反推方法调用
    Atitit..net clr il指令集 以及指令分类  与指令详细说明
    Atitit..net clr il指令集 以及指令分类  与指令详细说明
    Atitit.变量的定义 获取 储存 物理结构 基本类型简化 隐式转换 类型推导 与底层原理 attilaxDSL
    Atitit.变量的定义 获取 储存 物理结构 基本类型简化 隐式转换 类型推导 与底层原理 attilaxDSL
    Atitit.跨语言反射api 兼容性提升与增强 java c#。Net  php  js
  • 原文地址:https://www.cnblogs.com/CharlesGrant/p/9144253.html
Copyright © 2011-2022 走看看