找到kdb +中的单词对数

时间:2017-11-20 18:07:59

标签: kdb q-lang

我有一个包含多行项目代码的文件,如下所示。有100万行类似于这些

  1.  123,134,256,345,789.....
  2.  123,256,345,678,789......
   .
   .  

我想在kdb +中使用q找到文件中每行的所有单词/项目的计数。即,在同一行中出现的任何两对单词可以被认为是单词对。  e.g:

(123,134),(123,256),(134,256),(123,345)(123,789),(134,789)是第1行中的一些单词对 (123,256),(123,345),(123,345),(678,789),(345,789)是第2行中的一些单词对

word/item pair count  

 `123,134----1 
  123,256---2
  345,789---2`

我正在使用read0读取文件,并且能够使用vsusing count each group将每行转换为列表来计算单词数,但现在我想查找所有单词的数量文件中每行的单词对。

提前感谢您的帮助

3 个答案:

答案 0 :(得分:2)

我不是100%我理解你对单词对的定义。如果我的逻辑与你想要的不匹配,也许你可以扩展一点。

在下面的示例中,我创建了一个用于测试的5x5符号矩阵 - 从每行中选择不同的值对,然后检查每个行中出现的行数。

请仔细检查自己的结果。

q)test:5 cut`$string 25?5

q)test
2 0 1 0 0
2 4 4 2 0
1 0 0 3 4
2 1 1 4 4
3 0 3 4 0

q)count each group raze {l[where(count'[l:distinct distinct each asc'[x cross x:distinct x]])>1]} each test
0 2| 2
1 2| 2
0 1| 2
2 4| 2
0 4| 3
1 3| 1
1 4| 2
0 3| 2
3 4| 2

答案 1 :(得分:1)

要在Matthew上面的答案中添加一些其他案例,如果你想要的是以这种方式将列表分成两组:

l:"a,b,c,d,e,f,g"

变为

"a,b"
"b,c"
"c,d"
"d,e"
"e,f"
"f,g"

因此只能使用有效的对,你可以使用这样的东西:

f:{count each group b flip 0 1+\:til 1+count[b:","vs x]-1}

q)f l
,"a" ,"b"| 1
,"b" ,"c"| 1
,"c" ,"d"| 1
,"d" ,"e"| 1
,"e" ,"f"| 1
,"f" ,"g"| 1

我们将输入列表拆分为“。”,然后使用索引来获取每个元素的列表,并将元素直接放到其右侧,然后将结果列表对分组以计算不同的对。如果你想拆分它,那么我就变成了

"a,b"
"c,d"
"e,f"  

然后你可以使用它:

g:{count each group b flip 0 1+\:2*til count[b:","vs x]div 2}

q)g l
,"a" ,"b"| 1
,"c" ,"d"| 1
,"e" ,"f"| 1

使用类似的方法,从偶数定位的元素开始并将它们放到右边,并重复上述步骤。 您可以轻松地将这些应用于使用read0:

读取的行
r:read0`:file.txt
f each r

将输出每行的每对计数字典,这可以求和,以给出整个文件中每种方法的每个单词对的总数。

希望这会有所帮助 - 目前还不清楚你们的意思是什么,所以如果我的答案都不是马修的用法,那么你可以编辑一个更完整的解释你想要什么,我们可以帮助你。

答案 2 :(得分:1)

如果你想考虑每一行中2对的所有可能组合,那么这可能会有所帮助。以下函数可用于提供不同的组合,其中x是列表的大小,y是组合的长度:

q)comb:{$[x=y;enlist til x;1=y;flip enlist til x;.z.s[x;y],.z.s[x;y-1],'x-:1]}
q)comb[3;2]
0 1
0 2
1 2

从这里我们可以索引到每个列表以获取对,然后raze给出所有对的单个列表,group以获得每对发生的索引,然后{{1}每组中的索引数:

count