В KDB я хочу подсчитать количество различных элементов в наборе столбцов.
Например, в таблице будут столбцы a, b, c... и, предоставив список символов lst:`a`b`c, я смогу получить количество различных элементов в этих столбцах.
Я проделал большую часть этой работы, но в конце у меня возникли проблемы с созданием таблицы после использования «каждого» с моей функцией и списком.
До сих пор у меня есть
Сделал функцию:
f:{[x]?[`table;();0b;(enlist x)!enlist(#:;(?:;x))]}
Это было сделано путем анализа «выбрать отдельный x из таблицы».
Затем я хочу применить функцию к каждому элементу в списке символов, используя каждый, взять каждый ответ и соединить их вместе, используя каждый правый элемент.
table has columns a,b,c,d ...
lst:`a`b`c
ans:(),/: f each lst
В настоящее время это дает такой результат:
+(,`a)!,,983
+(,`b)!,,931
+(,`c)!,,5
Цифры верны, но я не понимаю, почему результат выглядит так.
Если я запущу функцию f только с одним входом, ответ будет:
f[`a]
a
----
983
Я ожидал, что функция создаст множество таких таблиц с одним столбцом, а затем объединит их в одну таблицу, но этого не произошло, я не понимаю почему.
Ваш f
возвращает таблицу, поэтому f each
вернет список таблиц.... но поскольку ваши таблицы не соответствуют одной и той же схеме (каждая из них будет иметь разные имена столбцов), то список таблиц не будет автоматически сворачиваться в один стол.
Например, вы можете использовать добавление-соединение для объединения таблиц разных схем.
q)table:([]a:10?10;b:10?2;c:10?10000)
q)(,'/)f each lst
a b c
------
7 2 10
но я не уверен, хотите ли вы видеть это так, вы хотите, чтобы это было так?
q){([]col:raze key each x;counts:raze value each x:raze x)}f each lst
col counts
----------
a 6
b 2
c 10
Этого можно добиться проще, изменив, например, функцию f
.
q)f:{`col`counts!(x;count distinct table x)}
q)f each lst
col counts
----------
a 6
b 2
c 10
(при условии, что таблица находится в памяти) или более соответствует вашему исходному решению:
q)f:{?[table;();(1#`col)!enlist 1#x;(1#`counts)!enlist(count distinct@;x)]}
q)raze f each lst
col| counts
---| ------
a | 6
b | 2
c | 10
f
можно настроить для выполнения необходимых действий в одном или нескольких столбцах:
q)table:([] a:100?100;b:100?100;c:100?100)
q)f:{[x]?[`table;();0b;((),x)!{(count;(distinct;x))} each (),x]}
q)f[`a]
a
--
65
q)f[`a`b`c]
a b c
--------
65 63 59
Альтернативный формат:
q)f:{[x]?[`table;();0b;`cls`counts!(enlist (),x;(each;{count distinct x};enlist,x))]}
q)f[`a]
cls counts
----------
a 65
q)f[`a`b`c]
cls counts
----------
a 65
b 63
c 59