深入理解 QueryDSL 的 BooleanBuilder:构建复杂逻辑表达式
文章目录
在 Java 的查询构建库 QueryDSL 中,
BooleanBuilder
是一个非常有用的工具类。它允许开发者通过链式调用轻松地构建复杂的布尔逻辑表达式。本文将详细介绍
BooleanBuilder
的各种方法,并通过代码示例展示如何使用这些方法。
一、方法介绍
1. 构造方法
默认构造方法
BooleanBuilder()
是一个无参构造方法,用于初始化一个空的 BooleanBuilder
实例。
BooleanBuilder builder = new BooleanBuilder();
带初始值的构造方法
BooleanBuilder(Predicate initial)
使用一个初始的 Predicate
对象来构造 BooleanBuilder
实例。
Predicate initialPredicate = QEntity.entity.field.eq("value");
BooleanBuilder builder = new BooleanBuilder(initialPredicate);
2. 逻辑运算方法
and 方法
BooleanBuilder and(@Nullable Predicate right)
用于将当前谓词与 right
谓词进行逻辑“与”操作。
Predicate predicate1 = QEntity.entity.field1.eq("value1");
Predicate predicate2 = QEntity.entity.field2.eq("value2");
BooleanBuilder builder = new BooleanBuilder(predicate1);
builder.and(predicate2);
// 结果为:field1 = "value1" AND field2 = "value2"
andAnyOf 方法
BooleanBuilder andAnyOf(Predicate... args)
将当前谓词与多个谓词中的任意一个进行逻辑“与”操作。
Predicate predicate3 = QEntity.entity.field3.eq("value3");
Predicate predicate4 = QEntity.entity.field4.eq("value4");
builder.andAnyOf(predicate3, predicate4);
// 结果为:field1 = "value1" AND field2 = "value2" AND (field3 = "value3" OR field4 = "value4")
andNot 方法
BooleanBuilder andNot(Predicate right)
将当前谓词与 right
谓词的“非”进行逻辑“与”操作。
Predicate predicate5 = QEntity.entity.field5.eq("value5");
builder.andNot(predicate5);
// 结果为:field1 = "value1" AND field2 = "value2" AND NOT field5 = "value5"
or 方法
BooleanBuilder or(@Nullable Predicate right)
将当前谓词与 right
谓词进行逻辑“或”操作。
Predicate predicate6 = QEntity.entity.field6.eq("value6");
builder.or(predicate6);
// 结果为:(field1 = "value1" AND field2 = "value2") OR field6 = "value6"
orAllOf 方法
BooleanBuilder orAllOf(Predicate... args)
将当前谓词与多个谓词中的所有进行逻辑“或”操作。
Predicate predicate7 = QEntity.entity.field7.eq("value7");
Predicate predicate8 = QEntity.entity.field8.eq("value8");
builder.orAllOf(predicate7, predicate8);
// 结果为:(field1 = "value1" AND field2 = "value2") OR (field7 = "value7" AND field8 = "value8")
orNot 方法
BooleanBuilder orNot(Predicate right)
将当前谓词与 right
谓词的“非”进行逻辑“或”操作。
Predicate predicate9 = QEntity.entity.field9.eq("value9");
builder.orNot(predicate9);
// 结果为:(field1 = "value1" AND field2 = "value2") OR NOT field9 = "value9"
not 方法
BooleanBuilder not()
对当前谓词进行逻辑“非”操作。
builder.not();
// 结果为:NOT (field1 = "value1" AND field2 = "value2")
3. 其他方法
accept 方法
<R, C> R accept(Visitor<R, C> v, C context)
接受一个访问者对象,用于处理当前谓词。
Visitor<String, Void> visitor = new MyVisitor();
String result = builder.accept(visitor, null);
clone 方法
BooleanBuilder clone() throws CloneNotSupportedException
克隆当前 BooleanBuilder
实例。
BooleanBuilder clonedBuilder = builder.clone();
equals 和 hashCode 方法
boolean equals(Object o)
和 int hashCode()
用于判断当前对象与另一个对象是否相等,并返回当前谓词的哈希码。
getValue 方法
@Nullable Predicate getValue()
获取当前的谓词值。
Predicate currentPredicate = builder.getValue();
hasValue 方法
boolean hasValue()
判断当前谓词是否有值。
boolean hasValue = builder.hasValue();
getType 方法
Class<? extends Boolean> getType()
返回布尔类型的类对象。
Class<? extends Boolean> type = builder.getType();
toString 方法
String toString()
返回当前谓词的字符串表示形式。
String predicateString = builder.toString();
二、案例
为了更好地理解 BooleanBuilder
的使用,我们将通过几个完整的案例来展示如何在实际应用中利用这个类构建复杂的查询条件。
案例 1:用户筛选
假设我们有一个用户表 User
,我们希望根据多个可选条件来筛选用户,例如用户名、年龄范围和是否激活。
import com.querydsl.core.BooleanBuilder;
import com.querydsl.sql.SQLQueryFactory;
import java.util.List;
public class UserFilter {
private final SQLQueryFactory queryFactory;
public UserFilter(SQLQueryFactory queryFactory) {
this.queryFactory = queryFactory;
}
/** * 根据用户名、年龄范围和激活状态筛选用户 * * @param username 用户名 * @param minAge 最小年龄 * @param maxAge 最大年龄 * @param isActive 是否激活 * @return 满足条件的用户列表 */
public List<User> filterUsers(String username, Integer minAge, Integer maxAge, Boolean isActive) {
QUser qUser = QUser.user;
// 初始化 BooleanBuilder
BooleanBuilder builder = new BooleanBuilder();
// 根据用户名构建条件
if (username != null) {
builder.and(qUser.username.eq(username));
}
// 根据最小年龄构建条件
if (minAge != null) {
builder.and(qUser.age.goe(minAge));
}
// 根据最大年龄构建条件
if (maxAge != null) {
builder.and(qUser.age.loe(maxAge));
}
// 根据激活状态构建条件
if (isActive != null) {
builder.and(qUser.isActive.eq(isActive));
}
// 执行查询并返回结果
return queryFactory.selectFrom(qUser)
.where(builder)
.fetch();
}
}
案例 2:产品搜索
假设我们有一个产品表 Product
,我们希望根据名称、价格区间和类别来进行搜索。
import com.querydsl.core.BooleanBuilder;
import com.querydsl.sql.SQLQueryFactory;
import java.util.List;
public class ProductSearch {
private final SQLQueryFactory queryFactory;
public ProductSearch(SQLQueryFactory queryFactory) {
this.queryFactory = queryFactory;
}
/** * 根据名称、价格区间和类别搜索产品 * * @param name 产品名称 * @param minPrice 最低价格 * @param maxPrice 最高价格 * @param category 产品类别 * @return 满足条件的产品列表 */
public List<Product> searchProducts(String name, Double minPrice, Double maxPrice, String category) {
QProduct qProduct = QProduct.product;
// 初始化 BooleanBuilder
BooleanBuilder builder = new BooleanBuilder();
// 根据名称构建条件
if (name != null) {
builder.and(qProduct.name.containsIgnoreCase(name));
}
// 根据最低价格构建条件
if (minPrice != null) {
builder.and(qProduct.price.goe(minPrice));
}
// 根据最高价格构建条件
if (maxPrice != null) {
builder.and(qProduct.price.loe(maxPrice));
}
// 根据类别构建条件
if (category != null) {
builder.and(qProduct.category.eq(category));
}
// 执行查询并返回结果
return queryFactory.selectFrom(qProduct)
.where(builder)
.fetch();
}
}
案例 3:订单查询
假设我们有一个订单表 Order
,我们想根据客户ID、订单状态和日期范围来查询订单。
import com.querydsl.core.BooleanBuilder;
import com.querydsl.sql.SQLQueryFactory;
import java.time.LocalDate;
import java.util.List;
public class OrderQuery {
private final SQLQueryFactory queryFactory;
public OrderQuery(SQLQueryFactory queryFactory) {
this.queryFactory = queryFactory;
}
/** * 根据客户ID、订单状态和日期范围查询订单 * * @param customerId 客户ID * @param status 订单状态 * @param startDate 开始日期 * @param endDate 结束日期 * @return 满足条件的订单列表 */
public List<Order> queryOrders(Long customerId, String status, LocalDate startDate, LocalDate endDate) {
QOrder qOrder = QOrder.order;
// 初始化 BooleanBuilder
BooleanBuilder builder = new BooleanBuilder();
// 根据客户ID构建条件
if (customerId != null) {
builder.and(qOrder.customerId.eq(customerId));
}
// 根据订单状态构建条件
if (status != null) {
builder.and(qOrder.status.eq(status));
}
// 根据开始日期构建条件
if (startDate != null) {
builder.and(qOrder.orderDate.goe(startDate));
}
// 根据结束日期构建条件
if (endDate != null) {
builder.and(qOrder.orderDate.loe(endDate));
}
// 执行查询并返回结果
return queryFactory.selectFrom(qOrder)
.where(builder)
.fetch();
}
}
三、总结
BooleanBuilder
提供了一种灵活且方便的方式来构建复杂的逻辑条件表达式。通过链式调用,开发者可以轻松地组合多个条件,从而生成复杂的查询逻辑。在实际应用中,它常用于构建动态查询条件,根据不同的业务需求生成相应的 SQL 语句。
文章评论