3

例如:

我在 UI 端有一张这样的表:

在此处输入图像描述

这是上面显示的所有数据的列表:

List<MyBean> myList;

现在我想搜索categoryNamelanguageID或者categoryID使用这样的方法:

private List<MyBean> search(List<MyBean> myList, String columnName, String criteria)

因此,我只需执行以下操作即可获得符合我的条件的结果:

第一种情况: List<Bean> results = this.search(myList, "categoryName", "Dog H");

第二种情况: List<Bean> results = this.search(myList, "categoryName", "Dog House");

(此时resultslist 在两种情况下都将返回 3 个元素——根据上表)。


有可能实现这一目标吗?正如你们所看到的,这是一种类似于%LIKE%功能的搜索,SQL但专注于java.util.List

提前致谢。

4

4 回答 4

6

我使用以下方法解决了我的问题:

然后我只是通过这种方式导入了以下命名空间:

import static ch.lambdaj.Lambda.*;

并使用以下方法从我的标准中获得结果:

List<MyBean> results = select(myList, having(on(MyBean.class).getCategoryName(), org.hamcrest.Matchers.containsString("Dog H")));

因此,在我传递的那行代码中,我在问题中要求myList"column"and criteria

该行的其余代码很容易理解,所以我不会写它。

希望这对其他人也有帮助。

于 2012-08-07T05:13:51.160 回答
3

这里有两种方法

“有力”的方法;)

public List<MyBean> search(List<MyBean> lstBeans, String method, String regExp) {
    List<MyBean> lstMatch = new ArrayList<>(lstBeans.size());
    Pattern pattern = Pattern.compile(regExp);
    for (MyBean bean : lstBeans) {

        if (method.equals("categoryName")) {
            String name = bean.getCategoryName();
            if (pattern.matcher(name).matches()) {
                lstMatch.add(bean);
            }
        }
    }
    return lstMatch;
}

.
.
.

List<MyBean> matches = search(lstBeans, "categoryName", "^Dog.*$");

基本上,这依赖于知道给定的方法名称将返回给定的结果,这将使过滤类别的结果变得困难,例如......

人们拼写错误的方法名称或没有考虑到它区分大小写也存在问题......

或者你可以尝试一些更可变的东西

public interface Criteria<T> {
    public boolean matches(T bean);
}

public class CategoryNameCriteria implements Criteria<MyBean> {

    private Pattern pattern;

    public CategoryCriteria(String criteria) {
        pattern = Pattern.compile(criteria);
    }

    @Override
    public boolean matches(MyBean bean) {
        return pattern.matcher(bean.getCategoryName()).matches();
    }

}

public <T> List<T> search(List<T> lstBeans, Criteria<T> critera) {
    List<T> lstMatch = new ArrayList<>(lstBeans.size());
    for (T bean : lstBeans) {
        if (critera.matches(bean)) {
            lstMatch.add(bean);
        }
    }
    return lstMatch;
}

.
.
.

matches = search(lstBeans, new CategoryNameCriteria("^Dog.*$"));

这将允许您在不更改基本方法的情况下“定义”自己的标准和匹配要求

这意味着您可以制定一系列独立于搜索方法的标准,例如

public class CategoryIDCriteria implements Criteria<MyBean> {

    private int id;

    public CategoryIDCriteria(int id) {
        this.id = id;
    }

    @Override
    public boolean matches(MyBean bean) {
        return bean.getCategoryID() == id;
    }

}

.
.
.

matches = search(lstBeans, new CategoryIDCriteria(1));

并且因为标准和搜索方法是通用的,所以可以在不同类型的对象中重用它

于 2012-08-07T04:37:18.603 回答
2

如果您愿意使用第三方库,也许JoSQL就足够了?它允许您使用 SQL 查询过滤 POJO 集合...

此外,如果您愿意放弃 SQL 查询,可能会对这篇旧文章感兴趣:How do you query object collections in Java (Criteria/SQL-like)?

于 2012-08-07T05:02:06.037 回答
0

为什么不使用 Guava 的Table而不是 List呢?

Table<Integer, Integer, String> table = HashBasedTable.create(); 
table.put(1, 1, "Advantage Flea");
table.put(1, 2, "Advantage Flea");
table.put(1, 3, "Advantage Flea");
.
.
.

案例#1需要类似的东西:

Collection<String> values = table.values();
for(String value : values) { 
   if(value.contains(queryString) { 
       //found it!
   }
}

案例 #2 很简单,看起来像:

if(table.containsValue("Advantage Flea") { 
    ...
}
于 2012-08-07T04:08:15.553 回答