Hibernate之集合映射的使用(Set集合映射,list集合映射,Map集合映射)
a:数据库的相关知识:
(1):一个表能否有多个主键:不能;
(2):为什么要设置主键:数据库存储的数据都是有效的,必须保持唯一性;
(3)为什么id作为主键:因为表中通常找不到合适的列作为唯一列,即主键,所有为了方便用id列,因为id是数据库系统维护可以保证唯一,所以就把这列作为主键,简单的说为了方便;如果找不到合适的列,除了使用id列以为作为主键,也可以使用联合主键,即多列的值作为一个主键,从而确保了记录的唯一性,即为联合主键;
Hibernate的映射很重要哦,如果是一般的映射,很容易掌握和使用,但是如果是集合映射呢,这里简单使用一下集合映射;
1:第一步,作为使用别人框架的中国人,我们只能先引入别人的包咯,千万别忘记了哦
2:第二步,就是配置hibernate.cfg.xml了,这里的配置之前已经说过了,分三大部分
第一部分,数据库连接配置。
第二部分,其他相关配置。
这里使用了自动创建数据表, <property name="hibernate.hbm2ddl.auto">update</property>
下面的源码详细介绍了几种方法的区别,如何找到hibernate.hbm2ddl.auto这句话呢,如下所示:
第三部分,加载映射文件。
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd"> <hibernate-configuration>
<!-- 一个session-factory节点代表一个数据库 -->
<session-factory>
<!-- 第一部分:数据库连接配置 -->
<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="hibernate.connection.url">jdbc:mysql:///test</property>
<property name="hibernate.connection.username">root</property>
<property name="hibernate.connection.password">123456</property> <!-- 第二部分:其他相关配置 -->
<property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
<property name="hibernate.show_sql">true</property>
<property name="hibernate.format_sql">true</property>
<property name="hibernate.hbm2ddl.auto">update</property>
<!--
1:每次在创建sessionFactory时执行创建表,当调用sessionFactory的close方法的时候,删除表
#hibernate.hbm2ddl.auto create-drop 2:每次都重新建表,如果已经存在就先删除再创建
#hibernate.hbm2ddl.auto create 3:如果表不存在就创建,表存在就不创建
#hibernate.hbm2ddl.auto update 4:生成环境时候执行验证,当映射文件的内容与数据库表结构不一样的时候就报错
#hibernate.hbm2ddl.auto validate
--> <!-- 第三部分,加载映射文件 -->
<mapping resource="com/bie/po/User.hbm.xml"/> </session-factory>
</hibernate-configuration>
3:第三步,创建实体类,我依次使用了set,list,map集合来完成映射,这里一下全都写到了实体类里面了!!!
package com.bie.po; import java.util.List;
import java.util.Map;
import java.util.Set; /**
* @author BieHongLi
* @version 创建时间:2017年3月15日 下午4:07:18
* 实体类
*/
public class User { private int id;
private String name;
//一个用户,对应多个地址
private Set<String> address; private List<String> addressList; private Map<String, String> addressMap; public Map<String, String> getAddressMap() {
return addressMap;
}
public void setAddressMap(Map<String, String> addressMap) {
this.addressMap = addressMap;
}
public List<String> getAddressList() {
return addressList;
}
public void setAddressList(List<String> addressList) {
this.addressList = addressList;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Set<String> getAddress() {
return address;
}
public void setAddress(Set<String> address) {
this.address = address;
} }
4:创建好实体类,就可以进行映射配置了,如实体类名.hbm.xml
(1)set集合属性的映射:重点消化
name指定要映射的set集合的属性
table集合属性要映射的表
key指定集合表(t_address)的外键字段
element指定集合表的其他字段
type元素类型,一定要指定
(2)List集合属性的映射
name指定要映射的list集合的属性
table集合属性要映射的表
key指定集合表(t_addressList)的外键字段
element指定集合表的其他字段
type元素类型,一定要指定
list-index是list集合一定要指定的,指定排序列的名称,因为list是有序的
(3) Map映射
name指定要映射的map集合的属性
table集合属性要映射的表
key指定集合表(t_addressMap)的外键字段
element指定集合map的其他字段value
type元素类型,一定要指定
map-key指定map的key
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> <hibernate-mapping>
<class name="com.bie.po.User" table="t_test">
<!-- 主键映射 -->
<id name="id" column="id">
<generator class="native"></generator>
</id>
<!-- 非主键映射 -->
<property name="name" column="name"></property> <!--
set集合属性的映射:重点消化
name指定要映射的set集合的属性
table集合属性要映射的表
key指定集合表(t_address)的外键字段
element指定集合表的其他字段
type元素类型,一定要指定
-->
<set name="address" table="t_address">
<key column="uid"></key>
<element column="address" type="string"></element>
</set> <!--
List集合属性的映射
name指定要映射的list集合的属性
table集合属性要映射的表
key指定集合表(t_addressList)的外键字段
element指定集合表的其他字段
type元素类型,一定要指定
list-index是list集合一定要指定的,指定排序列的名称,因为list是有序的
-->
<list name="addressList" table="t_addressList">
<key column="uid"></key>
<list-index column="idx"></list-index>
<element column="address" type="string"></element>
</list> <!--
Map映射
name指定要映射的map集合的属性
table集合属性要映射的表
key指定集合表(t_addressMap)的外键字段
element指定集合map的其他字段value
type元素类型,一定要指定
map-key指定map的key
-->
<map name="addressMap" table="t_addressMap">
<key column="uid"></key>
<map-key type="string" column="shortName"></map-key>
<element type="string" column="address"></element>
</map> </class>
</hibernate-mapping>
5:映射配置好之后呢,就可以开始进行测试了,这里使用junit进行测试哦~~~
这里需要注意的是最后一个测试获取数据的时候,
只有当使用集合数据的时候,才向数据库发送执行sql的语句(又叫做懒加载)
当查询用户,同时可以获取用户关联的list集合的数据,(因为存在正确映射)
package com.bie.test; import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set; import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.junit.Test; import com.bie.po.User; /**
* @author BieHongLi
* @version 创建时间:2017年3月15日 下午4:31:23
*
*/
public class SetTest { //私有化session工厂
private static SessionFactory sf;
static{
//首先默认加载src/hibernate.cfg.xml文件
//其次创建session工厂文件
sf = new Configuration()
.configure()
//.addClass(User.class),测试的时候可以使用这个代替加载映射文件<mapping resource="com/bie/po/User.hbm.xml"/>
.buildSessionFactory();
} @Test
public void test(){
//创建session
Session session = sf.openSession();
//创建session开启事务
Transaction tx = session.beginTransaction(); //保存
Set<String> addressSet = new HashSet<>();
addressSet.add("北京");
addressSet.add("上海"); //用户对象
User user = new User();
user.setName("tom");
user.setAddress(addressSet); //保存到session中
session.save(user); tx.commit();
//session.getTransaction().commit();这样写就不用使用事务tx接受了,更加方便快捷
session.close();
} @Test
public void test2(){
//创建session
Session session = sf.openSession();
//开启事务
session.beginTransaction(); //List集合保存
List<String> list = new ArrayList<>();
list.add("深圳");
list.add("广州"); //User用户
User user = new User();
user.setName("张三");
user.setAddressList(list); //保存实体类
session.save(user); //提交事务
session.getTransaction().commit();
//关闭session
session.close();
} @Test
public void test3(){
Session session = sf.openSession();
session.beginTransaction(); Map<String, String> map = new HashMap<String,String>();
map.put("1001", "新乡");
map.put("1002", "郑州"); User user = new User();
user.setName("李四");
user.setAddressMap(map); session.save(user); session.getTransaction().commit();
session.close();
} @Test
public void getList(){
Session session = sf.openSession();
session.beginTransaction(); User user = (User)session.get(User.class, 2);
System.out.println(user.getId());
System.out.println(user.getName()); //当查询用户,同时可以获取用户关联的list集合的数据,(因为存在正确映射)
//当使用集合数据的时候,才向数据库发送执行sql的语句(又叫做懒加载)
System.out.println(user.getAddressList()); session.getTransaction().commit();
session.close();
} }
演示效果如下所示,需要注意的是,这里使用自动创建表的:
如果生活也是这般,有简到难,该多好~~~
Hibernate之集合映射的使用(Set集合映射,list集合映射,Map集合映射)的更多相关文章
- java集合 之 Map集合
Map用于保存具有映射关系的数据,具有两组值:一组用于保存Map中的key:另一组用于保存Map中的value,形成key-value的存储形式. Map集合中包含的一些方法: void clear( ...
- Map集合重要练习
重要练习:将字符串中的字母按如下格式显示: a(1)b(2)...... 代码及思路如下: /* 获取字符串中字母的次数,并打印出如下格式a(1)b(2)c(3)...... 思路: 先定义一个方法, ...
- list和map集合
List特点:元素有放入顺序,元素可重复Set特点:元素无放入顺序,元素不可重复(注意:元素虽然无放入顺序,但是元素在set中的位置是有该元素的HashCode决定的,其位置其实是固定的)Map特点: ...
- Map集合。
Map集合: java.util,Map<k,v> 特点:1.键值对 2.key-value一一对应 3.key不允许重复. Map常用实现类: java.util.HashMap< ...
- Map集合架构总结
说明;这里先学习Map集合,然后再学习Set集合,是因为Set集合中的HashSet依赖于hashMap,就是通过hashMap集合来实现的,TreeSet集合依赖于TreeMap集合,TreeSet ...
- Map集合、HashMap集合、LinkedHashMap集合、Hashtable集合、Collections工具类和模拟斗地主洗牌和发牌
1.Map集合概述和特点 * A:Map接口概述 * 查看API可以知道: * 将键映射到值的对象 * 一个映射不能包含重复的键 * 每个键最多 ...
- Map集合与转化
|--Hashtable:底层是哈希表数据结构,是线程同步的.不可以存储null键,null值. |--HashMap:底层是哈希表数据结构,是线程不同步的.可以存储null键,null值.替代了Ha ...
- java集合(List集合与Map集合的数据转换)
List集合与Map集合的数据转换 实现List和Map数据的转换. 具体要求如下: 功能1:定义方法public void listToMap( ){ }将List中Student元素封装到Map中 ...
- 牛客网Java刷题知识点之Java 集合框架的构成、集合框架中的迭代器Iterator、集合框架中的集合接口Collection(List和Set)、集合框架中的Map集合
不多说,直接上干货! 集合框架中包含了大量集合接口.这些接口的实现类和操作它们的算法. 集合容器因为内部的数据结构不同,有多种具体容器. 不断的向上抽取,就形成了集合框架. Map是一次添加一对元素. ...
- Collections工具类、Map集合、HashMap、Hashtable(十八)
1.Map集合概述和特点 * A:Map接口概述 * 去重复, * 查看API可以知道, * 将键映射到值的对象, * 一个映射不能包含重复的键, * 每个键最多只能映射到一个值.* B:Map接口和 ...
随机推荐
- oracle解除锁表【原】
在日常操作中,经常会有不小心被锁表的情况发生 一般造成原因有: 开发人员不小心执行了 for update 查询语句后,没有解锁 不合理代码中开启事务(begin transaction)后,没有关闭 ...
- C#窗口防止闪烁两种方法
public class PaintIncrease { public static void SetDoubleBuffered(object obj) { Type type = obj.GetT ...
- 跨越VLAN
跨越VLAN VLAN(Virtual Local Area Network),是基于以太网交互技术构建的虚拟网络,既可以将同一物理网络划分为多个VLAN,也可以跨越物理网络障碍,将不同于子网中的用户 ...
- android 加载图片
package mydemo.mycom.demo2; import android.graphics.Bitmap; import android.graphics.BitmapFactory; i ...
- Elaticsearch 集群
elasticsearch开源的搜索引擎: ElasticSearch 个基于Lucene的搜索服务器:可以使用多节点的备份:集群设置: (类似是个数据库型.有索引有什么的).(lucene apa ...
- C - 数字配对 (网络流 最大费用最大流)
题目链接:https://cn.vjudge.net/contest/281959#problem/C 题目大意:中文题目 具体思路:用网络流的思想,我们求得是最大的匹配数,那么我们按照二分图的形式去 ...
- java 多线程面试
一.多线程的创建 1.多线程的创建 (1).继承Thread类 (2).实现Runnable接口 2.两种启动线程方法的区别 1.共同点 必须调用Thread 产生线程,然后调用start()方法 开 ...
- Android:(本地、可通信的、前台、远程)Service使用全面介绍
2.具体使用解析 2.1 本地Service 这是最普通.最常用的后台服务Service. 2.1.1 使用步骤 步骤1:新建子类继承Service类 需重写父类的onCreate().onStart ...
- .Net Core中使用RabbitMQ
(1).引入依赖 RabbitMQ.Client (2).编写发布者代码 var connectionFactory = new ConnectionFactory() { HostName=&quo ...
- Pytorch入门之VAE
关于自编码器的原理见另一篇博客 : 编码器AE & VAE 这里谈谈对于变分自编码器(Variational auto-encoder)即VAE的实现. 1. 稀疏编码 首先介绍一下“稀疏编码 ...