Android Sqlite+反射 实现CRUD

反射类:获取bean的属性和属性的对应值

public class ReflectUtil {
	
	public static String[] getFields(Class clz) {
		Field[] fields = clz.getDeclaredFields();
		String[] names = new String[fields.length];
		for (int i = 0; i < fields.length; i++) {
			names[i] = fields[i].getName();
		}
		return names;
	}
	
	public static <T>  Map<String, String> getFieldsAndValue(Class<T> clz, T data) throws Exception {
		Map<String, String> map = new HashMap<String, String>();
		Field[] fields = clz.getDeclaredFields();
		for (int i = 0; i < fields.length; i++) {
			String name = fields[i].getName();
			fields[i].setAccessible(true);
			if (fields[i].get(data) == null) {
				map.put(name, null);
			} else {
				map.put(name, fields[i].get(data).toString());
			}
			
			fields[i].setAccessible(false);
		}
		return map;
	}
}


Sqlite工具类

public class SqliteUtil {
	
    public static final String DB_NAME="abc.db";
    public static final int DB_VERSION = 3;
    public static final String TABLE_AA = "aa";
    private static DatabaseHelper dbHelper;
    private static boolean isRun; //标识是否需要使用db
    
    public static void createDatabase(Context context) {
    	dbHelper = new DatabaseHelper(context);
    	useDB();
    }
    
    public static void useDB() {
    	isRun = true;
    }
    
    public static void releaseDB() {
    	isRun = false;
    }
    
    /**
     * insert 和 update
     * @param table
     * @param clz
     * @param data
     */
    public static synchronized <T> void update(String table, Class<T> clz, T data) {
    	if (!isRun) return;
    	dbHelper.getWritableDatabase().close();
    	SQLiteDatabase db = dbHelper.getWritableDatabase();
    	ContentValues values = new ContentValues();
    	try {
    		Map<String, String> map = ReflectUtil.getFieldsAndValue(clz, data);
        	for (String key : map.keySet()) {
        		values.put(key, map.get(key));
        	}
        	db.beginTransaction();
    		db.replace(table, null, values);//记录中有则update,无则insert
    		db.setTransactionSuccessful();
    		
    	} catch (Exception e) {
    		e.printStackTrace();
    	} finally {
    		db.endTransaction();
    		db.close();
    	}
    }
    
    public static synchronized void delete(String table, String whereClause, String[] whereArgs) {
    	dbHelper.getWritableDatabase().close();
    	SQLiteDatabase db = dbHelper.getWritableDatabase();
    	try {
    		db.beginTransaction();
    		db.delete(table, whereClause, whereArgs);
    		db.setTransactionSuccessful();
    	} catch (Exception e) {
    		e.printStackTrace();
    	} finally {
    		db.endTransaction();
    		db.close();
    	}
    }
    
    public static synchronized <T> List<T> query(String table, Class<T> clz, String selection, String[] selectionArgs) {
    	List<T> list = new ArrayList<T>();
    	if (!isRun) return list;
    	SQLiteDatabase db = dbHelper.getReadableDatabase();
    	T instance = null;
    	try {
    		Constructor<T> constructor = clz.getConstructor();
    		Cursor cursor =  db.query(table, null, selection, selectionArgs, null, null, null);
    		while (cursor.moveToNext()) {
    			instance = constructor.newInstance();
    			Field[] fields = clz.getDeclaredFields();
    			for (int i = 0; i < fields.length; i++) {
    				String value = cursor.getString(cursor.getColumnIndex(fields[i].getName()));
    				fields[i].setAccessible(true);
    				fields[i].set(instance, value);
    				fields[i].setAccessible(false);
    			}
    			list.add(instance);
    		}
    	} catch (Exception e) {
    		e.printStackTrace();
    	} finally {
    		db.close();
    	}
    	return list;
    }
        
    public static class DatabaseHelper extends SQLiteOpenHelper{

        public DatabaseHelper(Context context) {
            super(context, DB_NAME, null, DB_VERSION);
        }

        @Override
        public void onCreate(SQLiteDatabase db) {
	        
//        	db.execSQL("DROP TABLE IF EXISTS aa");  
            String execSql = "CREATE TABLE " + TABLE_AA + " (_id INTEGER PRIMARY KEY AUTOINCREMENT, ";
            String[] fields = ReflectUtil.getFields(DataAA.class);
            for (int i = 0; i <fields.length; i++) {
            	execSql += fields[i] + " VARCHAR,"; //默认可以为空
    		}
            execSql = execSql.substring(0, execSql.length() - 1) + ")"; //建表
            db.execSQL(execSql);
            execSql = "CREATE UNIQUE INDEX unique_index_aa ON "+TABLE_AA+" (url)";  //建唯一索引
            db.execSQL(execSql);
            
            
        }

        @Override
        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
        	  if (oldVersion < 3) {
        		  db.execSQL("alter table " + TABLE_AA + " add col1 VARCHAR null");
        		  db.execSQL("alter table " + TABLE_AA + " add col2 VARCHAR null");
        	  }
        }
        
    }
}

—————————————————————

自己手写了下,用在项目里了。在此备注下

关于isRun属性:可能退出程序后,db还在被循环执行时,或者说在一个线程中被不断执行时,需要停止db操作

可能db没有正确close,所以每次操作先close下

onUpdate中 执行更新版本的操作:添加列、移除表等等

每次传table名,是有点好麻烦的:可在javabean中加个注解表名,反射时传入class<T>,拿到表名

db的开关,耗资源的:所以对于CRUD操作应该都有 操作一条数据和多条数据的方法,这里缺失了一些...尴尬

大家好,个人觉得用Sqlite数据库时,经常需要进行机械性的CRUD操作,故对其进行了一下封装,希望能起到抛砖引玉的作用。 目的:封装共有的CRUD 下面简单的说一下使用步骤,如果觉得多余,可以无视。 1. 实现自己的DBHelper: /** * * @author Kee.Li * * 1. 继承了SmartDBHelper,不需要重写SQLiteOpenHelper的那两个方法 * 2. 父类构造方法参数modelClasses是实体类的数组,也就是需要生产的类的Class数组 * */ public class DBHelper extends SmartDBHelper { //数据库名称 private final static String DATABASE_NAME = "books.db"; //数据库版本 private final static int DATABASE_VERSION = 2; //需要生成数据库的类的数组 private final static Class<?>[] modelClasses = {Book.class,User.class}; public DBHelper(Context context) { super(context, DATABASE_NAME, null, DATABASE_VERSION,modelClasses); } } 2.创建app需要的实体,也就是对应的数据库(这的实体添加到DBHelper的modelClasses数组中) /** * 数据库的实体 * @author Kee.Li * 关于注解: * Table: 此类对应的数据库名 * Id:标识此属性为数据库自增长的id,应为int型 * Column:标识此属性对应的数据库字段名 */ @Table(name="t_books") public class Book{ @Id @Column(name="book_id") private int bookId; @Column(name="book_name") private String bookName; @Column(name="book_author") private String bookAuthor; //set get 方法省略.... } 3. 实现DAO,也就是对实体的CRUD类 /** * @author Kee.Li * * 此类只需要继承TemplateDAO,在构造方法面给父类的属性dbHelper赋值,即可实现CRUD操作 * 若有复杂的操作,可以自定义方法 */ public class BookDAO extends TemplateDAO { /** * 创建DAO时初始化连接数据库对象helper * @param context */ public BookDAO(Context context) { super(new DBHelper(context)); } } 4. activity的调用 bookDAO = new BookDAO(this); List books = bookDAO.find(); 好了,到此结束,如果有什么好的建议或者意见,希望可以共同学习!谢谢大家!
一个简单的基于AndroidSqlite数据库的操作封装,它有如下的好处:便捷地创建和增添字段灵活的数据类型处理通过操作对象来insert或者update记录支持多种查询方式,支持多自定义的复杂查询,支持分页查询支持事务快速开始:    1. 设计:@Table(name="t_user") public class UserModel {     @Table.Column(name="user_id",type=Column.TYPE_INTEGER,isPrimaryKey=true)     public Integer userId;     @Table.Column(name="user_name",type=Column.TYPE_STRING,isNull=false)     public String userName;     @Table.Column(name="born_date",type=Column.TYPE_TIMESTAMP)     public Date bornDate;     @Table.Column(name="pictrue",type=Column.TYPE_BLOB)     public byte[] pictrue;     @Table.Column(name="is_login",type=Column.TYPE_BOOLEAN)     public Boolean isLogin;     @Table.Column(name="weight",type=Column.TYPE_DOUBLE)     public Double weight; }2. 初始化对象:SQLiteDatabase db = context.openOrCreateDatabase("test.db", Context.MODE_PRIVATE, null); DbSqlite dbSqlite = new DbSqlite(db); IBaseDao userDAO = DaoFactory.createGenericDao(dbSqlite, UserModel.class);3. 创建:userDAO.createTable(); 4. Insert 记录:UserModel user = new UserModel(); user.userName = "darcy"; user.isLogin = true; user.weight = 60.5; user.bornDate = new Date(); byte[] picture = {0x1,0x2,0x3,0x4}; user.pictrue = picture; userDAO.insert(user);5. Update 记录:UserModel user = new UserModel(); user.weight = 88.0; userDAO.update(user, "user_name=?", "darcy");6. 查询://单条结果查询 UserModel user = userDAO.queryFirstRecord("user_name=?", "darcy"); //一般查询 List userList = userDAO.query("user_name=? and weight > ?", "darcy" , "60"); //分页查询 PagingList pagingList = userDAO.pagingQuery(null, null, 1, 3);7. 事务支持:DBTransaction.transact(mDb, new DBTransaction.DBTransactionInterface() {         @Override         public void onTransact() {             // to do                 } };8. 更新(目前只支持添加字段)@Table(name="t_user" , version=2) //修改版本 public class UserModel {     //members above...     //new columns     @Table.Column(name="new_column_1",type=Column.TYPE_INTEGER)     public Integer newColumn;     @Table.Column(name="new_column_2",type=Column.TYPE_INTEGER)     public Integer newColumn2; } userDAO.updateTable();缺点和不足:还没支持多对一或者一多的关系没支持联合主键没支持的外键设计其他...实例:SqliteLookup(Android内查看Sqlite数据库利器): https://github.com/YeDaxia/SqliteLookup 标签:SQLiteUtils
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值