我正在尝试使用指南中描述的setDistinct(true)
:http://mybatis.github.io/generator/generatedobjects/exampleClassUsage.html
我用这种方式写的:
testExample ae = new testExample();
testExample.Criteria criteriatest = ae.createCriteria();
ae.setDistinct(true);
criteriatest.andIDENTLAVEqualTo(Long.parseLong(cert.getCODINDIVID()));
ae.or(criteriatest);
List<test> listtest = testMapper.selectByExample(ae);
但setDistinct(true)
不会影响结果。
我应该在哪里添加setDistinct行?
答案 0 :(得分:2)
您引用的链接看起来像是一个非常旧版本的 MyBatis 。在该页面上,它列出了以下内容:
版本:1.3.3-SNAPSHOT
最新版本是:
的MyBatis-3.3.0-SNAPSHOT
为setDistinct
加密3.x代码不会返回任何内容:
https://github.com/mybatis/mybatis-3/search?q=setDistinct
我很惊讶您没有收到有关未找到方法的编译时错误。您使用的是版本1.3.3 (或1.x)吗?
我建议在查询中执行DISTINCT
权限。由于 MyBatis 通常是一种接近SQL-metal 类型的映射框架,我认为最好将其添加到映射器中文件的查询本身。加上这种方式,你可以具体选择DISTINCT
的内容。 setDistinct
方法似乎没有提供任何指定目标的方法。
对于 MyBatis 3 ,我认为类似的查询风格是这样的:
http://mybatis.github.io/mybatis-3/statement-builders.html
这似乎类似于 jOOQ -style DSL 。它有一个SELECT_DISTINCT
方法。我个人觉得根据映射文件中的动态SQL需要使用一些 XML标记来编码/读取纯SQL 更容易,但这是当然是 MyBatis 3 中可行的选择。
修改强>
所以,我做了一些挖掘工作,而我无法在 MyBatis3 git repo中找到代码的原因是因为setDistinct
位于 mybatis-生成器代码库。
我认为这里的部分问题可能源于 Mybatis-Generator 对 GitHub 的描述:
MBG寻求对大部分数据库产生重大影响 简单CRUD(创建,检索,更新,删除)的操作。
因此,它提供了一种简单DISTINCT
的方法,但控制有限。
代码位于addClassElements
类的ProviderSelectByExampleWithoutBLOBsMethodGenerator
方法中。搜索setDistinct
不会显示在Github搜索上,因为它是自动生成的 setter 。
这是相关的code snippet:
boolean distinctCheck = true;
for (IntrospectedColumn introspectedColumn : getColumns()) {
if (distinctCheck) {
method.addBodyLine("if (example != null && example.isDistinct()) {"); //$NON-NLS-1$
method.addBodyLine(String.format("%sSELECT_DISTINCT(\"%s\");", //$NON-NLS-1$
builderPrefix,
escapeStringForJava(getSelectListPhrase(introspectedColumn))));
method.addBodyLine("} else {"); //$NON-NLS-1$
method.addBodyLine(String.format("%sSELECT(\"%s\");", //$NON-NLS-1$
builderPrefix,
escapeStringForJava(getSelectListPhrase(introspectedColumn))));
method.addBodyLine("}"); //$NON-NLS-1$
} else {
method.addBodyLine(String.format("%sSELECT(\"%s\");", //$NON-NLS-1$
builderPrefix,
escapeStringForJava(getSelectListPhrase(introspectedColumn))));
}
distinctCheck = false;
}
所以,从本质上讲,这看起来好像包装了我原先提到的SELECT_DISTINCT
方法,它试图反省列并将DISTINCT
应用于它返回的所有列。
深入挖掘,它最终会调用此代码来获取列:
/**
* Returns all columns in the table (for use by the select by primary key
* and select by example with BLOBs methods)
*
* @return a List of ColumnDefinition objects for all columns in the table
*/
public List<IntrospectedColumn> getAllColumns() {
List<IntrospectedColumn> answer = new ArrayList<IntrospectedColumn>();
answer.addAll(primaryKeyColumns);
answer.addAll(baseColumns);
answer.addAll(blobColumns);
return answer;
}
所以,这绝对是一个全有或全无DISTINCT
(而 Postgres 本身只允许DISTINCT
在某些列上。)
在实际调用setDistinct
对象之前,尝试将ae
移动到最后一行。也许随后的调用会影响列集(尽管从代码中看,它似乎不应该 - 基本上一旦设置了列,setDistinct
应该使用它们。)
另一件有趣的事情是看看它实际生成的SQL是否有setDistinct
。
检查此链接以获取有关调试/日志记录的更多详细信息:
http://mybatis.github.io/generator/reference/logging.html
我建议尝试使用基于XML的映射器文件定义,这些定义将 SQL 与 XML 标记交错以实现动态性。 IMO,它比上面的代码 Mybatis Generator 代码片段更容易理解。我认为这是使用生成器的主要权衡之一 - 最初更容易创建,但以后更难以阅读/维护。
对于超级动态查询,我可以看到更多优势,但那种情况与简单CRUD 操作的自我描述背道而驰。