kdb q - update statement in try catch
Asked Answered
U

2

5

In q, say someone was naughty and created a function that sometimes returns a table with a mixed-type column:

t:([] c1:(`a;"dfdf";`b;"ccvcv"))

and sometimes a table with a symbol-only column:

t:([] c1:`a`dfdf`b`ccvcv)

I want to update c1 to contain only symbols in a try-catch in case tc1` already contains only symbols. But I have a hard time translating the statement

update c1:`$c1 from t where 10h=type each c1

into the ![t;c;b;a] syntax which works with the try-catch @ operator

t:([] c1:(`a;"dfdf";`b;"ccvcv"));
c:enlist(=;type each `c1;10h);
b:0b;
a:(enlist`c1)!(enlist `$`c1); / TYPE ERROR
@[![;c;b;a];t;`continue] / this is what I want to do

Thanks for the help

Ukulele answered 22/3, 2018 at 11:48 Comment(0)
B
5

Your a should be defined like so:

a:(enlist`c1)!enlist($;enlist`;`c1)

You can get this by using parse on your original update Q-SQL statement:

q)parse "update c1:`$c1 from t where 10h=type each c1"
!
`t
,,(=;10h;(k){x'y};@:;`c1))
0b
(,`c1)!,($;,`;`c1)

Noting that , in k is enlist in Q

You also need to change your definition of c:

c:enlist(=;(each;type;`c1);10h);

Putting it all together:

q)t:([] c1:(`a;"dfdf";`b;"ccvcv"))
q)c:enlist(=;(each;type;`c1);10h);
q)b:0b;
q)a:(enlist`c1)!enlist($;enlist`;`c1)
q)![t;c;b;a]
c1
-----
a
dfdf
b
ccvcv

But as pointed out in another answer, best to avoid functional form wherever possible

Barbera answered 22/3, 2018 at 11:55 Comment(0)
K
2

Sometimes it's best to avoid functional selects, if your use case permits then @ amend is a great alternative which can be particularly useful in place of update statements.

q)@[t;`c1;{$[10=type x;`$x;x]}each]
c1
-----
a
dfdf
b
ccvcv

Or if you still wish to use try-catch:

q)@[t;`c1;{@[`$;x;x]}each]
c1
-----
a
dfdf
b
ccvcv
Krause answered 22/3, 2018 at 12:0 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.