当前位置: 首页 > news >正文

Hibernate(Spring Data)抓取策略

文章目录

  • 示例代码放到最后,使用的是Springboot 项目
  • 1. 简介
  • 2. Hibernate抓取策略分类
    • 2.1 即时加载(Eager Loading)
    • 2.2 延迟加载(Lazy Loading)
    • 2.3 子查询加载(Subselect Loading)
    • 2.4 基于批处理的加载(Batch Loading)
  • 3. 即时加载(Eager Loading)
    • 3.1 概述
    • 3.2 实体类映射配置
    • 3.3 使用场景和注意事项
  • 4. 延迟加载(Lazy Loading)
    • 4.1 概述
    • 4.2 实体类映射配置
    • 4.3 使用场景和注意事项
  • 5. 子查询加载(Subselect Loading)
    • 5.1 概述
    • 5.2 实体类映射配置
    • 5.3 使用场景和注意事项
  • 6. 基于批处理的加载(Batch Loading)
    • 6.1 概述
    • 6.2 实体类映射配置
    • 6.3 使用场景和注意事项
  • 7. 总结
  • Demo

示例代码放到最后,使用的是Springboot 项目

1. 简介

本文将深入讨论Hibernate中的抓取策略,介绍不同类型的抓取策略以及它们的使用场景和注意事项。

2. Hibernate抓取策略分类

2.1 即时加载(Eager Loading)

即时加载是指在查询主实体时立即加载相关联的实体对象。这种策略会在查询时一次性加载所有关联的实体对象,可以减少数据库查询次数。

2.2 延迟加载(Lazy Loading)

延迟加载是指在访问关联属性时才会真正加载相关的实体对象。这种策略在查询主实体时只会加载主实体对象,而关联的实体对象只有在被访问时才会被加载。

2.3 子查询加载(Subselect Loading)

子查询加载是指通过执行子查询来加载关联的实体集合对象,而不是通过单独的SQL语句执行关联查询。这种策略适用于一对多或多对多关系,并可以提高性能。

2.4 基于批处理的加载(Batch Loading)

基于批处理的加载是指通过执行批量SQL语句一次性加载多个实体对象。这种策略可以减少数据库交互次数,提高性能。

3. 即时加载(Eager Loading)

3.1 概述

即时加载策略可以通过设置@ManyToOne@OneToOne等注解来实现,默认情况下Hibernate会使用即时加载进行关联对象的加载。

3.2 实体类映射配置

在关联属性上使用fetch = FetchType.EAGER注解来指定即时加载策略。

@Entity
@Data
public class Classes {@Idprivate int id;private String name;@OneToMany(mappedBy = "classes", fetch = FetchType.EAGER)private List<Student> students;
}

这里可以看到查询的班级实体种student属性集合有二十个对象
在这里插入图片描述

3.3 使用场景和注意事项

  • 适用于关联实体对象数据量较小且经常被使用的情况。
  • 频繁加载大量关联对象可能导致性能问题,需要谨慎使用。

4. 延迟加载(Lazy Loading)

4.1 概述

延迟加载策略可以通过设置@ManyToOne@OneToOne等注解来实现,默认情况下Hibernate会使用延迟加载进行关联对象的加载。

4.2 实体类映射配置

在关联属性上使用fetch = FetchType.LAZY注解来指定延迟加载策略。

@Entity
public class Classes{// ...@OneToMany(mappedBy = "classes", fetch = FetchType.LAZY)private List<Student> students;// ...
}

这里开启懒加载后查询到的对象种数据是空的,只有当执行get方法时才会去获取数据
在这里插入图片描述

在这里插入图片描述

4.3 使用场景和注意事项

  • 适用于关联实体对象数据量较大或者不经常被使用的情况,可以减少不必要的数据库查询。
  • 注意检查在延迟加载策略下可能引发的懒加载异常,需要合理处理。

5. 子查询加载(Subselect Loading)

5.1 概述

子查询加载策略通过执行子查询来加载关联的实体集合对象,适用于一对多或多对多关系。

5.2 实体类映射配置

在关联集合属性上使用@Fetch注解,并指定@Fetch(FetchMode.SUBSELECT)来启用子查询加载策略。

@Entity
public class Order {// ...@OneToMany(mappedBy = "order")@Fetch(FetchMode.SUBSELECT)private List<OrderItem> orderItems;// ...
}

5.3 使用场景和注意事项

  • 适用于一对多或多对多的关联关系,减少关联集合对象的查询次数,提高性能。
  • 子查询加载策略会执行多条SQL语句,需要考虑数据库性能和查询效率的平衡。

6. 基于批处理的加载(Batch Loading)

6.1 概述

基于批处理的加载策略通过执行批量SQL语句一次性加载多个实体对象,减少数据库交互次数,提高性能。

6.2 实体类映射配置

在关联集合属性上使用@BatchSize注解,并指定要批量加载的大小。

@Entity
public class Order {// ...@OneToMany(mappedBy = "order")@BatchSize(size = 10)private List<OrderItem> orderItems;// ...
}

@BatchSize 注解的作用是为了优化 Hibernate 对关联集合属性的查询性能。它可以应用于实体类的集合属性上,告诉 Hibernate 在加载该集合属性时一次性加载指定个数的数据,从而减少数据库查询次数。

具体来说,@BatchSize 注解会影响到使用延迟加载(FetchType.LAZY)的关联集合属性的时候。当访问该集合属性时,如果该属性还没有被初始化,Hibernate 会触发查询加载数据。通过设置 @BatchSize 注解,可以控制同时加载的数据量,从而减少数据库查询的次数。

例如,假设我们有一个 EntityA 实体类,其中包含一个 List<EntityB> 类型的集合属性,我们可以在该属性上添加 @BatchSize 注解来优化查询性能:

@Entity
public class EntityA {// ...@OneToMany(mappedBy = "entityA", fetch = FetchType.LAZY)@BatchSize(size = 10) // 在这里添加注解private List<EntityB> entityBList;// getters and setters
}

在这个例子中,将 @BatchSize(size = 10) 注解应用于 entityBList 属性上。当访问 entityBList 属性时,Hibernate 会一次性加载 10 条 EntityB 数据,从而减少查询次数,提高性能。

需要注意的是,@BatchSize 注解只对延迟加载的集合属性有效,对于即时加载(FetchType.EAGER)的集合属性无效。此外,它只影响到关联集合属性本身的加载,不会影响到关联实体对象的加载。

总结来说,@BatchSize 注解可以优化延迟加载的关联集合属性的查询性能,通过一次加载多个数据项减少数据库查询次数。但需要根据具体情况选择合适的批处理大小,并综合考虑内存消耗和查询性能。

6.3 使用场景和注意事项

  • 适用于一对多或多对多的关联关系,减少数据库交互次数,提高性能。
  • 需要根据实际情况调整批量加载的大小,避免一次性加载过多数据导致内存占用过大。

7. 总结

Hibernate提供了多种抓取策略用于加载关联实体对象,包括即时加载、延迟加载、手动加载、子查询加载和基于批处理的加载。选择合适的抓取策略可以提高查询性能和减少数据库交互次数,但需要根据实际情况和性能要求进行综合考虑。

Demo

import lombok.Data;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import java.util.List;
@Entity
@Data
public class Classes {@Idprivate int id;private String name;
//	@OneToMany(mappedBy = "classes")
//	private List<Student> students;//子查询加载
//	@OneToMany(mappedBy = "classes")
//	@Fetch(FetchMode.SUBSELECT)
//	private List<Student> students;//基于批处理的加载@OneToMany(mappedBy = "classes")@BatchSize(size = 6)private List<Student> students;public void loadCustomer() {// 手动加载关联的Customer对象Hibernate.initialize(students);}}import lombok.Data;
import javax.persistence.*;@Entity
@Data
public class Student {@Id@GeneratedValue(strategy = GenerationType.IDENTITY)private int id;private String name;@ManyToOne(fetch = FetchType.EAGER)private Classes classes;}
public interface JPAClassesDao extends JpaRepository<Classes, Integer>, Serializable {
}
public interface JPAStudentDao extends JpaRepository<Student, Integer> , Serializable {
}
@AutowiredJPAStudentDao jpastudentDao;@AutowiredJPAClassesDao jpaclassesDao;
//    @Resource
//    private  SessionFactory factory;@RequestMapping("/Insert")public void InsertClassesTest(){List<Classes> a=new ArrayList<>();List<Student> s=new ArrayList<>();for (int i = 0; i < 10; i++) {Classes b=new Classes();b.setId(i);b.setName("班级"+i);a.add(b);for (int j = 0; j < 20; j++) {Student c=new Student();c.setClasses(b);c.setName("学生"+i+j);s.add(c);}}jpaclassesDao.saveAll(a);jpastudentDao.saveAll(s);}@RequestMapping("/QueryEAGER")public void queryEAGERTest(){Classes byId = jpaclassesDao.findById(0).get();for (Student student : byId.getStudents()) {System.out.println("班级"+byId.getName()+"的:"+student.getName());}}@RequestMapping("/QueryLAZY")public void queryLAZYTest(){Classes byId = jpaclassesDao.getOne(1);System.out.println("--------------------------------------");for (Student student : byId.getStudents()) {System.out.println("班级"+byId.getName()+"的:"+student.getName());}}@RequestMapping("/QueryTriggerLAZY")public void queryTriggerTest(){Classes byId = jpaclassesDao.getOne(1);// byId.loadCustomer();for (Student student : byId.getStudents()) {System.out.println("班级"+byId.getName()+"的:"+student.getName());}}@RequestMapping("/QuerySubselect")public void querySubselectTest(){Classes byId = jpaclassesDao.getOne(1);for (Student student : byId.getStudents()) {System.out.println("班级"+byId.getName()+"的:"+student.getName());}}
        <!-- hibernate依赖 --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-jpa</artifactId></dependency><dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</artifactId></dependency>

相关文章:

Hibernate(Spring Data)抓取策略

文章目录 示例代码放到最后&#xff0c;使用的是Springboot 项目1. 简介2. Hibernate抓取策略分类2.1 即时加载&#xff08;Eager Loading&#xff09;2.2 延迟加载&#xff08;Lazy Loading&#xff09;2.3 子查询加载&#xff08;Subselect Loading&#xff09;2.4 基于批处理…...

【高阶数据结构】map和set的介绍和使用 {关联式容器;键值对;map和set;multimap和multiset;OJ练习}

map和set的介绍和使用 一、关联式容器 关联式容器和序列式容器是C STL中的两种不同类型的容器。 关联式容器是基于键值对的容器&#xff0c;其中每个元素都有一个唯一的键值&#xff0c;可以通过键值来访问元素。关联式容器包括set、multiset、map和multimap。 序列式容器是…...

系统架构技能之设计模式-单件模式

一、开篇 其实我本来不是打算把系统架构中的一些设计模式单独抽出来讲解的&#xff0c;因为很多的好朋友也比较关注这方面的内容&#xff0c;所以我想通过我理解及平时项目中应用到的一 些常见的设计模式,拿出来给大家做个简单讲解&#xff0c;我这里只是抛砖引玉&#xff0c…...

Redis进阶 - JVM进程缓存

原文首更地址&#xff0c;阅读效果更佳&#xff01; Redis进阶 - JVM进程缓存 | CoderMast编程桅杆https://www.codermast.com/database/redis/redis-advance-jvm-process-cache.html 传统缓存的问题 传统的缓存策略一般是请求到达 Tomcat 后&#xff0c;先查询 Redis &…...

SD-WAN带您告别高成本、单一功能和安全性差

现今&#xff0c;随着企业规模不断扩大和分散办公越来越普遍&#xff0c;企业对于网络的需求也变得越来越高。然而&#xff0c;传统的组网方式面临着很多的问题&#xff0c;比如&#xff1a;成本高、功能单一、安全性差等问题。 传统组网方式有哪些&#xff1f; 传统的组网方式…...

面试必备:揭秘ArrayList和LinkedList,区别、优缺点与使用场景

大家好&#xff0c;我是你们的小米&#xff01;今天我要跟大家聊一个在面试中经常被问到的热门话题——ArrayList和LinkedList的区别、优缺点以及它们的使用场景。作为程序员&#xff0c;掌握这些知识点不仅可以在面试中脱颖而出&#xff0c;还能帮助我们更好地在项目中选择合适…...

【局部活动轮廓】使用水平集方法实现局部活动轮廓方法研究(Matlab代码实现)

&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜密&#xff0c;逻辑清晰&#xff0c;为了方便读者。 ⛳️座右铭&a…...

Git 同步远程新的同名分支

背景 因为远程分支的提交记录过多&#xff0c;导致本地的commit内容过大&#xff0c;会产生一些问题&#xff1a; 第一次拉取时间较长占用本地和远程的存储 原因 因为项目已有一些年头&#xff0c;若是每次文件提交比较大&#xff0c;那么占用空间就更大 解决方案 该方案…...

PingCode DevOps 团队:企业CICD流水线可能会遇到的问题及解法

CICD 流水线是指一系列自动化的构建、测试和部署步骤&#xff0c;用于将应用程序从开发到生产环境的过程。在 CICD 流水线中&#xff0c;每个步骤都是自动化的&#xff0c;并且在完成后会触发下一个步骤的执行。 CICD 的价值 CICD 流水线可以帮助团队更快地交付产品&#xff…...

【LeetCode题目详解】第九章 动态规划part01 509. 斐波那契数 70. 爬楼梯 746. 使用最小花费爬楼梯 (day38补)

本文章代码以c为例&#xff01; 一、力扣第509题&#xff1a;斐波那契数 题目&#xff1a; 斐波那契数 &#xff08;通常用 F(n) 表示&#xff09;形成的序列称为 斐波那契数列 。该数列由 0 和 1 开始&#xff0c;后面的每一项数字都是前面两项数字的和。也就是&#xff1a…...

图像处理 信号处理板 设计原理图:367-基于zynq XC7Z100 FMC接口通用计算平台

基于zynq XC7Z100 FMC接口通用计算平台 一、板卡概述 板卡由SoC XC7Z100-2FFG900I芯片来完成卡主控及数字信号处理&#xff0c;XC7Z100内部集成了两个ARM Cortex-A9核和一个kintex 7的FPGA&#xff0c;通过PL端FPGA扩展FMC、光纤、IO等接口&#xff0c;PS端ARM扩展网络、USB、R…...

PHP中header()的七种用法

我们在实际开发中经常使用header()实现一些功能&#xff0c;这篇文章介绍关于header()的7中用法&#xff0c;需要的伙伴的开参考一下。 PHP header()的7中用法&#xff1a; 1、跳转页面 可以使用header()实现跳转页面功能。 header(Location:.$url); // $url 跳转页面的地址…...

臻图信息以数字孪生技术推动智慧小区数字化建设

伴随着智慧城市建设进程的加速发展&#xff0c;加速传统小区的管理与服务向智能化升级转型。运用智慧化的管理和服务&#xff0c;利用信息技术和物联网等技术手段&#xff0c;将传统的居住区域与智能设备相结合&#xff0c;实现楼宇、社区设施、服务管理的数字化、网络化、智能…...

15.CSS发光按钮的悬停特效

效果 源码 <!DOCTYPE html> <html> <head><title>CSS Modern Button</title><link rel="stylesheet" type="text/css" href="style.css"> </head> <body><a href="#" style=&quo…...

MyBatis —— 动态SQL和缓存

前言 在上一篇文章中荔枝梳理了一些特殊的SQL查询和一对多、多对一的映射关系&#xff0c;而在这篇文章中荔枝将会梳理有关MyBatis动态SQL和MyBatis缓存的相关知识&#xff0c;同时也稍微了解了有关MyBatis中借助MAVEN中的插件管理来实现逆向工程。希望对需要的小伙伴有帮助哈哈…...

恒流电路的三种设计方案

作为硬件研发工程师相信对恒流电路不会陌生&#xff0c;本文介绍下三种恒流电路的原理图。 三极管恒流电路 三极管恒流电路 三极管的恒流电路&#xff0c;主要是利用Q2三极管的基级导通电压为0.6~0.7V这个特性&#xff1b;当Q2三极管导通&#xff0c;Q1三极管基级电压被拉低而…...

QT基础 关于QT延迟

目录 QT提供延时 1.自定义延时 2.使用QElapsedTimer 3.使用事件循环 4.跨平台延时 QT提供延时 这里提供四种方法&#xff1a; 1、多线程程序使用QThread::sleep()或者QThread::msleep()或QThread::usleep()或QThread::wait()进行延时处理。 Sleep不会释放对象锁&#x…...

LLM - LLaMA-2 获取文本向量并计算 Cos 相似度

目录 一.引言 二.获取文本向量 1.hidden_states 与 last_hidden_states ◆ hidden_states ◆ last_hidden_states 2.LLaMA-2 获取 hidden_states ◆ model config ◆ get Embedding 三.获取向量 Cos 相似度 1.向量选择 2.Cos 相似度 3.BERT-whitening 特征白化 …...

【创建型设计模式】C#设计模式之工厂模式,以及通过反射实现动态工厂。

题目如下&#xff1a; 假设你正在为一家汽车制造公司编写软件。公司生产多种类型的汽车&#xff0c;包括轿车、SUV和卡车。每种汽车都有不同的特点和功能。请设计一个工厂模式&#xff0c;用于创建不同类型的汽车对象。该工厂模式应具有以下要求&#xff1a;工厂类名为 CarFac…...

可拖拽编辑的流程图X6

先上图 //index.html&#xff0c;有时候可能加载失败&#xff0c;那就再找一个别的cdn 或者npm下载&#xff0c;如果npm下载&#xff0c; //那么需要全局引入或者局部引入&#xff0c;代码里面写法也会不同&#xff0c;详细的可以看示例<script src"https://cdn.jsdeli…...

利用最小二乘法找圆心和半径

#include <iostream> #include <vector> #include <cmath> #include <Eigen/Dense> // 需安装Eigen库用于矩阵运算 // 定义点结构 struct Point { double x, y; Point(double x_, double y_) : x(x_), y(y_) {} }; // 最小二乘法求圆心和半径 …...

idea大量爆红问题解决

问题描述 在学习和工作中&#xff0c;idea是程序员不可缺少的一个工具&#xff0c;但是突然在有些时候就会出现大量爆红的问题&#xff0c;发现无法跳转&#xff0c;无论是关机重启或者是替换root都无法解决 就是如上所展示的问题&#xff0c;但是程序依然可以启动。 问题解决…...

C++_核心编程_多态案例二-制作饮品

#include <iostream> #include <string> using namespace std;/*制作饮品的大致流程为&#xff1a;煮水 - 冲泡 - 倒入杯中 - 加入辅料 利用多态技术实现本案例&#xff0c;提供抽象制作饮品基类&#xff0c;提供子类制作咖啡和茶叶*//*基类*/ class AbstractDr…...

边缘计算医疗风险自查APP开发方案

核心目标:在便携设备(智能手表/家用检测仪)部署轻量化疾病预测模型,实现低延迟、隐私安全的实时健康风险评估。 一、技术架构设计 #mermaid-svg-iuNaeeLK2YoFKfao {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg…...

在rocky linux 9.5上在线安装 docker

前面是指南&#xff0c;后面是日志 sudo dnf config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo sudo dnf install docker-ce docker-ce-cli containerd.io -y docker version sudo systemctl start docker sudo systemctl status docker …...

基于Flask实现的医疗保险欺诈识别监测模型

基于Flask实现的医疗保险欺诈识别监测模型 项目截图 项目简介 社会医疗保险是国家通过立法形式强制实施&#xff0c;由雇主和个人按一定比例缴纳保险费&#xff0c;建立社会医疗保险基金&#xff0c;支付雇员医疗费用的一种医疗保险制度&#xff0c; 它是促进社会文明和进步的…...

【磁盘】每天掌握一个Linux命令 - iostat

目录 【磁盘】每天掌握一个Linux命令 - iostat工具概述安装方式核心功能基础用法进阶操作实战案例面试题场景生产场景 注意事项 【磁盘】每天掌握一个Linux命令 - iostat 工具概述 iostat&#xff08;I/O Statistics&#xff09;是Linux系统下用于监视系统输入输出设备和CPU使…...

大语言模型如何处理长文本?常用文本分割技术详解

为什么需要文本分割? 引言:为什么需要文本分割?一、基础文本分割方法1. 按段落分割(Paragraph Splitting)2. 按句子分割(Sentence Splitting)二、高级文本分割策略3. 重叠分割(Sliding Window)4. 递归分割(Recursive Splitting)三、生产级工具推荐5. 使用LangChain的…...

【AI学习】三、AI算法中的向量

在人工智能&#xff08;AI&#xff09;算法中&#xff0c;向量&#xff08;Vector&#xff09;是一种将现实世界中的数据&#xff08;如图像、文本、音频等&#xff09;转化为计算机可处理的数值型特征表示的工具。它是连接人类认知&#xff08;如语义、视觉特征&#xff09;与…...

现代密码学 | 椭圆曲线密码学—附py代码

Elliptic Curve Cryptography 椭圆曲线密码学&#xff08;ECC&#xff09;是一种基于有限域上椭圆曲线数学特性的公钥加密技术。其核心原理涉及椭圆曲线的代数性质、离散对数问题以及有限域上的运算。 椭圆曲线密码学是多种数字签名算法的基础&#xff0c;例如椭圆曲线数字签…...