zoukankan      html  css  js  c++  java
  • android数据库升级的措辞

    在基类table增加upgrade操作:

    public abstract class DbBaseTable {
    
    	private static final String TAG = "DbBaseTable";
    
    	/**
    	 * @return the DB table name
    	 */
    	abstract String getName();
    
    	/**
    	 * Creates the DB table according to the DB scheme
    	 * 
    	 * @param db
    	 */
    	abstract void onCreate(SQLiteDatabase db);
    	
    	void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion, String tempName) {
            
            //Rename old table to temporary name
    	<strong>DbUtils.renameTable(db, getName(), tempName);</strong>
    		
            //Create clear table according to the new scheme
           <strong> onCreate(db);</strong>
            //Copy content of the matching columns from the old table to the new one
           <strong> joinColumns(db, tempName, getName());</strong>
            
            //Delete old table
           <strong> DbUtils.dropTable(db, tempName);</strong>
            
            //这个是更新一些表的内容
            initTableContent(db);
        }
        
        void initTableContent(SQLiteDatabase db) {
        }
       
        void joinColumns(SQLiteDatabase db, String tempName, String tableName) {
        	<strong>DbUtils.joinColumns(db, tempName, tableName);</strong>
        }
    
    }
    

    final class DbUtils {
        
        private static final String TAG = "DbUtils";
        private static final boolean DEBUG = false;
        
        private static final String SQLITE_STMT_LIST_TABLES =
            "SELECT name FROM sqlite_master WHERE type='table' AND name NOT LIKE 'sqlite_%' AND name NOT LIKE 'android%'";
        private static final String SQLITE_TABLE_NAME_COLUMN = "name";
        private static final String SQLITE_STMT_TEMPLATE_LIST_COLUMNS = "SELECT * FROM %s LIMIT 1";
        private static final String SQLITE_STMT_TEMPLATE_DROP_TABLE = "DROP TABLE IF EXISTS %s";
        private static final String SQLITE_STMT_TEMPLATE_RENAME_TABLE = "ALTER TABLE %s RENAME TO %s";
        private static final String SQLITE_STMT_TEMPLATE_COPY_COLUMNS = "INSERT INTO %s (%s) SELECT %s FROM %s";
    
        
        /**
         * @param db
         * @return Collection object containing table names in the database 
         */
        static Collection<String> listTables(SQLiteDatabase db) {
    
            Cursor cursor = db.rawQuery(SQLITE_STMT_LIST_TABLES, null);
            if (cursor == null || !cursor.moveToFirst()) {
    
                if (cursor != null) {
                    cursor.close();
                }
                return null;
            }
            
            int table_name_column = cursor.getColumnIndex(SQLITE_TABLE_NAME_COLUMN);
            HashSet<String> tables = new HashSet<String>(cursor.getCount());
            do {
                tables.add(cursor.getString(table_name_column));
            } while (cursor.moveToNext());
            cursor.close();
    
            
            return tables;
        }
    
        
        /**
         * @param db
         * @param table
         * @return List of column names in the DB table
         */
        public static List<String> listColumns(SQLiteDatabase db, String table) {
            
            Cursor cursor = db.rawQuery(String.format(SQLITE_STMT_TEMPLATE_LIST_COLUMNS, table), null);
            if (cursor == null) {
                return null;
            }
            
            List<String> columns = Arrays.asList(cursor.getColumnNames());
            cursor.close();
    
            return columns;
        }
        
        
        /**
         * @param db
         * @param table
         */
        static void dropTable(SQLiteDatabase db, String table) {
    
            db.execSQL(String.format(SQLITE_STMT_TEMPLATE_DROP_TABLE, table));
        }
        
    
        static void renameTable(SQLiteDatabase db, String oldName, String newName) {
    
            db.execSQL(String.format(SQLITE_STMT_TEMPLATE_RENAME_TABLE, oldName, newName));
        }
        
        
        static void joinColumns(SQLiteDatabase db, String oldTable, String newTable) {
            
            //Delete all records in the new table before copying from the old table
            db.delete(newTable, null, null);
            
            //Find columns which exist in both tables
            ArrayList<String> old_columns = new ArrayList<String>(listColumns(db, oldTable));
            List<String> new_columns = listColumns(db, newTable);
            old_columns.retainAll(new_columns);
    
            String common_columns = TextUtils.join(",", old_columns);
            
            //Copy records from old table to new table  example:<span style="font-family: 微软雅黑;"><strong><span style="font-size:10px;">INSERT INTO Mytest1 (_id,account_id,test1,test3) SELECT _id,account_id,test1,test3 FROM Mytest1_temp_</span></strong></span>
            db.execSQL(String.format(SQLITE_STMT_TEMPLATE_COPY_COLUMNS, newTable, common_columns, common_columns, oldTable));
        }
    
    }
    

    然后在DBHelper中重载onUpgrade方法:

     @Override
        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    
            //Get table names in the old DB
            Collection<String> old_tables = DbUtils.listTables(db);
            if (old_tables == null || old_tables.size() == 0) {
                onCreate(db);
                return;
            }
            
            //Get table names in the new DB
            Set<String> new_tables = DataBaseClass.sRCMDbTables.keySet();
            
            try {
                db.beginTransaction();
                //Remove old tables which are not in the new DB scheme
                HashSet<String> obsolete_tables = new HashSet<String>();
                for (String table : old_tables) {
                    if (!new_tables.contains(table)) {
                    	System.out.println("====DBHelp onUpgrade droptable table="+table);
                        DbUtils.dropTable(db, table);
                        obsolete_tables.add(table);
                    }
                }
                old_tables.removeAll(obsolete_tables);
        
                //Create and upgrade new tables 
                DbBaseTable table_descriptor; 
                for (String table : new_tables) {
                    table_descriptor = DataBaseClass.sRCMDbTables.get(table);
                    
                    //Check if the new table exists in the old DB
                    if (old_tables.contains(table)) {
                        String temp_name = getTempTableName(table, old_tables, new_tables);
                        System.out.println("====DBHelp onUpgrade temp_name ="+temp_name);
                        table_descriptor.onUpgrade(db, oldVersion, newVersion, temp_name);
                    } else {
                        table_descriptor.onCreate(db);
                    }
                }
                db.setTransactionSuccessful();
            } catch (Throwable e) {
                
                throw new RuntimeException("DB upgrade failed: " + e.getMessage());
            } finally {
                db.endTransaction();
            }
        }


    中心思想是:

    对照新旧的database结构,假设旧表中有table新的database里没有,则删除旧表里的

    假设新database中有一个table更新。则须要更新这个表的结构。然后把旧表中数据拷贝过来

    (把旧表rename一个名字。把命名后的表中的数据复制到新表中)

    代码能够在http://download.csdn.net/detail/baidu_nod/7684479下载

    版权声明:本文博客原创文章。博客,未经同意,不得转载。

  • 相关阅读:
    HDU 1010 Tempter of the Bone
    HDU 4421 Bit Magic(奇葩式解法)
    HDU 2614 Beat 深搜DFS
    HDU 1495 非常可乐 BFS 搜索
    Road to Cinema
    Sea Battle
    Interview with Oleg
    Spotlights
    Substring
    Dominating Patterns
  • 原文地址:https://www.cnblogs.com/mengfanrong/p/4643169.html
Copyright © 2011-2022 走看看