Java Steam.filter() 過濾 通過Predicate實現 多條件動態 or and 過濾
阿新 • • 發佈:2019-02-11
/** * ============================================== * Copy right 2015-2018 by ja * ---------------------------------------------- * This is not a free software, without any authorization is not allowed to use and spread. * ============================================== * * @author : Jalan * @version : v1.0.0 * @desc : 把物件屬性抽象出來,可做為引數傳遞 * @since : 2018/2/7 21:07 */ @FunctionalInterface public interface ObjectPropertyPredicate<T> { /** * 把屬性當引數傳遞到方法中,由方法去處理這個屬性的值做什麼。 * 傳參使用: o -> o.propertyName * 接收引數方法內使用: * 引數:ObjectPropertyPredicate<FreeReportDataVO> express * Predicate<Object> press = (obj) -> express.getProperty(obj).toString().startsWith("測試"); * express.getProperty(obj) * @param o * @return */ Object getProperty(T o); }
/** * * ============================================== * Copy right 2015-2018 by Jalan * ---------------------------------------------- * This is not a free software, without any authorization is not allowed to use and spread. * ============================================== * * @author : Jalan * @version : v1.0.0 * @desc : 查詢選項 * @since : 2018/2/7 19:28 */ public enum FilterModeEnum { startsWith , equals, contains }
/** * * ============================================== * Copy right 2015-2018 by Jalan * ---------------------------------------------- * This is not a free software, without any authorization is not allowed to use and spread. * ============================================== * * @author : Jalan * @version : v1.0.0 * @desc : 測試實體類 * @since : 2018/2/7 11:58 */ @ApiModel(description = "測試實體類") @Data @EqualsAndHashCode(callSuper = true) public class TestDataVO{ private String code; private String name; private String remark; }
/**
* 通過批量過濾條件(codes) 過濾指定物件屬性的值
* @param dataSource 資料來源集合
* @param codes 過濾條件集合
* @param express 過濾集合物件目標屬性表示式
* @param filterMode 過濾方式
* @return 返回符合過濾條件codes的物件集合
*/
public static List<TestDataVO> queryArray(List<TestDataVO> dataSource, List<String> codes, ObjectPropertyPredicate<TestDataVO> express, FilterModeEnum filterMode) {
List<TestDataVO> result = new ArrayList<>();
if (dataSource == null) {
return result;
}
if (codes == null || (long) codes.size() == 0) {
return dataSource;
}
if (express == null) {
return dataSource;
}
if (filterMode == FilterModeEnum.startsWith) {
Predicate<TestDataVO> expressOr = f -> false;
for (String code : codes) {
Predicate<TestDataVO> press = (w) -> express.getProperty(w).toString().startsWith(code);
expressOr = expressOr.or(press);
}
result = dataSource.stream().filter(expressOr).collect(Collectors.toList());
} else if (filterMode == FilterModeEnum.contains) {
result = dataSource.stream().filter(f -> codes.contains(express.getProperty(f).toString())).collect(Collectors.toList());
} else if (filterMode == FilterModeEnum.equals) {
Predicate<TestDataVO> expressOr = f -> false;
for (String code : codes) {
Predicate<TestDataVO> press = (w) ->StringUtils.equals(express.getProperty(w).toString(),code);
expressOr = expressOr.or(press);
}
result = dataSource.stream().filter(expressOr).collect(Collectors.toList());
}
return result;
}
最後測試:
List<TestDataVO> data = new ArrayList<>();
TestDataVO td1 = new TestDataVO();
td1.setCode("測試A-code");
td1.setName("測試A-name");
TestDataVO td2 = new TestDataVO();
td2.setCode("測試B-code");
td2.setName("測試B-name");
TestDataVO td3 = new TestDataVO();
td3.setCode("測試C-code");
td3.setName("測試C-name");
TestDataVO td4 = new TestDataVO();
td4.setCode("測試D-code");
td4.setName("測試D-name");
TestDataVO td5= new TestDataVO();
td5.setCode("測試E-code");
td5.setName("測試E-name");
data.add(td1);
data.add(td2);
data.add(td3);
data.add(td4);
data.add(td5);
List<String> filterCodeCondition = ArrayList<>();
filterCodeCondition.add("測試A-code");
filterCodeCondition.add("測試C-code");
/**
* 過濾結果為 td1,td3 物件
*/
List<TestDataVO> filterResult = queryArray(data,filterCodeCondition , TestDataVO::getCode, FilterModeEnum.startsWith);
List<String> filterNameCondition = ArrayList<>();
filterCodeCondition.add("D-name");
filterCodeCondition.add("E-name");
/**
* 過濾結果為 td4,td5 物件
*/
List<TestDataVO> filterResult = queryArray(data,filterCodeCondition , TestDataVO::getName, FilterModeEnum.contains);