1 实体类编写规则
2 hibernate主键生成策略
3实体类操作
(1)crud操作
(2)实体对象状态
4 hibernate的一级缓存
5 hibernate事务操作
(1)事务代码规则写法
6 hibernate其他的api(查询)
实体类编写规则
1 实体类里面属性私有的
2 私有属性使用公开的set方法和get方法操作
3 要求实体类有属性作为唯一值(一般都使用id值)
4 实体类属性建议不使用基本数据类型,使用基本数据类型对应的包装类。
(1)八个基本数据类型对应的包装类
-int - Integer
-char--Character
-其他的都是首字母大写 比如double-Double
(2)比如表示学生的分数,假如 int score;
-比如学生得了0分,int score-0;
-如果表示学生没有参加考试,int scrore无法为null,int score不能准确表示学生是否参加考试
解决:使用包装类可以了,Integer score=0,学生得了0分
表示学生没有参加考试,Integer score=null;
Hibernate主键生成策略
1 hibernate要求实体类里面有一个属性作为唯一值,对应主键,主键可以不同生成策略
2 hibernate主键生成策略有很多的值
<!-- 设置数据库id增长策略 native:生成表id值就是主键自动增长 --> <generator class="native"></generator>
主要记住native和uuid。
identity只能用在mysql中,sequence只能用在oracle中。
因为不知道用什么数据库,所以用native,它会帮我们根据不同的数据库选择不一样的值。
(1)native:根据使用的数据库帮我们选择哪个值
CREATE TABLE `t_user` ( `uid` int(11) NOT NULL AUTO_INCREMENT, `username` varchar(255) DEFAULT NULL, `password` varchar(255) DEFAULT NULL, `address` varchar(255) DEFAULT NULL, PRIMARY KEY (`uid`) ) ENGINE=InnoDB AUTO_INCREMENT=8 DEFAULT CHARSET=utf8 |
(2)uuid:hibernate帮我们生成uuid值。
(1)使用uuid生成策略,实体类id属性类型必须是字符串类型。
在User.java中
private String uid; //如果有哪个属性值没有生成get和set方法,那么程序会出现异常
在User.hbm.xml中
<generator class="uuid"> </generator>
show create table t_user;展示如下所示:
CREATE TABLE `t_user` ( `uid` varchar(255) NOT NULL, `username` varchar(255) DEFAULT NULL, `password` varchar(255) DEFAULT NULL, `address` varchar(255) DEFAULT NULL, PRIMARY KEY (`uid`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 |
实体类操作
对实体类crud操作
添加操作
1 调用session里面的save方法实现
//添加功能 User user = new User(); user.setUsername("xiaoMA"); user.setPassword("250"); user.setAddress("China"); session.save(user);
根据id查询
hibernate可以帮我们创建表,但无法创建数据库。
1 调用session里面的get方法实现
//4 根据id查询 //调用session里面的get方法 //第一个参数:实体类的class //第二个参数:id值 User user = session.get(User.class, 1);
底层输出语句
<!-- 输出底层sql语句 --> <property name="hibernate.show_sql">true</property>
的输出结果是:
Hibernate: select user0_.uid as uid1_0_0_, user0_.username as username2_0_0_, user0_.password as password3_0_0_, user0_.address as address4_0_0_ from t_user user0_ where user0_.uid=? User [uid=1, username=lucy, password=123, address=china]
修改操作
(1)根据id查询,返回对象
// 4 修改操作 // 修改uid=2记录username值 User user = session.get(User.class, 2); //4.2向返回的user对象里面设置修改之后的值 user.setUsername("dongfangbubai"); //4.3 调用session方法update修改 //执行过程:到user对象里面找到uid值,根据uid进行修改 session.update(user);
底层代码
Hibernate: select user0_.uid as uid1_0_0_, user0_.username as username2_0_0_, user0_.password as password3_0_0_, user0_.address as address4_0_0_ from t_user user0_ where user0_.uid=? Hibernate: update t_user set username=?, password=?, address=? where uid=?
删除操作
// 4 删除操作 // 第一种 根据id查询对象 User user = session.get(User.class, 2); session.delete(user);
第二种删除方式
//第二种 User user = new User(); user.setUid(3); session.delete(user);
save和update
在表中已经有了uid值为1的数据,再执行下面语句,有的(主键不是自动增长的)运行会报错,有的会另外增加一条数据(uid值不一样)。
User user = new User(); user.setUid(1); user.setUsername("mary"); user.setPassword("250"); user.setAddress("yuenan"); session.save(user);
同样下面代码,运行不会报错,
User user = new User(); user.setUid(1); user.setUsername("tom"); session.update(user);
但是导致剩余没有赋值的字段为空
所以一般都不建议这样做。
实体类对象状态(概念)
1 实体类状态有三种
(1)瞬时态:对象里面没有id值,对象与session没有关联
User u = new User(); u.setUsername("jack"); u.setPassword("124"); u.setAddress("China"); session.save(u);
(2)持久态:对象有id值,对象与session有关联
User user = session.get(User.class, 1);
(3)托管态:对象有id值,对象与session没有关联
User user = new User(); user.setUid(3);
2 演示操作实体类对象的方法
(1)saveOrUpdate方法:实现添加、实现修改
瞬时态对象
//1 添加操作 User user = new User(); user.setUsername("jack"); user.setPassword("520"); user.setAddress("north korean"); //实体类对象状态是瞬时态,做添加操作 session.saveOrUpdate(user);
托管态对象
User user = new User(); user.setUid(2);//表中有uid为2的数据 user.setUsername("rose"); user.setPassword("1234"); user.setAddress("aerbaliya"); //实体类对象状态是托管态,做修改操作 session.saveOrUpdate(user);
查询先后结果如下所示:
持久态对象
//持久态 User user = session.get(User.class,7); user.setUsername("rose"); //实体类对象状态是持久态,做修改操作 session.saveOrUpdate(user);
运行报错,不知是不是主键没有设置动态增长的原因。
Hibernate的一级缓存
什么是缓存
1 数据存到数据库里面,数据库本身是文件系统,使用流方式操作文件,效率并不是很高。
(1)把数据存到内存中,不需要使用流的方式,可以直接读取内存中数据
(2)把数据放到内存中,提供读取效率
Hibernate缓存
1 hibernate框架中提供了很多优化方式,hibernate的缓存就是一种优化方式
2 hibernate缓存特点:
第一类 hiberante的一级缓存
(1)hibernate的一级缓存默认打开的
(2)hibernate的一级缓存使用范围,是session的范围,从session创建到session关闭范围
(3)hibernate的一级缓存中,存储数据必须是持久态数据
第二类 hibernate的二级缓存
(1)目前已经不使用了,替代技术redis
(2)二级缓存默认不是打开的,需要配置
(3)二级缓存使用范围,是sessionFactory范围
验证一级缓存存在
1 验证方式
(1)首先根据uid=1查询,返回对象
(2)其次再根据uid=1查询,返回对象
//1 根据uid=2查询 // 执行第一个get方法是否查询数据库,是否发送sql语句 User user1 = session.get(User.class, 2); System.out.println(user1); //2 再根据uid=6查询 //执行第二个get方法是否查询数据库,是否发送sql语句 User user2 = session.get(User.class, 2); System.out.println(user2);
Hibernate: select user0_.uid as uid1_0_0_, user0_.username as username2_0_0_, user0_.password as password3_0_0_, user0_.address as address4_0_0_ from t_user user0_ where user0_.uid=? User [uid=2, username=rose, password=5678, address=aerbaliya] User [uid=2, username=rose, password=5678, address=aerbaliya]
第一步执行get方法之后,发送sql语句查询数据库
第二个执行get方法之后,没有发送sql语句,查询一级缓存内容。
一级缓存的执行过程