技术标签: spring ExampleMatcher jpa SSM 分页查询
之前写过一篇博客
Spring Data JPA 使用JpaSpecificationExecutor实现多条件查询(分页查询和非分页查询)
然后发现还有其他两种写法,会更简便一些。
1、使用JPA自带的findByXxx接口
这种方法其实还比较方便,除了如果字段多的话findByXxx这个方法的名字会很长很长很长…
Containing的用法与like一致.
示例:
顺便说明一下default方法:
在java8以后,接口中可以添加使用default或者static修饰的方法,在这里我们只讨论default方法,default修饰方法只能在接口中使用,在接口中被default标记的方法为普通方法,可以直接写方法体。
实现类会继承接口中的default方法。
@Repository
public interface UserRepository extends JpaRepository<UserDO,Long> {
Page<UserDO> findByUsernameContainingAndUserPasswordContaining(String username, String password, Pageable pageable);
default Page<UserDO> searchUserByCondition(String username, String password, Pageable pageable){
if(username == null){
username = "";
}
if(password == null){
password = "";
}
return findByUsernameContainingAndUserPasswordContaining(username, password, pageable);
}
}
写个类测试一下:
注意要加上注解@RunWith(SpringRunner.class),有了这个注解@Autowired注入的类才能实例化到spring容器中,自动注入才能生效,如果不加这一行会报错NullPointerExecption.
@RunWith(SpringRunner.class)
@SpringBootTest
public class UserTest {
@Autowired
private UserRepository userRepository;
@Test
public void Test1(){
UserDO userDO = new UserDO();
userDO.setUsername("yogi");
userDO.setUserPassword("123456");
userRepository.saveAndFlush(userDO);
List<UserDO> userDOList = userRepository.searchUserByCondition("yog",null, PageRequest.of(0,10)).getContent();
System.out.println(userDOList.size());
}
}
2、使用ExampleMatcher
@Repository
public interface UserRepository extends JpaRepository<UserDO,Long> {
default Page<UserDO> searchUserByCondition2(UserDO userDO, Pageable pageable){
if (StringUtils.isEmpty(userDO.getUserPassword())) {
// 对于数据库中允许为空的字段,需要设置null值,否则传入双引号会被判断成有值
userDO.setUserPassword(null);
}
ExampleMatcher matcher = ExampleMatcher.matching()
.withIgnoreNullValues()
.withIgnoreCase(false)
.withMatcher("username", ExampleMatcher.GenericPropertyMatchers.contains())
.withMatcher("userPassword", ExampleMatcher.GenericPropertyMatchers.contains())
.withIgnorePaths("userId", "userPhone");//忽略属性
Example<UserDO> userDOExample = Example.of(userDO, matcher);
return this.findAll(userDOExample,pageable);
}
}
方法如下:
方法 | 含义 |
---|---|
caseSensitive() | 大小写敏感 |
ignoreCase() | 忽略大小写 |
contains() | 模糊匹配,%{str}% |
startsWith() | 匹配起始字符串,{str}% |
endsWith() | 匹配结尾字符串,%{str} |
exact() | 精确匹配字符串 |
reges() | 将字符串作为正则表达式进行匹配 |
注意一下当使用完全匹配.exact()时,参数为String类型时,传参时如果传""
(空字符串),并不是不进行筛选,而是会筛选""
,结果极有可能查询结果为空。
要解决这个问题,也可以在之前对需要完全匹配的属性做出如下设置:
if (StringUtils.isEmpty(userDO.getXxx())) {
userDO.setXxx(null);
}
此时该属性需要完全匹配,并当传入""时会不进行筛选,而是查出全部。
在数据库中你定义了一个时间,但是这个时间字段是字符串类型的查看数据库,原来是start_time有误, (start_time为0000-00-00 00:00:00)修改后在次访问即可以成功..._int' object has no attribute 'tzinfo
汇编伪指令db,dw,dd。位、字节、字_汇编中位等于字还是字节
C语言执行时报错“表达式必须是可修改的左值,无法从“const char [3]”转换为“char [120]” ”,原因:字符串不能直接赋值解决该问题的方法:使用strcpy函数进行字符串拷贝原型声明:char *strcpy(char* dest, const char *src);头文件:#include <string.h> 和 #include <stdio.h>功能:把从src地址开始且含有NULL结束符的字符串复制到以dest开始的地址空_表达式必须是可修改的左值
进程基本概念一、进程是什么?两个角度来理解:对于用户来说: 进程就是一个正在运行的程序对操作系统来说: 进程就是一个正在运行的程序的信息的描述集合,我们一般称它为 pcb,这个pcb实际上是一个名为:task_struct的结构体。所以对于操作系统来说,一个个进程就是一个个pcb。用户在点击程序或文件后,程序或者文件就会运行,首先文件中的数据就会拷贝一份放入内存中,同时操作系统会创建一个PCB(创建pcb就是创建进程),PCB中会有一个内存指针指向该内存,CPU通过PCB就能对进程控制和管理_进程和详细信息有什么区别
写在前边:今天袋鼠云更新了FlinkX1.12,从之前的1.10版本迭代到现在的1.12。现在要重新编译部署一下。这里记录一下操作流程,同时记录下常见的错误,便于以后查阅使用一、软件版本FlinkX 1.12Flink 1.12.4二、前期准备下载FlinkXgit clone https://github.com/DTStack/flinkx.git增加flinkx/pom.xml中的下载源,不然会非常慢 <repository> <id&g_flinkx部署
共轭梯度法(以希尔伯特矩阵为例)实现共轭梯度算法并且使用它解决对称矩阵——希尔伯特矩阵为系数矩阵A时,右边常数项列向量为单位列向量,初始点为零向量。展示维度分别为5,8,12,20时的迭代次数与结果。迭代终止条件为残差的二范数小于1e-6import numpy as npdef cg(x0, A, b): r0 = np.dot(A, x0) - b p0 = -r0 rk = r0 pk = p0 xk = x0 t = 0 #记录迭代次数 _录残量2范数达到1e-6时的迭代步数
1. 先到先服务FCFS和去银行办业务一样,大家站队或者取号,先来的先办业务。这是我们能够理解的很朴素的公平主义。对应到代码实现,可以使用有先进先出特性的队列来实现。但对于操作系统而言,有一种情况下这种实现就很差劲。比如,有一个任务A需要执行一个小时,另外N个任务B执行几十秒就能完成。如果任务A先执行,那么N个任务B必须等到A执行完毕之后,才能依次执行。这对于用户来讲,体验显然是非常差的。于是就有了下面的方案。2. 短作业优先SJF短作业优先,可以是平均等待时间最短。用户体验一般和等待时间成正比,越久_操作系统 线程调度
蓝桥杯刷题——C/C++第十届蓝桥杯大赛软件类省赛C/C++ 大学C组试题A:求和题目:示例:代码:结果:试题B: 矩形切割题目:小明有一块n*m的矩形白纸,每次他都会从中间切一刀切出一个最大的正方形,随后从剩余矩形再切出最大正方形,直到剩下的都是正方形为止。示例:一个5*3的矩形可以切出 3*3 2*2 1*1 1*1 四个正方形 那么2019*324 可以切出多少个正方形共能切出的正方形的个数?代码:#include <iostream>using nam_蓝桥杯:计划周一至周五每天
1.java平台体系的划分? 答:标准版(JAVASE,stantard edition)主要应用场景:主要用于桌面应用软件的编程。 企业版(JAVAEE,enterprise edition)主要应用场景:主要用于分布式的网络程序开发,比如电子商务网站和ERP系统,简化企业解决方案的开发。 Micro版(JAVA ME,micro edition)主要应用场景:主要用于
研究生朋友写小论文经常会用到matlab,小论文中对图片的处理要求往往很高,怎么把matlab中示波器波形图导出,变成矢量图后,波形图再怎么放大也不会失真。1、仿真完毕打开示波器,示波器背景是黑的,肯定不能直接导入word2、示波器界面中没有对波形图处理的选项,因为示波器的有些功能是隐藏的,在commond window输入下面的指令set(0,'ShowHiddenHandles','On')s..._matlab2013示波器导出矢量图
购物车模块购物车存储方式: 1)保存在session中;此次项目保存在session中 2)保存在cookie中; 3)保存在数据库中: 不同方式的优缺点: 1.Session(Memcached)方式 优点:购物车信息保存在服务端,可以保存1M 信息。 缺点:1)对于大型网站会占有过多的服务器内存资源,造成服务器压力过大。 2)Session保存的信息会在用户退...
arguments是JavaScript里的一个内置对象,是指向实参对象的引用,它很古怪,也经常被人所忽视,但实际上是很重要的。所有主要的js函数库都利用了arguments对象,所以agruments对象对于javascript程序员来说是必需熟悉的。JS本身并没有重载函数的功能,但Arguments对象能够模拟重载,JS中每个函数都会有一个Argu..._javascriptagrument