Параметризация запроса select в унарной функции kdb - PullRequest
0 голосов
/ 17 марта 2019

Я бы хотел иметь возможность выбирать строки в пакетах из очень большой таблицы ключей, которая хранится удаленно на диске. В качестве игрушечного примера для проверки моей функции я настроил следующие таблицы t и nt ...

t:([sym:110?`A`aa`Abc`B`bb`Bac];px:110?10f;id:1+til 110)
nt:0#t

Я выбираю из таблицы только записи, которые начинаются с символа «A», подсчитываю количество символов, делю счет на количество строк, которые я хотел бы получить для каждого вызова функции (10), и округляю их вверх до ближайшего целого числа ...

aRec:select from t where sym like "A*"
counter:count aRec
divy:counter%10
divyUP:ceiling divy

Затем я устанавливаю переменную idx равной 0 и записываю if statement в качестве параметризованной функции. Это проверяет, равен ли idx divyUP. Если нет, то он должен выбрать первые 10 строк aRec, перенести их в таблицу nt, увеличить аргумент функции x на 10 и увеличить переменную idx на 1. После того, как idx переменная и divyUP равны, она должна выйти из функции ...

idx:0
batches:{[x]if[not idx=divyUP;batch::select[x 10]from aRec;`nt upsert batch;x+:10;idx+::1]}

Однако, когда я вызываю функцию, она возвращает type ошибку ...

q)batches 0
'type
[1]  batches:{[x]if[not idx=divyUP;batch::select[x 10]from aRec;`nt upsert batch;x+:10;idx+::1]}
                                                 ^

Я тоже пытался использовать его с sublist, но получаю тот же результат ...

batches:{[x]if[not idx=divyUP;batch::x 10 sublist aRec;`nt upsert batch;x+:10;idx+::1]}

q)batches 0
'type
[1]  batches:{[x]if[not idx=divyUP;batch::x 10 sublist aRec;`nt upsert batch;x+:10;idx+::1]}
                                          ^

Однако выполнение одной из этих команд за пределами функции возвращает ожидаемые результаты ...

q)select[0 10] from aRec
sym| px        id
---| ------------
A  | 4.236121  1
A  | 5.932252  3
Abc| 5.473628  5
A  | 0.7014928 7
Abc| 3.503483  8
A  | 8.254616  9
Abc| 4.328712  10
A  | 5.435053  19
A  | 1.014108  22
A  | 1.492811  25

q)0 10 sublist aRec
sym| px        id
---| ------------
A  | 4.236121  1
A  | 5.932252  3
Abc| 5.473628  5
A  | 0.7014928 7
Abc| 3.503483  8
A  | 8.254616  9
Abc| 4.328712  10
A  | 5.435053  19
A  | 1.014108  22
A  | 1.492811  25

Ответы [ 2 ]

2 голосов
/ 18 марта 2019

Проблема в том, что в вашем примере выберите [], и для подсписка требуется список в качестве входных данных, но ваш ввод не является списком. Причина этого заключается в том, что когда в элементах есть переменная (которая будет формировать список), она больше не рассматривается как простой список, означающий, что пробел (пробел) нельзя использовать для разделения значений. В этом случае точка с запятой обязательна.

q) x:2
q) (1;x) / (1 2)

Выберите команду: Измените ввод на (x; 10), чтобы он работал.

q) t:([]id:1 2 3; v: 3 4 5)
q) {select[(x;2)] from t} 1
`id  `v
---------
 2    4
 3    5

Другой альтернативой является использование столбца «i» (индекс):

q) {select from t where i within x + 0 2} 1

Команда подсписка: Преобразовать левый ввод функции подсписка в список (x; 10).

 q) {(x;2) sublist t}1
1 голос
/ 17 марта 2019

Вы не можете использовать форму select [] с таким же вводом переменных, вместо этого вы можете использовать функциональный выбор, показанный в https://code.kx.com/q4m3/9_Queries_q-sql/#912-functional-forms, где вы в качестве 5-го аргумента вводите нужные вам строки

Надеюсь, это поможет!

...