繁体   English   中英

计算嵌套数组中多个列和单词之间的匹配

[英]Count matches between multiple columns and words in a nested array

我先前的问题已解决。 现在,我需要开发一个相关但更复杂的查询。

我有一张这样的桌子:

id     description          additional_info
-------------------------------------------
123    games                XYD
124    Festivals sport      swim

我需要计算与数组匹配的次数,如下所示:

array_content varchar[] := {"Festivals,games","sport,swim"}

如果列descriptionadditional_info中的任何一个包含用逗号分隔的任何标签,则我们将其计为1。因此,每个数组元素(由多个单词组成)只能对总数贡献1。

以上示例的结果应为:

id    RID    Matches
1     123    1
2     124    2

答案并不简单,但要弄清您的要求却比较困难:

SELECT row_number() OVER (ORDER BY t.id) AS id
     , t.id AS "RID"
     , count(DISTINCT a.ord) AS "Matches"
FROM   tbl t
LEFT   JOIN (
   unnest(array_content) WITH ORDINALITY x(elem, ord)
   CROSS JOIN LATERAL
   unnest(string_to_array(elem, ',')) txt
   ) a ON t.description ~ a.txt
       OR t.additional_info ~ a.txt
GROUP  BY t.id;

准确产生您想要的结果。
array_content是您搜索词的数组。

这是如何运作的?

搜索项中外部数组的每个数组元素都是一个逗号分隔的列表。 通过取消嵌套两次来分解奇数构造(将外部数组的每个元素转换为另一个数组之后)。 例:

SELECT *
FROM   unnest('{"Festivals,games","sport,swim"}'::varchar[]) WITH ORDINALITY x(elem, ord)
CROSS  JOIN LATERAL
       unnest(string_to_array(elem, ',')) txt;

结果:

 elem            | ord |  txt
-----------------+-----+------------
 Festivals,games | 1   | Festivals
 Festivals,games | 1   | games
 sport,swim      | 2   | sport
 sport,swim      | 2   | swim

既然你要指望一次为每个外数组元素的比赛,我们生成与飞一个唯一的编号WITH ORDINALITY 细节:

现在我们可以在所需匹配的条件下将LEFT JOIN到此派生表:

   ... ON t.description ~ a.txt
       OR t.additional_info ~ a.txt

..并使用count(DISTINCT a.ord)获得计数,即使多个搜索字词匹配,每个数组也仅计数一次。

最后,我在row_number() OVER (ORDER BY t.id) AS id添加了神秘的id row_number() OVER (ORDER BY t.id) AS id假设它应该是序列号)。 Voilá。

正则表达式匹配( ~ )的注意事项与上一个问题相同:

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM