我正在尝试使用search:search
API在Marklogic中进行搜索。
let $q := "Foo ^ Bar"
let $start := 0
let $page-length := 10
search:search($q ,$config:SEARCH-OPTIONS ,$start ,$page-length)
其中$config:SEARCH-OPTIONS
是一堆搜索选项。
我的数据库中有两条记录,但上面的查询只能返回一条记录。
现在我搜索时得到1场比赛。但是,我得到的结果总数为2.这是错误的,然后我将“未过滤”设置应用于查询,并且有两个匹配。但是,为什么过滤后的查询会给我一个BEFORE过滤结果的计数,给我一个不正确的总数?
有没有办法让Marklogic代替实际计数? <{1}}如果你返回每个结果都有效,但如果你正在使用分页,这显然不起作用。
答案 0 :(得分:3)
不幸的是,搜索API无法满足您的需求。获得100%准确计数的唯一方法是执行已过滤查询结果的fn:count
。如果你的两个结果的情况不太费时,但如果你的搜索返回了数百万个文件,那就太高了。这就是为什么在内部,搜索API使用xdmp:estimate而不能配置为不这样做。
解决此问题的常用方法是使用消息传递和UI;确保您的UI谈论近似结果计数,并且不要让分页控件在一次跳转中将用户带入结果集太远,以防它们超出结束。 Google就是这种方法的一个很好的例子。
在比例的另一端,我只是检查了搜索API的计数估算值,并在结果集看起来将其替换为fn:count
的输出时取得了成功小到足以让用户注意到估计值与实际计数之间的差异(如您的示例所示)。在这种情况下,fn:count
的成本应该很低。
您没有明确询问,因此您可能知道这一点,但在这种情况下估计错误的原因很可能是您在查询字符串中包含标点符号,这会导致无法从索引中解析的查询单独(我假设你的文件都包含“Foo”和“Bar”这两个词,并且区别因素是它们中只有一个包含“^”?)。如果您的申请允许排除该选项,那么它将为您提供更可靠的估算。
最后的选择,如果您确定结果集总是很小,则完全绕过搜索API并直接调用cts:search
。然后,您可以自由地对结果运行自己的fn:count
,并根据需要对它们进行分页。您可以自己以编程方式构建cts:query
,或使用search:parse函数生成搜索api将在内部使用的cts查询,并将其自行传递给cts:search
。
答案 1 :(得分:2)
为什么过滤后的查询会返回BEFORE过滤结果的计数?
因为总数基于xdmp:estimate
或cts:remainder
,它总是返回与索引中的查询匹配的未过滤的片段数。 http://docs.marklogic.com/guide/search-dev/count_estimate的文档讨论了这个主题:“有效地,xdmp:估计通过使用开发人员手中的索引来决定优化计数。”
您可以使用fn:count
代替xdmp:estimate
或cts:remainder
- 但您的应用程序将使用结果总数执行O(n)。通常最好的策略是使用xdmp:estimate
或cts:remainder
,但要安排文档结构和数据库索引,以便估算准确。