用过框架的人应该都知道,像mybatis这种将数据库查询出的结果自动封装成对象是如何实现的呢?这篇文章将会模仿此功能。
1、首先设计一个工具类,用来获取数据库连接,关闭资源
public class ConnUtil {
final static String URL = "jdbc:mysql://127.0.0.1:3306/zsdj?useSSL=false";
final static String USERNAME = "root";
final static String PASSWORD = "root";
private static Connection conn;
static{
try {
Class.forName("com.mysql.jdbc.Driver");
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
//获取数据库连接
public static Connection getConn(){
try {
if (conn==null||conn.isClosed()) {
conn=DriverManager.getConnection(URL, USERNAME, PASSWORD);
}
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return conn;
}
//关闭资源
public static void closeAll(ResultSet rs,PreparedStatement ps,Connection conn){
try {
if (rs!=null) {
rs.close();
}
if (ps!=null) {
ps.close();
}
if (conn!=null) {
conn.close();
}
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
2、sql预编译,动态化添加参数(参数的顺序要对应),返回PreparedStatement对象。
public static PreparedStatement getPS(PreparedStatement ps, Object... objects) {
for (int i = 0; i < objects.length; i++) {
try {
ps.setObject(i + 1, objects[i]);
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return ps;
}
3、将查询结果与对象属性绑定,返回一个HashMap对象
public static Map<String, Object> setMap(Object obj,ResultSet rs){
HashMap<String, Object> hm=new HashMap<>();
Field[] fields=obj.getClass().getDeclaredFields();
for(int i=0;i<fields.length;i++){
try {
hm.put(fields[i].getName(), rs.getObject(fields[i].getName()));
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return hm;
}
4、将查询出的结果set到对象里public static void setT(Object obj, Map<String, Object> map1) {
Class c = obj.getClass();
Method[] methods = c.getMethods();
for (Method m : methods) {
if (m.getName().startsWith("set")) {
String name = m.getName();
name = name.substring(3, 4).toLowerCase() + name.substring(4, name.length());
if (map1.containsKey(name)) {
try {
m.invoke(obj, map1.get(name));
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
}
基本利用的反射的原理以及字符串的操作,需要注意,数据库字段与实体类属性要对应,如数据库字段name,实体类是name,并且需要对应的set方法,setName。或者我们可以自定义注解,来对应实体类属性和数据库字段以及实体类和表名对应,参照Mybatis-plus的注解TableField来指定表明,TableName来指定字段。