Send Feedback
Skip to content

A. Built-in Functions

A.0 Overview

The collection of built-in functions in q is rich and powerful. In previous versions of this tutorial we tried for complete coverage of built-ins. However, in this release we no longer attempt to be all-inclusive. First, there are functions that are more advanced than this tutorial. And second, the built-in functions are now well documented on the KX Documentation website; please go there for complete coverage.

In this chapter, we extend the coverage of built-ins in the main text by detailing here those that were omitted or only mentioned in passing in the main text.

Note

  • If we do not mention the valence (rank) of a function explicitly, it is unary.
  • In the description of each function, x refers to the first parameter, y to the second (if it exists) and z to the third (if it exists).
  • Check the list in 4.0 to see which of the built-ins are multi-threaded (many are as of q4.0).

A.1 and all

The aggregate and is the same as & for people who like typing extra characters.

q)1b and 0b
0b
q)42 and 43
42

The aggregate all is &/, which applies & cumulatively across a numeric list and returns the boolean result. For people who like typing extra characters.

q)all 100100b
0b
q)all 10 20 30
1b

A.2 asc desc

The uniform asc takes a list of comparables x and returns a list sorted in ascending order with the `s# attribute applied. When evaluated on a dictionary, it reorders the key-value pairs (on a copy) so that the values are sorted.

q)asc 3 7 2 8 1 9
`s#1 2 3 7 8 9
q)asc `b`c`a!3 2 1
a| 1
c| 2
b| 3

A table is sorted by the first non-key column and the sorted attribute is set on that column if there is only one non-key column; otherwise the parted attribute is set. The sort is stable in that it preserves the original order of equals; thus it acts as the identity on a sorted list

/ table
q)meta asc ([]a:3 4 1;b:`a`d`s) / sets parted attribute
c| t f a
-| -----
a| j p
b| s
q)meta asc([]a:3 4 1)           / sets sorted attribute
c| t f a
-| -----
a| j s
/ keyed table
```q
q)meta asc ([c1:`a`b] c2:2 1; c3:01b) / sets parted attribute
c | t f a
--| -----
c1| s
c2| j p
c3| b
q)meta asc ([c1:`a`b] c2:2 1)        / sets sorted attribute
c | t f a
--| -----
c1| s
c2| j s

The uniform desc returns a copy of x, a list of comparables, sorted in descending order. When evaluated on a dictionary, it reorders the key-value pairs so that the values are sorted. The sort is stable in that it preserves the original order of equals; thus it acts as the identity on a sorted list.

q)desc 3 7 2 8 1 9
9 8 7 3 2 1
q)desc `b`c`a!2 3 1
c| 3
b| 2
a| 1

For a table it sorts on the first non-key column and places the `s# attribute on that column.

q)desc([]a:3 4 1;b:`a`d`s)
a b
---
4 d
3 a
1 s
q)meta desc([]a:3 4 1;b:`a`d`s)
c| t f a
-| -----
a| j
b| s

Unlike asc, which sets the parted attribute when there are other non-key columns, desc sets no attribute.

A.3 attr

The function attr returns any attribute of x as a symbol. No attributes is the empty symbol.

Code Attribute
s sorted
u unique (hash table)
p partitioned (grouped)
g true index (dynamic attribute): enables constant time update and access for real-time tables
q)attr til 5
`
q)attr asc 30 20 40 10
`s

A.4 avg avgs mavg

The aggregate avg returns the float arithmetic mean of a numeric or temporal list x.

q)avg 1+til 1000
500.5

The function avg is equivalent to

{sum[x]%count x}

It is possible to apply avg to a nested list provided the sublists conform. In this context, the result conforms to the sublists and the average is calculated recursively on the sublists.

q)avg (1 2;100 200;1000 2000)
367 734f

The uniform avgs is avg\, which computes the running averages of a numeric list.

q)avgs 1+til 10
1 1.5 2 2.5 3 3.5 4 4.5 5 5.5

The binary mavg takes a positive integer x and returns the x-wide moving average of the numeric list y. At each position in y, it computes the average of the x preceding items, or as many as are available up to x.

One way to visualize this is avg uses a moving window of width x extending as far to the left as can fit. It ignores any nulls, which would otherwise null any window that contains them. It is uniform in its second argument.

In the following example, the first item in the result is the average of itself only; the second result item is the average of the first two source items; all other items reflect the average of the item at the position along with its two predecessors.

q)3 mavg 10 20 30 40 50
10 15 20 30 40f
q)3 mavg 0N 10 20 30 40 50
0n 10 15 20 30 40

Tip

For length 1, the result is the source converted to float.

A.5 bin binr

The binary bin takes a simple list of items x sorted in strictly increasing order. It returns the index of the last item in x which is less than or equal to y. It is atomic in y. Loosely speaking, the result of bin is (one less than) the position at which y would fall in x, looking from the left starting at -1. The type of y must strictly match the type of x; no type promotion is performed.

More precisely, the result is -1 if y is less than the first item in x. Otherwise, the result is the index of the last item of x that is less than or equal to y, which is the found index if y is in x. If y is greater than the last item in x, the result is the last index of x.

Note

While the items of x should be in strictly increasing order for the result to meaningful, this condition is not enforced. The result of bin when x is not strictly increasing is essentially undefined.

Tip

For large sorted lists, the binary search performed by bin can be much faster than the linear search performed by (?).

q)L:1.0+til 50000000
q)L bin 25000000.
24999999
q)L?25000000.
2499999
q)\t L bin 25000000.
0
q)\t L?25000000.
22

q)L bin 25000000.5
24999999
q)L?25000000.5
50000000
q)\t L bin 25000000.5
0
q)\t L?25000000.5
20

q)\t L bin 50000000.5
0
q)\t L?50000000.5
115

The binary binr is closely related to bin. Whereas bin looks from the left, binr looks from the right. The result is the index of the first item of the x that is greater than or equal to y.

q)L:1.0+til 50000000
q)L bin 25000000.5
24999999
q)L binr 25000000.5
25000000

A.6 ? Choose

The binary Choose comprises several overloads of ? that generate pseudo-random results. In the case where x is a non-negative long and y is a non-negative numeric value, ? is called Roll and returns a list of pseudo-random numbers with replacement between 0 and y, not including y.

q)5?10
2 4 5 4 2
q)5?10
7 8 5 6 4
q)10?100.0
10.24432 86.71096 72.78528 16.27662 68.84756 81.77547 75.20102 10.868..
q)10?100.0
64.30982 67.08738 67.89082 41.2317 98.77844 38.67353 72.6781 40.46546..

In the case where x is a negative integer and y is a non-negative integer, ? is called Deal and returns a list of pseudo-random numbers without replacement between 0 and y, not including y.

q)-5?10
1 8 5 7 0
q)5?10
2 4 5 4 2

In case y is a list and x is an integer, ? returns a list of x items randomly drawn from y. Again it is called Roll when it acts with replacement for positive x and called Deal when it acts without replacement for negative x.

q)5?`a`b`c`d`e`f
`b`c`f`f`b
q)5?`a`b`c`d`e`f
`e`e`a`e`e
q)-5?`a`b`c`d`e`f
`c`a`d`f`e
q)-5?`a`b`c`d`e`f
`f`a`e`d`c

In case x is a positive integer and y is a symbol of the form `n where n is a positive integer not greater than eight, the result is a random list of x symbols drawn from `a through `p, each comprising exactly n characters. The symbols are distinct when x is negative.

q)10?`1
`c`d`o`m`h`m`n`e`m`m
q)-10?`1
`h`p`j`n`e`o`a`k`l`i
q)-10?`3
`emb`agl`mho`ndm`gmj`egi`gek`hcc`mmb`kbh

The expression -n?n returns a random permutation of til n. This can also be achieved by using 0N as the first parameter to get Permute.

q)0N?10
8 2 4 1 6 0 5 3 7 9
q)0N?`3
`nni`hlc`ikp`egh`mfn`koh`aej`leg`fde`cpg`mih`clp`mea`olm`mpe..
q)0N?("Tom"; "Dick"; "Harry")
"Dick"
"Tom"
"Harry"

A.7 ? Enumerate

The Enum Extend overload of ? enumerates a symbol, with x being the symbolic name of a (presumably unique) list of symbols. It is atomic in y, which is a symbol. The result is the enumeration of y over the domain x. As a side effect, symbols from y not in x are appended to x.

q)sym:`a`b`c
q)`sym?`a`x`b`y`z
`sym$`a`x`b`y`z
q)sym
`a`b`c`x`y`z

Note

The domain can be a file symbol in which case both the file and the variable are updated.

A.8 cor

The binary cor takes two conforming numeric lists and returns the mathematical correlation between the items of the two lists as a float in the range -1f to 1f.

q)23 -11 35 0 cor 42 21 73 39
0.9070229

The function cor is equivalent to

{cov[x;y]%dev[x]*dev y}

A.9 cos acos

The atomic cos is the mathematical cosine of the argument.

q)pi:3.141592653589793
q)cos 0
1f
q)cos pi
-1f
q)cos pi%2
6.123234e-17

The atomic acos is the mathematical inverse of cos. For a float x between -1 and 1, the result is the value between 0 and π whose cosine is x.

q)acos 1
0f
q)acos 1.414213562373095
0n
q)acos -1
3.141593
q)acos 0
1.570796

A.10 count mcount

The aggregate count returns a long representing the number of items in its atom or list parameter. As with any function defined on a lists, it also applies to the value list of a dictionary and hence to tables and keyed tables.

q)count 42
1
q)count til 100
100
q)count `a`b`c`d!10 20 30 40
4
q)count ([] c1:10 20 30; c2:1.1 2.2 3.3)
3
q)count ([k:10 20] c:`one`two)
2

Tip

You cannot use count to determine whether an entity is an atom or list since atoms and singletons both have count 1. Instead test the sign of the type.

q)0>signum type 42
1b
q)0>signum type enlist 42
0b

Tip

Do you know why they call it count? Because it loves to count! Nyah, ha, ha, ha, ha. Vun, and two, and tree, and ...

The binary mcount takes a positive integer x and returns the x-wide moving count of the numeric list y. At each position in y, it counts the number of non-null preceding items up to x. This function is useful in computing other moving quantities, such as moving average, since it correctly reports the effective width of the window at the head of the list and also ignores internal nulls.

q)3 mcount 10 20 30 40 50
1 2 3 3 3i
q)3 mcount 10 20 0N 40 50 60 0N
1 2 2 2 2 3 2i

A.11 cov

The aggregate binary cov takes two conforming numeric lists and returns a float equal to the mathematical covariance between the items of the two lists. Two atoms return 0f.

q)23 -11 35 0 cov 42 21 73 39
411.25

The function cov is equivalent to,

avg[x*y]-avg[x]*avg y

A.12 cross

The binary cross takes atoms or lists as arguments and returns their Cartesian product – that is, the set of all pairs drawn from the two arguments.

q)1 2 cross `a`b`c
1 `a
1 `b
1 `c
2 `a
2 `b
2 `c

Tip

You can also apply cross to dictionaries and tables.

The function cross is equivalent to,

{raze x,\:/:y}

A.13 cut

The binary cut is an instance of Cut that takes a list of integer indices x and a list y. It returns the list obtained by splitting y at the positions in x.

Tip

If the initial item of x is not 0, the first sublist split out is dropped.

q)0 2 5 7 cut 10 20 30 40 50 60 70 80 90 100
10 20
30 40 50
60 70
80 90 1000

q)2 5 7 cut 10 20 30 40 50 60 70 80 90 100
30 40 50
60 70
80 90 100 30 40 50

When x is a strictly positive integral atom, y is split at indices that are multiples of x.

q)2 cut 10 20 30 40 50 60 70 80 90 100
10 20
30 40
50 60
70 80
90 100
q)3 cut 10 20 30 40 50 60 70 80 90 100
10 20 30
40 50 60
70 80 90
,100

A.14 _ Drop, Cut

The binary Cut _ has several forms, depending on the types of its parameters. See also Drop and cut.

Tip

When _ is used infix, surround it with whitespace to avoid it getting mixed up with variable names, since _ is a valid q name character.

When x is an integral atom and y is a list, _ is called Drop and the result is y with x items removed from the head if x is positive and from the tail if x is negative.

q)2 _ 10 20 30 40 50 60 70 80 90 100
30 40 50 60 70 80 90 100
q)-2 _ 10 20 30 40 50 60 70 80 90 100
10 20 30 40 50 60 70 80

When x is a list of integers and y is a list, it is called Cut and returns the list obtained by splitting y at the positions in x. This is the same behavior as cut for this signature.

Tip

If the initial item of x is not 0, the first sublist split out is dropped.

q)0 2 5 7 _ 10 20 30 40 50 60 70 80 90 100
10 20
30 40 50
60 70
80 90 100
q)2 5 7 _ 10 20 30 40 50 60 70 80 90 100
30 40 50
60 70
80 90 100

When y is a dictionary and x is a list of key values whose type matches y, it is called Drop and the result is a dictionary obtained by removing the specified key-value pairs from the target. Since tables and keyed tables are dictionaries, _ applies to them by extension.

q)`a`c _ ([a:10; b:20; c:30])
b| 20

q)`c1`c2 _ ([] c1:`a`b; c2:10 20; c3:1.1 2.2)
c3
---
1.1
2.2
q)([] k:`a`c) _ ([k:`a`b`c] v:10 20 30)
k| v
-| --
b| 20

Tip

The parameter x must be a list, so a single value for the first parameter in this form must be enlisted.

q)(enlist `b) _ ([a:10; b:20; c:30])
a| 10
c| 30

When x is a list or a dictionary and y is an atom representing an index or key, it is called Drop and the result is obtained by deleting the specified item from (a copy of) x.

q)01 102 103 104 105 _ 2
1 102 104 105

q)([a:10; b:20; c:30]) _ `b
a| 10
c| 30
                            ^
q)([k:101 102 103] c:`one`two`three) _ 102
k | c
---| -----
101| one
103| three

Note

The last overload cannot accept a list of indices to be dropped. Why?

A.15 deltas

The uniform deltas is -':, which returns the difference of each item in a numeric list with its predecessor.

q)deltas 1 2 3 4 5
1 1 1 1 1
q)deltas 96.25 93.25 58.25 73.25 89.50 84.00 84.25
96.25 -3 -35 15 16.25 -5.5 0.25

Tip

If you are looking to bound the absolute difference between successive elements, the second example shows that the initial item of the result will be troublesome.In this case, you can use,

deltas0:{first[x] -': x}

In our example above,

q)deltas0 96.25 93.25 58.25 73.25 89.50 84.00 84.25
0 -3 -35 15 16.25 -5.5 0.25

A.16 dev mdev

The aggregate dev returns the float standard deviation of a numeric list – the square root of the variance.

q)dev 1000?100.
29.40271

The function (dev) is equivalent to,

{sqrt var x}

The binary mdev takes a positive integer x and returns the x-wide moving standard deviation of the numeric list y. At each position in y, it computes the standard deviation of the x preceding items, or as many as are available in the moving window up to that position. It excludes internal nulls from the calculation.

q)3 mdev 10 20 30 40 50
0 5 8.164966 8.164966 8.164966
q)3 mdev 10 20 30 0N 50
0 5 8.164966 5 10

A.17 differ

The uniform differ is

"b"$ not (~':)

It asks if each item in a list is not identical to its predecessor. The item at index 0 in the result is always 1b.

q)differ 0 1 1 2 3 2 2 2 4 1 1 3 4 4 4 4 5
11011100110110001b

q)differ "mississippi"
11101101101b

q)differ (1 2; 1 2; 3 4 5)
101b

One use of differ is to locate runs of repeated items in a list.

q)L:0 1 1 2 3 2 2 2 4 1 1 3 4 4 4 4 5
q)nd|next nd:not differ L
01100111011011110b

A.18 distinct

The unary distinct returns the unique items in its list argument in order of first occurrence. Note that it does not apply the `u# attribute. (The Q Gods explain that this would incur the overhead of creating a hash table which you likely don't want for a garden variety call to distinct.

q)distinct 1 2 3 2 3 4 6 4 3 5 6
1 2 3 4 6 5

Following is a test for existence of duplicates.

{count[x]=count distinct x}

Since a table is a list of records, distinct effectively removes duplicate rows. All fields' records must be identical for them to be considered identical.

q)distinct ([]a:1 2 3 2 1;
b:`washington`adams`jefferson`adams`washington)
a b
------------
1 washington
2 adams
3 jefferson

q)distinct ([]a:1 2 3 2 1;
b:`washington`adams`jefferson`adams`wasington)
a b
------------
1 washington
2 adams
3 jefferson
1 wasington

A.19 enlist

The multivalent enlist returns a list whose items comprise its arguments. The most common use is to create a singleton list from an atom. Unlike user-defined functions, the number of arguments to enlist is not restricted to eight.

Important

To save space, the display of an enlisted item uses , which is the k form of enlist.

q)enlist 42
,42

q)count enlist 10 20 30
1

q)enlist[1;2;3;4;5;6;7;8;9;10]
1 2 3 4 5 6 7 8 9 10

/ a list with one column dictionary *is* a table
q)enlist ([c1:`a; c2:100])
c1 c2
------
a 100

Tip

Since amend in place does not require its target to be previously defined, here is a hack to create and assign a singleton atom.

q)x,:42
q)x~enlist 42
1b

A.20 eval and reval

Both eval and reval evaluate a list representing a valid q parse tree; the same code is used in the q interpreter. Such a list can be produced using parse on a string containing a valid q expression, or by hand – if you know what you're doing. A full discussion of parse trees is beyond the scope of this tutorial.

q)parse "a:6*7"
:
`a
(*;6;7)

q)eval parse "a:6*7"
42
q)a
42

/ create parse tree by hand
q)eval (+;1;(*;6;7))
43

The reval function is the same as eval except that it bocks any and all behavior that could be potentially destructive. Specifically it behaves as if command-line options -u 1 and -b were active; it also blocks all system calls which change state. See the documentation on the KX Documentation website for details.

A.21 except

The binary except takes a list (or dictionary) x and an atom or list y that is of the same type as x and returns the items in x that are not in y. Otherwise put, it excludes the items of y from x. The returned items are in the order of their first occurrence in x.

q)1 2 3 4 3 2 except 2
1 3 4 3

q)string[2025.01.01] except "."
"20250101"

q)([a:10; b:20; c:30; d:40]) except ([a:10; d:40])
20 30

q)([] c1:`a`b`c`d; c2:10 20 30 40) except ([] c1:`a`d; c2:10
40)
c1 c2
-----
b 20
c 30

Tip

The result of (except) is always a list.

A.22 exit

Use exit with a integer parameter to terminate the q process immediately, returning the parameter to the OS. It is blocked during (reval) or with -u on the command line.

Important

There is no prompt for confirmation.

A.23 ^ fill and Fills

The binary fill ^ takes an atom x and a list y. It returns (a copy of) y having null values replaced with x.

q)42^1 2 3 0N 5 0N
1 2 3 42 5 42
q)"_"^"Now is the time"
"Now_is_the_time"

q)`NA^`First`Second``Fourth
`First`Second`NA`Fourth

Fill is atomic in the second parameter.

q)42^(1;0N;(100;200 0N))
1
42
(100;200 42)

Like all functions, fill operates on the values of a dictionary.

q)42^([a:100; b:0N; c:200; d:0])
a| 100
b| 42
c| 200
d| 0
q)0^([]c1:1.0 2.0 0n; c2:0N 2 0N)
c1 c2
-----
1 0
2 2
0 0

The uniform fills is ^\, which fills forward, meaning that null items are replaced with preceding non-nulls.

q)fills 1 0N 3 0N 0N 5
1 1 3 3 3 5
q)fills `x``y```z
`x`x`y`y`y`z
q)update fills c2 from ([] `a`b`c`d`e`f; c2:1 0N 3 0N 0N 5)
x c2
----
a 1
b 1
c 3
d 3
e 3
f 5

Tip

If you need to fill initial nulls, use the corresponding binary form of ^\.

q)fills 0N 0N 3 0N 5
0N 0N 3 3 5

q)0 ^\ 0N 0N 3 0N 5
0 0 3 3 5

A.24 ? Find

This binary overload of ? called Find takes a list x and an atom y of the same type as x. It returns the index of the first occurrence of y in x or the count of x if it is not found. It is atomic in y.

Zen Moment

Viewing a list or dictionary as a mapping, find is the (partial) inverse mapping.

The simplest case is when y is an atom.

q)100 99 98 87 96 98?98
2
q)`one`two`three?`four
3
q)"Now is the time"?"the" / strings are just lists of char
7 8 9

Tip

The first example demonstrates that Find returns only the index of the first occurrence of y.

To find the indices of all occurrences you could use,

q){where x=y}[100 99 98 87 96 98;98]
2 5
Find also works on general lists as long as they conform, although if you need this you should probably consider redesigning your program.

q)(1 2; 3 4; `a`b)?`a`b
2
q)((0;1 2);3 4;5 6)?5 6 / uh oh
2

Find can also take a dictionary as x and a dictionary value as y. It returns the first key that maps to value. It is atomic in y.

q)([a:10;b:20;c:30;d:40])?10
`a
q)([a:10;b:20;c:30;d:40])?10 30
`a`c

By extension, Find applies to tables and keyed tables.

q)([] c1:`a`b`c; c2:10 20 30)?([c1:`b;c2:20])
1
q)([] c1:`a`b`c; c2:10 20 30)?(`b;20)
1
q)([k:1 2 3] c:100 101 102)?101
k| 2

A.25 flip

Use flip to transpose a rectangular list, column dictionary or table.

When x is a rectangular list, the items are rearranged, effectively reversing the first two indices in indexing. For example,

q)show m:(1 2 3;10 20 30)
1 2 3
10 20 30

q)flip m
1 10
2 20
3 30

When flip converts a column dictionary to a table and vice versa, no data is actually rearranged. Only column indexing is reversed.

q)d:([c1:`a`b`c; c2:10 20 30])
q)t:([] c1:`a`b`c; c2:10 20 30)
q)d[`c1;2]~t[2;`c1]
1b

A.26 getenv setenv

Use getenv with a symbol naming an OS environment variable to return the value (if any) of that environment variable as a string.

q)getenv `SHELL
"/bin/zsh"

The binary setenv takes x a symbol name of an OS environment variable and a string y. It calls the underlying OS to set the environment variable named in x to the specified y.

q) `FOO setenv "test"
q)getenv `FOO
"test"

A.27 group

Apply group to a list x to return a dictionary in which each distinct item in x is mapped to the indices of its occurrences in x. The keys of the result are in the order of their first appearance in x.

q)group "i miss mississippi"
i| 0 3 8 11 14 17
| 1 6
m| 2 7
s| 4 5 9 10 12 13
p| 15 

q)count each group "i miss mississippi"
i| 6
| 2
m| 2
s| 6
p| 2

A.28 gtime ltime

The atomic gtime converts local time to UTC time.

q).z.P
2025.07.12D08:18:10.378409000
q)gtime .z.P
2025.07.12D12:18:14.878884000

The atomic ltime converts UTC time to local time.

q).z.P
2025.08.25D15:36:26.432993000
q)ltime .z.p
2025.08.25D15:36:35.511399000
q).z.p
2025.08.26D01:36:40.355924000

A.29 iasc idesc Grade

The uniform iasc takes a list or a dictionary. The result is a list of the indices/keys of x in the order needed to sort it. Otherwise put, composing x with the result of iasc sorts in ascending order.

q)L:30 70 20 80 10 90
q)show I:iasc L
4 2 0 1 3 5
q)show S:L I
10 20 30 70 80 90
q)L~S iasc I
1b

q)d:([c:30;a:10;b:20])
q)iasc d
`a`b`c
q)d iasc d
10 20 30
q)(iasc d)#d
a| 10
b| 20
c| 30

This is useful when you want to use one list to control the order of others – e.g., manual sort on the serialized columns of a splayed table (see 14.2).

Zen Moment

The composite iasc iasc provides the list of indices that transforms the sorted entity back to the original.

The uniform idesc takes a list or a dictionary. The result of idesc is a list of the indices/keys of x in the order needed to sort its argument. Otherwise put, composing x with the result of idesc sorts in descending order.

q)L:30 70 20 80 10 90
q)show I:idesc L
5 3 1 0 2 4
q)show S:L I
90 80 70 30 20 10
q)S iasc I
30 70 20 80 10 90

q)idesc d
`c`b`a
q)d idesc d
30 20 10
q)(idesc d)#d
c| 30
b| 20
a| 10

This is useful when you want to use one list to control the order of others – e.g., manual sort on the serialized columns of a splayed table (see 14.2).

Zen Moment

The composite iasc idesc provides the list of indices that transforms the sorted entity back to the original.

A.30 identity

The unary :: is the identity function – i.e., it returns its argument.

q)::[42]
42
q)(::) `Zaphod
`Zaphod

Tip

The identity function cannot be used naked with juxtaposition or @. You must either enclose it in parentheses or enclose its argument in square brackets. This is to disambiguate this use from others.

A.31 in

The binary function in is atomic in x and takes an atom or list y. It returns a boolean indicating whether source appears in target. The comparison is strict with regard to type. When x is a list and y is a list of lists of the same type as x, it treats the lists of y as irreducible for the comparison.

q)42 in 0 6 7 42 98
1b
q)4 in 42
0b
q)"4" in "42"
1b
q)"cat" in "abcdefg"
110b
q)"cat" in ("dog"; "cat"; "parrot")
1b

A.32 inter union

The binary inter returns the items in x that occur in y.

q)1 2 3 4 inter 3 4 4 5
3 4

Note

Lists differ from sets in that they are ordered and allow duplicates. So inter is not the list equivalent of set intersection, despite of what the KX web site says. You can obtain this with distinct.

q)1 2 3 1 4 inter 4 1 4
1 1 4
q)distinct 1 2 3 1 4 inter 4 1 4
1 4

Tip

You can use inter to find common records in tables having identical schemas.

q)([] c1:`a`b`c; c2:10 20 30) inter ([] c1:`c`d; c2:30 40)
c1 c2
-----
c 30

The binary union returns the list equivalent of the set theoretic union of its two list parameters. The result has the distinct items of x,y in order of their first appearance.

q)1 1 2 3 union 2 2 3 4
1 2 3 4
q)"a good time" union "was had by all"
"a godtimewshbyl"

Since a table is a list of records, union can be used to perform the analogue of SQL UNION for tables having the same schemas. Observe that this is different from join , since duplicate records are eliminated.

q)([] c1:`a`b`c; c2:10 20 30) union ([] c1:`b`c`d; c2:20 300 400)
c1 c2
------
a 10
b 20
c 30
c 300
d 400

Tip

Use uj for tables that do not have matching schemas – see 9.9.7.

A.33 inv

Use inv to return the inverse of a float matrix. An integer matrix must be cast to float.

q)inv (1.1 2.1 3.1; 2.3 3.4 4.5; 5.6 7.8 9.8)
-8.165138 16.51376 -5
12.20183 -30.18349 10
-5.045872 14.58716 -5

Note

Since q3.6 inv uses LU (lower-upper) decomposition.

A.34 , Join

The binary Join , appends y to x. When both operands are either lists or atoms, the result concatenates y to x.

q)1,2
1 2
q)1 2 3,4
1 2 3 4
q)1 2,3 4
1 2 3 4

The result is a general list unless all items are of homogeneous type.

q)1 2 3,4.0
1
2
3
4f

When both x and y are dictionaries, the result is the merge of the y into x using upsert semantics. Otherwise put, assignments in the second parameter prevail over those in the first.

q)([a:10;b:20;c:30]),([c:300;d:400])
a| 10
b| 20
c| 300
d| 400

By extension, you can use , on tables and keyed tables with identical schemas where it is analogous to a union join in SQL.

q)([] c1:`a`b;c2:10 20),([]c1:1#`s; c2:30)
c1 c2
-----
a 10
b 20
s 30

Important

You can use ,: to append to a list in place, meaning no copy is made. This also has the advantage that the variable being assigned does not have to be defined before first use. In a fresh q session,

q)x
'x
[0] x
^
q)x,:42
q)x,:100 200 300
We note that (,:) does not allow mixing types unless the list is already a general list.

A.35 key

The key operator vies for the title of most overloaded q operator. Its eponymous action is to return the key of a dictionary, including the special case of the key portion of a keyed table. It can be applied by value or name.

q)key ([a:10;b:20;c:30])
`a`b`c
q)key kt:([k:`a`b`c] v:10 20 30)
k
-
a
b
c
q)key `kt
_

A context – i.e. the content of a namespace – is a dictionary, so key applied to the symbolic name will return the names of its constituents. Observe that contexts below the root all have an initial null symbol. In a fresh q session,

q)key `.
`symbol$()
q)a:42
q)key `.
,`a
q).jab.a:42
q)key `.jab
``a
To list all current namespaces, apply key to the null symbol.

q)key `
`q`Q`h`j`o`jabkey

You can use key to determine if a variable exists in the current namespace.

q)x
'x
q)()~key `x / tests if x exists in current namespace
1b
q)x:42
q)key `x
`x

Given a simple list, key returns the symbolic name of its type.

q)key 10 20 30
`long
q)key "so long"
`char

Given an enumerated entity, key returns the name of its enumeration domain. This applies to foreign key columns, where it returns the name of the target keyed table.

q)key `sym?`a`b`a`c`a
`sym
q)key `sym1?`a`b`a`c`a
`sym1_
q)kt:([k:`a`b`c] v:10 20 30)
q)t:([] k:`kt$`a`b`a`b`a; v: 10 20 30 49 59)
q)key t[`k]
`kt

Given an I/O handle corresponding to a directory, key returns a list of the symbolic names of entities in that directory, including hidden files.

q)\ls q
"k4.lic"
"kc.lic.old"
"m64"
"q.k"
"sp.q"
q)key `:q
`s#`.DS_Store`k4.lic`kc.lic.old`m64`q.k`sp.q

Tip

An empty directory returns an empty list of symbols whereas a non-existent directory returns an empty general list. This provides a simple test for the existence of a directory.

q)\ls Q4M/jab
ls: Q4M/jab: No such file or directory
q)()~key `:Q4M/jab
1b
q)\mkdir Q4M/jab
q)key `:Q4M/jab
`s#`symbol$()

Given an I/O handle corresponding to a file, key returns the symbolic file name if the file exists and the general empty list () if it does not. As above, this provides a test for existence of the file.

q)`:Q4M/trade.q 0: enlist "dummy"
`:Q4M/trade.q
q)key `:Q4M/trade.q
`:Q4M/trade.q
q)()~key `:Q4M/quote.q
1b

Last, but not least, key also acts as a synonym of til.

q)key 10
0 1 2 3 4 5 6 7 8 9

A.36 like

The binary like performs matching of a string (or symbol) x according to the pattern in the string (or symbol) y. It returns a boolean result indicating whether y is matched. The pattern is expressed as a mix of regular characters and special formatting characters.

The special chars are ?, *, the pair [ and ], and finally ^ that is enclosed in square brackets. The special char ? represents an arbitrary single character in the pattern.

q)"fan" like "f?n"
1b
q)"fun" like "f?n"
1b
q)"foP" like "f?p"
0b

The special char * represents an arbitrary sequence of characters in the pattern.

Note

As of this writing (July 2025), only a single occurrence of * is allowed in the pattern, except that a * can occur at both the beginning and end of the pattern.

q)"how" like "h*"
1b
q)"hercules" like "h*"
1b
q)"wealth" like "*h"
1b
q)"flight" like "*h*"
1b
q)"Jones" like "J?ne*"
1b
q)"Joynes" like "J*ne*"
'nyi

The special character pair [ and ] encloses a sequence of alternatives for a single character match.

q)"flap" like "fl[ao]p"
1b
q)"flip" like "fl[ao]p"
0b
q)"459-0609" like "[0-9][0-9][0-9]-0[0-9][0-9][0-9]"
1b
q)"459-0609" like "[0-9][0-9][0-9]-1[0-9][0-9][0-9]"
0b

The special character ^ is used in conjunction with [ and ] to indicate that the enclosed sequence of characters is disallowed. For example, to test whether a string ends in a non-numeric character,

q)"M26d" like "*[^0-9]"
1b
q)"Joe999" like "*[^0-9]"
0b

Enclose a special char in square brackets to escape it as a normal char.

q)"a_c" like "a*"
1b
q)"a_c" like "a[*]"
0b
q)"a*c" like "a[*]c"
1b

As usual with dictionaries, like matches on the values.

q)([a:`nuba;b:`devi;c:`lorenzo]) like "devi"
a| 0
b| 1
c| 0

A.37 lower upper

The atomic lower takes a char, string or symbol x and returns the result of converting all alpha characters in x to lower case.

q)lower `A
`a
q)lower "a Bc42De?"
"a bc42de?"

The atomic (upper) takes a char, string or symbol x and returns the result of converting any alpha characters to upper case.

q)upper `a
`A
q)upper `a`b
`A`B
q)upper "a Bc42De"
"A BC42DE"

Note

Only letters in the ASCII range are affected.

q)-1 upper "árvíztűrő"
áRVíZTűRő

A.38 lsq

The binary matrix operator lsq takes float matrix parameters A and B and returns the matrix X that solves the following matrix equation, where · is matrix multiplication.

A = X·B
Integer matrices must be cast to float.

For example,

q)A:(1.1 2.2 3.3;4.4 5.5 6.6;7.7 8.8 9.9)
q)B:(1.1 2.1 3.1; 2.3 3.4 4.5; 5.6 7.8 9.8)
q)A lsq B
1.211009 -0.1009174 2.993439e-12
-2.119266 2.926606 -3.996803e-12
-5.449541 5.954128 -1.758593e-11

We note that lsq  solves a normal equations matrix via Cholesky decomposition – solving systems is more robust than matrix inversion and multiplication. Thus although lsq is theoretically equivalent to computing the inverse explicitly, the results do not agree within multiplicative tolerance due to different methods used.

q)A mmu inv B
1.211009 -0.1009174 7.105427e-15
-2.119266 2.926606 0
-5.449541 5.954128 7.105427e-15

q)(A lsq B)=A mmu inv B
000b
000b
000b

A.39 max maxs mmax

The aggregate max is |/, which applies | cumulatively across a list of items of underlying numeric type and returns the final result. It is the same as (any) on a boolean list. Nulls are ignored, except that if all the items of x are null, the result is negative infinity.

q)max 100100b
1b
q)max 10?2025.01.01
2017.09.06

The uniform maxs is |\, which applies | across a list of comparable items and returns the intermediate results. Nulls are ignored, except that if all the items of x are null, the result is negative infinity.

q)maxs 1 2 5 4 10
1 2 5 5 10
q)maxs "Beeblebrox"
"Beeelllrrx"

The binary mmax takes a positive integer x and returns the x-wide moving maximum of the numeric list y. At each position in y, it computes the maximum of the x preceding items, or as many as are available in the moving window up to that position. It excludes internal nulls from the calculation.

q)3 mmax 20 10 30 50 40
20 20 30 50 50
q)3 mmax 20 10 30 0N 40
20 20 30 30 40

A.40 md5

The unary function md5 computes the MD5 (Message Digest Algorithm 5) hash of a string as a list of 16 bytes.

q)md5 "Life the Universe and Everything"
0x0e9a5631e4db880d43808504d05348df

From the KX Documentation website: MD5 is a widely used, Internet standard (RFC 1321), hash function that computes a 128-bit hash, commonly used to check the integrity of files. It is not recommended for serious cryptographic protection, for which strong hashes should be used.

A.41 med

The aggregate med returns the float median of a numeric list.

q)med 1000?1000.
509.5941
q)med 1000000?1000000

The function med is equivalent to,

{avg x (iasc x)@floor .5*-1 0+count x,:()}

A.42 min mins mmin

The aggregate min is &/, which applies & cumulatively across a list of underlying numeric type and returns the final result. It is the same as and for a boolean list. Nulls are ignored, except that if the argument has only nulls, the result is infinity. The minimum of an atom is itself.

q)min 100?100
1
q)min 100100b
0b

The uniform mins is &\, which computes the cumulative minimums of a list of comparables and returns the intermediate results. Nulls are ignored, except that if the argument has all nulls, the result is infinity.

q)mins 10 4 0N 1 2
10 4 4 1 1
q)mins "the cat"
"theecaa"

The binary mmin takes a positive integer x and returns the x-wide moving minimum of the numeric list y. At each position in y, it computes the minimum of the x preceding items, or as many as are available in the moving window up to that position. It excludes internal nulls from the calculation.

q)3 mmin 20 10 30 50 40
20 10 10 10 30

A.43 $ mmu matrix multiply

The binary matrix multiplication mmu returns the matrix product of its two float vector or matrix parameters, which must be of the correct shapes. It reduces to dot product on vectors. Integer matrices must be cast to float.

q)m1:(1.1 2.2 3.3;4.4 5.5 6.6;7.7 8.8 9.9)
q)m1 mmu flip m1
16.94 38.72 60.5
38.72 93.17 147.62
60.5 147.62 234.74
q)m2:`float$(0 0 1; 0 1 0; 1 0 0)
q)m2 mmu m2
1 0 0
0 1 0
0 0 1
q)1 2 3f mmu 1 2 3f
14f

Note

The $ operator is overloaded to yield matrix multiplication when its parameters are float vectors or matrices.

q)m2 $ m2
1 0 0
0 1 0
0 0 1

A.44 next prev xprev

The uniform next returns its list x shifted one position to the left with a null (or empty list for nested lists) in the last item. Otherwise put, each item in x is replaced with its successor.

q)next 1 2 3 4 5
2 3 4 5 0N
q)next (1 2; 3 4 5; 6 7)
3 4 5
6 7
`long$()

The uniform prev returns a list x shifted one position to the right with a null (or empty list in the case of a nested list) in the first item. Otherwise put, each item in x is replaced with its predecessor.

q)prev 1 2 3 4 5
0N 1 2 3 4
q)prev (1 2; 3 4 5; 6 7)
`long$()
1 2
3 4 5

The binary xprev takes an integer x and shifts the list y by x positions. When x is 0 or positive, the shift is forward; otherwise it is backward. The beginning – respectively end – of the list is filled with x null items (or empty list items for nested y).

q)2 xprev 10 20 30 40 50
0N 0N 10 20 30
q)-2 xprev 10 20 30 40 50
30 40 50 0N 0N
q) 
q)2 xprev (1 2 3; 4 5; enlist 6; 7 8) 
`long$() 
`long$() 
1 2 3 
4 5 
3 
4 5   

A.45 null

The atomic function null tests its argument for null value. It is preferred to testing for equality as it works for all types.

q)null 42
0b
q)null 0n
1b
q)null "Now is the time"
000100100010000b
q)null (1; 3 0N; ((5; 0N); 7))
0b
01b
(01b;0b)
q)

A common idiom combines where with null to obtain the positions of the null items in a list.

q)where null 1 2 3 0N 5 0N
3 5

Because null is atomic, it picks out null values in all fields of a table.

q)null ([] c1:`a``b; c2:0N 20 30)
c1 c2
-----
0 1
1 0
0 0

This can be used to identify null columns.

q)where all null ([] c1:`a`b`c; c2:0n 0n 0n; c3:10 0N 30)
,`c2

A.46 or any

The binary or is the same as | for people who like typing extra characters.

q)1b or 0b
1b
q)42 or 43
43

The aggregate any is |/, which applies | cumulatively across a numeric list and returns the boolean result. For people who like typing extra characters.

q)any 100100b
1b
q)any null til 10
0

A.47 over scan

The higher-order function over is a convenience function that renames the unary form of / for people who like typing extra characters.

Note

Symbolic operands must be parenthesized.

q){x+2*y} over 2 3 5 7
32
q)
q)(+) over 2 3 5 7
17

The higher-order function scan is a convenience function that renames the unary form of \ for those who like to type more characters.

Note

Symbolic operators must be parenthesized.

q){x+2*y} scan 2 3 5 7
2 8 18 32
q)(+) scan 2 3 5 7
2 5 10 17

A.48 parse

Use parse to produce a q parse tree from a string representing a q expression. Applying eval to the result of parse effectively evaluates the expression. The composition of eval after parse is essentially the q interpreter. A discussion of q parse trees is beyond the scope of this tutorial.

q)parse "7*4+2"
*
7
(+;4;2)
q)eval parse "7*4+2"
42

Note

It is useful to apply parse to a string containing a query template for the purpose of expressing the query in functional form. The result will often include k code but it is usually recognizable and you can use it in functional form. The constraint portion of the resulting parse tree will contain an extra level of nesting displayed in the k form ,,. You must remove one level for the functional form.

q)t:([]c1:`a`b`c; c2:10 20 30)
q)parse "select c2:2*c2 from t where c1=`c"
?
`t
,,(=;`c1;,`c)
0b
(,`c2)!,(*;2;`c2)

q)?[`t; enlist (=;`c1;enlist `c); 0b; (enlist `c2)!enlist (*;2;`c2)]
c2
--
60

A.49 peach

A full discussion of how q handles concurrency and distributed processing is beyond the scope of this text. We provide a description of the essential features as of this writing (July 2025) and refer the reader to "Parallel processing" on the KX Documentation website for up-to-date details.

Concurrency in q uses two basic constructs: peach and secondary threads (secondaries). The maximum number of secondaries are declared to the q process at startup and the actual number can be set at runtime from the console with \s. The function peach is a "parallel" version of each that applies a function over a list by distributing the items of the list across secondaries.

While each and peach perform the same computation and return the same result, their performance can be drastically different. If q is not started with secondaries, peach reverts to each, meaning function application across a list occurs sequentially in the main q thread.

Note

For those who are not symbolically challenged, for a unary function f, we point out that f each is actually f' and f peach is actually f':.

A.49.1 Threads

When q is started with -s n, the q process automatically spawns n secondary threads in addition to the main thread. When you subsequently use (peach) to apply a function – i.e., map it across a list – the application is automatically distributed across the secondary threads for you.

The result of the application is the same as if you had used (each) but if q is running on a machine with multiple cores, you should expect a speedup, depending on what the function does, how secondary threads are allocated to cores and the load on your machine.

For example, on the author's laptop that has 10 cores, we find that the benefit of multiple secondaries for evaluating a compute-intensive calculation on a list of 8 items plateaus at 8 secondaries.

jaborror@unalome ~ % q
q)\t {sum exp x?1.0} each 8#1000000
51
q)\t {sum exp x?1.0} peach 8#1000000
51

jaborror@unalome ~ % q -s 2
q)\t {sum exp x?1.0} each 8#1000000
42
q)\t {sum exp x?1.0} peach 8#1000000
27

jaborror@unalome ~ % q -s 4
q)\t {sum exp x?1.0} each 8#1000000
31
q)\t {sum exp x?1.0} peach 8#1000000
16

jaborror@unalome ~ % q -s 8
q)\t {sum exp x?1.0} each 8#1000000
28
q)\t {sum exp x?1.0} peach 8#1000000
9

jaborror@unalome ~ % q -s 10
q)\t {sum exp x?1.0} each 8#1000000
29
q)\t {sum exp x?1.0} peach 8#1000000
9

In order to maintain consistency during concurrent application, the following restriction is placed on function evaluation within secondary threads.

Code executed in a secondary thread cannot update global variables – i.e., a function can only update local variables.

Warning

If you use a timer on the main thread or other tricks to update globals that are read by secondary threads, you are cruising for a bruising. While these updates are locked, there is no notion of a transaction with attendant rollback. It is unlikely that your function executing on the timer is atomic at the hardware level. Should it fail mid-flight, you should expect the workspace would be in an inconsistent state with no built-in recovery mechanism.

A.49.2 Workload distribution

From the KX Documentation website: In q4.1t 2024.01.04, peach Workload Distribution methodology changed to dynamically redistribute workload and allow nested invocation. The limitations on nesting have been removed, so peach (and multi-threaded primitives) can be used inside peach. To facilitate this, round-robin scheduling has been removed. Even though the initial work is still distributed in the same manner as before for compatibility, the workload is dynamically redistributed if a thread finishes its share before the others.

See the KX Documentation website or the latest documentation on peach processing.

A.50 prd prds

The aggregate prd is */, which applies * cumulatively across a numeric list and returns the final result.

Tip

Note the missing o in the name.

q)prd 1+til 5
120
q)prd 1+til 5
120
q)prd 10?100.
5.677673e+16

It is possible to apply prd to a nested list provided the sublists conform. In this case, the result conforms to the sublists and the product is calculated recursively on the sublists.

q)prd (1 2; 100 200; 1000 2000)
Z100000 800000

The uniform prds is *\, which applies * cumulatively across a list of numeric type and returns the intermediate results.

Tip

Note the missing o in the name.

q)prds 1+til 5
1 2 6 24 120

A.51 prior

The function prior is a convenience function that renames the unary form of ': for people who like typing extra characters.

Tip

You likely still won't be happy with the initial item of the result.

q)(-) prior 10 11 12 13 14
10 1 1 1 1

A.52 rank

The uniform rank returns the sort order of each item in a list of comparables.

q)rank 50 20 30 10 40
4 1 2 0 3
q)iasc iasc 50 20 30 10 40
4 1 2 0 3

q)rank `x`a`b`z`c
3 0 1 4 2

A.53 ratios

The uniform ratios is %':, which applies % across a list of numeric type and returns the intermediate results. That is, it returns the ratio of each item with its predecessor.

q)ratios 10 20 30 40 50
10 2 1.5 1.333333 1.25

Tip

The initial item in the result is not 1.0. If you are looking to bound the relative difference between successive elements, this example shows that the initial item of the result will be troublesome.

In this case, you can use,

ratios1:{first[x] %': x}

For our example above,

)ratios1:{first[x] %': x}
q)ratios1 10 20 30 40 50
1 2 1.5 1.333333 1.25

A.54 raze

The unary raze is ,/. It effectively eliminates the top-most level of nesting from a list by joining – i.e., concatenating – across it.

q)raze (1 2 3;3; 4 5)
1 2 3 3 4 5

Observe that raze only removes the top-most level of nesting but you can use each repeatedly to reach deeper levels. Also you can flatten the entire structure of a nested list with the iterated raze/. (This is a good q test question).

q)raze ((1 2;3 4);(5;(6 7;8 9)))
1 2
3 4
5
(6 7;8 9)
q)raze each ((1 2;3 4);(5;(6 7;8 9)))
1 2 3 4
(5;6 7;8 9)
q)(raze each) each ((1 2;3 4);(5;(6 7;8 9)))
1 2 3 4
,5 6 7 8 9
q)raze/[((1 2;3 4);(5;(6 7;8 9)))]
1 2 3 4 5 6 7 8 9

A.55 reverse

The uniform function reverse inverts the item order of its argument.

q)reverse 1 2 3 4 5
5 4 3 2 1
q)reverse ([a:10; b:20; c:30])
c| 30
b| 20
a| 10
q)reverse ([] c1:`a`b`c; c2:10 20 30)
c1 c2
-----
c 30
b 20
a 10
q)reverse ([k:`a`b`c] v:10 20 30)
k| v
-| --
c| 30
b| 20
a| 10

For nested entities, the reversal takes place only at the topmost level but you can use (each) to reach lower levels.

q)reverse (1 2 3;"abc";`Four`Score`and`Seven)
`Four`Score`and`Seven
"abc"
1 2 3
q)reverse each (1 2 3;"abc";`Four`Score`and`Seven)
3 2 1
"cba"
`Seven`and`Score`Four

A.56 rotate

The uniform binary rotate takes an integer x and returns the result of rotating y by x positions. The rotation is to the left for positive x and to the right for negative x. When x is 0, it returns y.

q)2 rotate 1 2 3 4 5
3 4 5 1 2
q)22 rotate 1 2 3 4 5
3 4 5 1 2

A.57 rsave rload

The convenience function rsave takes a symbolic directory handle and splays to it a table from a variable with the same name as the directory. The preferred way to do this is with set, which allows the directory name to be specified.

Note

Do not include the trailing / in the directory handle.

q)t:([] c1:10 20 30; c2:1.2 2.2 3.3)
q)rsave `:db/t
`:db/t/
q)`:db/t1/ set t
`:db/t1/

The convenience function rload takes a symbolic directory handle and loads a splayed table into a variable with the same name as the splayed directory. The usual way to do this is with get, whose result can be assigned to an arbitrary variable.

Note

Do not include the trailing / in the directory handle.

q)`:db/t/ set ([] c1:10 20 30; c2:1.2 2.2 3.3)
`:db/t/
q)rload `:db/t
`t
q)count t
3
q)t1:get `:db/t
q)count t1
3

A.58 scov

The binary scov returns the statistical covariance of two conforming numeric lists.

q)2 3 5 7 scov 4 3 0 2
-2.416667

It is equivalent to:

{cov[x;y]*count[x]%-1+count x}

A.59 sdev

The aggregate sdev returns the statistical standard deviation of its numeric list argument.

q)sdev 10 343 232 55
155.1322

It is equivalent to:

{sqrt var[x]*count[x]%-1+count x}

A.60 sin asin

The atomic sin takes a float and returns its mathematical sine.

q)pi:3.141592653589793
q)sin pi
1.224647e-16
q)sin pi%2
1f

The atomic asin is the mathematical inverse of sin. For a float x between -1 and 1, asin returns the float between -π/2 and π/2 whose sine is x.

q)asin 0
0f
q)asin 1.414213562373095%2
0.7853982
q)asin 1
1.570796
q)asin -1
-1.570796

A.61 ss ssr

The binary ss, for "string search", performs similar pattern matching as like against the string x, looking for matches with y. The result is a list containing the position(s) of the matches of y in x.

q)ss["Now is the time for all good men to come to";"me"]
13 29 38
q)"fun" ss "f?n"
,0

If no matches are found, an empty list of long is returned.

q)ss["ab";"z"]
`long$()

Note

You cannot use * to match with ss.

The ternary ssr, for "string search and replace", extends the capability of ss with replacement. The result is a string based on the string x in which all matches of the string y are replaced with the string z.

q)ssr["suffering succotash";"s";"th"] / Sylvester is from Madrid
"thuffering thuccotathh"

Tip

A useful idiom is ssr/ to replace multiple items.

q)(ssr/)["results_%div_%dept.csv"; ("%div";"%dept");
("banking";"m&a")]
"results_banking_m&a.csv"

Note

You cannot use * to match with ssr.

A.62 string

Use string to produce a string representation of any q entity. For atoms, lists and functions, the result of string is a list of char that does not contain any q formatting characters. Following are some examples.

q)string 42
"42"
q)string `Zaphod
"Zaphod"
q)string 6*7
"42"
q)string 424224242i
"424224242"
q)string {[a] a*a}
"{[a] a*a}"

The first two examples demonstrate that string is not atomic because the output does not conform to the input. Although string is not atomic, it does recurse into a list.

q)string 42 98
"42"
"98"
q)string (10 20; 30 40)
"10" "20"
"30" "40"

This accounts for the un-intuitive behavior of string on an actual string.

q)string "Beeblebrox"
,"B"
,"e"
,"e"
,"b"
,"l"
,"e"
,"b"
,"r"
,"o"
,"x"

As expected, string acts on the values of a dictionary.

q)string ([a:10; b:20; c:30])
a| "10"
b| "20"
c| "30"

This is convenient for tables.

q)string ([] c1:`a`b`c; c2:10 20 30)
c1 c2
---------
,"a" "10"
,"b" "20"
,"c" "30"

Finally, string operates on the value portion of a keyed table.

q)string ([k:1 2 3] c:100 101 102)
k| c
-| -----
1| "100"
2| "101"
3| "102"

A.63 sublist

The binary sublist retrieves a sub-list of contiguous items from the target list y, where x is either a non-negative integral count of items to retrieve or a simple list of two non-negative integers comprising the starting index and the count of items to retrieve.

q)3 sublist 10 20 30 40 50
10 20 30
q)1 3 sublist 10 20 30 40 50
20 30 40
q)6 sublist 10 20 30 40 50
10 20 30 40 50
q)2 sublist ([a:10; b:20; c:30])
a| 10
b| 20

Warning

The construct (n sublist ...) is preferred to (n# ...) for extracting the first n items from a list since the latter will repeat the initial items if necessary to reach the specified count. This is ignored surprisingly often in practice.

q)6 sublist 10 20 30 40 50
10 20 30 40 50
q)6#10 20 30 40 50
10 20 30 40 50 10

A.64 sum sums msum

The aggregate sum is +/, which applies + cumulatively across a numeric list and returns the final result. It is for those who like to type more characters.

q)sum 1+til 100
5050

It is possible to apply sum to a nested list provided the sublists conform. In this case, the result conforms to the sublists and the sum is calculated recursively on the sublists.

q)sum (1 2;100 200;1000 2000)
1101 2202

The uniform sums is (+), which applies (+) cumulatively across a list of numeric type and returns the intermediate results. It is for those who like to type more characters.

q)sums 1+til 10
1 3 6 10 15 21 28 36 45 55

The binary msum takes a positive integer x and returns the length-wide moving sum of the numeric list y. At each position in y, it computes the sum of the x preceding items, or as many as are available in the moving window up to that position. It excludes internal nulls from the calculation.

q)3 msum 10 20 30 40 50
10 30 60 90 120

A.65 sv

The binary sv – "scalar from vector" – has several overloads. It is usually written infix for ease of reading. Most of the overloads have corresponding forms for sv.

The first form takes a char, a string (or the null symbol) x and a list of strings y. It returns a string that is the concatenation of the strings in y, joined with x.

q)"," sv ("Now";"is";"the";"time";"")
"Now,is,the,time,"
q)`$"," sv ("Now";"is";"the";"time";"")
`Now,is,the,time,
q)",," sv ("Now";"is";"the";"time";"")
"Now,,is,,the,,time,"

When sv is used with an empty symbol x and a list of symbols y, the result is a symbol in which the items in x are concatenated with a separating dot. This is useful for q context names.

q)` sv `qalib`stat
`qalib.stat

When sv is used with an empty symbol x and a symbolic list y whose items comprise the parts of a file handle, the result is a symbol in which the items in source are concatenated with a separating /. This is useful for fully qualified path names.

q)` sv `:`q`tutorial`draft`3
`:/q/tutorial/draft/3

When sv is used with an empty symbol x and a list of strings y, it concatenates the strings, inserting a new line character after each.

q)` sv ("abc";"de")
"abc\nde\n"

When sv is used with a long x that is greater than 1, together with a simple list y of place values expressed in base x, the result is a long representing the converted base 10 value.

q)2 sv 101010b
42
q)10 sv 1 2 3 4 2
12342
q)
q)256 sv 0x001092
4242

More precisely, the last version of sv evaluates the polynomial,

(d[n-1]*b exp n-1) + ... +d[0]

where d is the list of digits, n is the count of d, and b is the base.

Thus, we find,

q)10 sv 1 2 3 11 2
12412
q)-10 sv 2 1 5
195

A.66 svar

The aggregate svar returns the statistical standard variance of its numeric list x.

q)svar 2 3 5 7
4.916667

It is equivalent to

{var[x]*count[x]%-1+count x}

Important

The svar function was added in version 3.2 meaning that Finance apps could no longer use a variable name svar for stress value at risk in this and later versions.

A.67 system

Use system on a string x to execute a q command or to "shell out". By this we mean q executes x if it is a q command, otherwise it is passed to the OS for execution. This is convenient to execute q commands or OS commands programmatically. The normal result of the command becomes the return value of the evaluation.

Important

Do not include the initial \ as you would when executing the command from the q session prompt.

q)system "c"
24 74i
q)system "c 20 200"
q)system "c"
20 200i
q)system "cd data" / this is q \cd which creates directory
q)system "pwd"
"/Users/jaborror/data"

A.68 # Take Reshape

The binary # has several overloads.

When x is an integer atom and y is an atom or list, Take returns x items drawn from y. The items are extracted from the head when x is positive and from the tail when x is negative. When x is zero, the result is an empty list of the same type as the first item in y. The result of take is always a list.

Important

When x is greater than the count of y, items of y are recycled until x items are obtained.

q)2#10 20 30 40 50
10 20
q)-3#10 20 30 40 50
30 40 50
q)0#10 20 30 40 5
`long$()
q)3#42
42 42 42
q)10#10 20 30 40 5
10 20 30 40 5 10 20 30 40 5

Tip

The idiom 0#atom is a common way to create an empty list of the type of atom.

q)meta ([] a:0#0; b:0#`)
c| t f a
-| -----
a| j
b| s

Since a dictionary is ordered, Take also applies to dictionaries and, by extension, to tables and keyed tables.

q)2#([a:10; b:20; c:30])
a| 10
b| 20
q)-1#([] c1:`a`b`c; c2:10 20 30)
c1 c2
-----
c 

q)2#([k:`a`b`c] v:10 20 30)
k| v
-| --
a| 10
b| 20

Observe that 1# does not convert a record dictionary into a table; you must use enlist.

q)1#([a:10; b:20; c:30])
a| 10
q)enlist ([a:10; b:20; c:30])
a b c
--------
10 20 30

Another overload of Take has x a list of keys and y a dictionary. The result is the sub-dictionary for the specified keys.

q)`a`c#([a:10;b:20;c:30])
a| 10
c| 30

Since a table is a column dictionary, this form also applies to a table and a list of column names.

q)`c1`c2#([] c1:`a`b`c; c2:10 20 30; c3:1.1 2.2 3.3)
c1 c2
-----
a 10
b 20
c 30

Using an anonymous table is a slick way to generate a list of keys for Take with a keyed table.

q)([] k:`a`c)#([k:`a`b`c] v:10 20 30)
k| v
-| --
a| 10
c| 30

The simple case of Reshape has x a list (r; c) of non-negative integers and y a list or atom source. The result is a nested list with r items, each having c items, drawn sequentially from the beginning of source, repeatedly if necessary. Otherwise put, the result is an r by c array obtained by reshaping source.

q)2 3#10 20 30 40 50
10 20 30
40 50 10

If in Reshape either ror c is null, the result is a nested list obtained by reshaping y into the specified number of rows or columns. This is generally a ragged array.

q)2 0N#10 20 30 40 50
10 20
30 40 50
q)0N 3#10 20 30 40 50
10 20 30
40 50

You can also use Reshape to create higher dimensional matrices although the null behavior only works in two dimensions.

q)2 3 4#til 24
0 1 2 3 4 5 6 7 8 9 10 11
12 13 14 15 16 17 18 19 20 21 22 23

A.69 tan atan

The atomic tan takes a float and returns its mathematical tangent.

q)tan 0
0f
q)pi:3.141592653589793
q)tan pi
-1.224647e-16
q)tan pi%2
1.633124e+16
q)tan pi%4
1f

The function tan is equivalent to:

(sin x)%cos x

The atomic atan is the mathematical inverse of tan. For a float xatan returns the float between – π/2 and π/2 whose tangent is x.

q)atan 0
0f
q)atan 1.414213562373095
0.9553166
q)atan 1
0.7853982

A.70 til

Use til with non-negative integral x to return a list of x consecutive longs starting with 0. The result is always a list

Tip

The result does not include x.

q)til 10
0 1 2 3 4 5 6 7 8 9
q)\t til 10000000
19
q)til 0
`long$()
q)til 1
,0
q)1+til 10
1 2 3 4 5 6 7 8 9 10
q)2*til 10
0 2 4 6 8 10 12 14 16 18
q)1+2*til 10
1 3 5 7 9 11 13 15 17 19
q).5*til 10
0 0.5 1 1.5 2 2.5 3 3.5 4 4.5
q)2025.01.01+til 5
2025.01.01 2025.01.02 2025.01.03 2025.01.04 2025.01.05

You can also use key in place of til.

q)key 10
0 1 2 3 4 5 6 7 8 9

A.71 trim ltrim rtrim

Use ltrim to remove leading nulls from a list. For strings it removes leading banks.

q)ltrim 0N 20 30 0N 0N
20 30 0N 0N
q)ltrim " abc "
"abc "
q)ltrim " "
""

You can also apply ltrim to a non-blank char but it fails for a blank char (why?).

q)ltrim"a"
"a"
q)ltrim" "
'type

Use rtrim to remove trailing nulls from a list. For strings this removes trailing blanks.

q)rtrim 0N 20 30 0N 0N
0N 20 30
q)rtrim " abc "
" abc"
q)rtrim " "
""

You can apply rtrim to a non-blank char but it fails for a blank char.

q)rtrim "a"
"a"
q)rtrim " "
'type
  [0] rtrim " "
      ^
Use trim to remove both leading and trailing nulls from x. For strings the removes leading and trailing blanks.

q)trim 0N 20 30 0N 0N
20 30
q)trim " abc "
"abc"
q)trim " "
""

The function trim is equivalent to:

{ltrim rtrim x}.

A.72 ungroup

Use ungroup to flatten the result of xgroup or a select ... by without aggregation. You can also apply ungroup to tables with nested columns of the same form that are otherwise generated.

The action of ungroup expands each key group, resulting in one row for each item in the nested columns. The fields in a result row are drawn from corresponding positions across the nested columns.

We use the distribution example.

q)\l sp.q
q)sp
s p qty
---------
s1 p1 300
s1 p2 200
s1 p3 400
s1 p4 200
s4 p5 100
s1 p6 100
s2 p1 300
s2 p2 400
s3 p2 200
q)select s, qty by p from sp
p | s               qty
--| -------------------------------
p1| `s$`s1`s2       300 300
p2| `s$`s1`s2`s3`s4 200 400 200 200
p3| `s$,`s1         ,400
p4| `s$`s1`s4       200 300
p5| `s$`s4`s4       100 400
p6| `s$,`s1         ,100
q)ungroup select s, qty by p from sp
p  s  qty
---------
p1 s1 300
p1 s2 300
p2 s1 200
p2 s2 400
p2 s3 200
p2 s4 200
p3 s1 400
p4 s1 200
p4 s4 300
p5 s4 100
p5 s4 400
p6 s1 100

q)`p xgroup sp 
p | s               qty             
--| ------------------------------- 

p1| `s$`s1`s2       300 300         
 
q)ungroup `p xgroup sp 
p  s  qty 
--------- 
p1 s1 300 
p1 s2 300 
 

Tip

Observe that ungroup is not quite the inverse of a grouping operation. Since grouping sorts on the keys, a subsequent ungroup returns the original records sorted by the grouped column(s).

A.73 value

Simply put, value runs the q interpreter on a string argument.

Tip

The functions value and get are identical since they are both unary (.) in k. Conventionally get is used with file I/O.

When value is applied to a symbol, it returns the value associated with the variable of that symbolic name. In a fresh q session,

q)value `a
'a
q)a:42
q)value `a
42

When applied to a dictionary, value returns the values portion of the dictionary.

q)value ([a:10; b:20; c:30])
10 20 30
q)value ([k:`a`b`c] v:10 20 30)
v
--
10
20
30

Tip

A common idiom uses value to extract the columns lists from a table.

q)value flip ([] c1:`a`b`c; c2:10 20 30)
a b c
10 20 30

When value is applied to an enumerated value, it de-enumerates it. This is handy when switching between kdb+ databases having different sym domains. In a fresh q session,

q)ev:`sym?`a`x`b`y`a`c`b
q)ev
`sym$`a`x`b`y`a`c`b
q)value ev
`a`x`b`y`a`c`b

Given a function, value returns the following list:

(bytecode;parameters;locals;(namespace,globals);constants[0];...;constants[n];m;n;f;l;s)

where

Item Description
m Bytecode to source position map; -1 if position unknown
n Fully qualified (with namespace) function name as a string, set on first global assignment, with @ appended for inner lambdas; () if not applicable
f Full path to the file where the function originated from; "" if not applicable
l Line number in said file; -1 if not applicable
q)f:{[a;b]d::neg c:a*b+42;c+e}
q)value f
`a`b
,`c
``d`e
42
21 19 20 17 18 0 16 11 0 9 0 9 0 26 24 25 2 2
"..f"
""
-1
"{[a;b]d::neg c:a*b+42;c+e}"

Given a view alias, value returns the list:

(cached value;parse tree;dependencies;definition)

When the evaluation of the expression in the alias is as yet deferred, the cached value is ::.

q)a:42
q)b::a+1       / evaluation is deferred
q)value `.[`b] / inspect b in global context
::
`s#(+;`a;1)
,`a
(("q";`);"";0;"b::a+1")

q)b
43
q)value `.[`b]
43
`s#(+;`a;1)
,`a
(("q";`);"";0;"b::a+1")

Given a projection, value returns a list containing the function body followed by the supplied arguments.

q)value f[2;3;]
{x+y+z}
2
3
::

Given a function that is the result of applying a unary iterator, value returns the argument to the iterator, viewing the latter as a higher order function.

q)value (+/)
+
q)value (+')
+
q)f:{x+y}
q)value (f')
{x+y}

The final and most powerful form of value is: when applied to a string it is the q interpreter itself.

q)value "6*7"
42
q)value "{x*x} til 10"
0 1 4 9 16 25 36 49 64 81

It will also evaluate some parse trees – i.e., a (potentially) nested list of functions followed by arguments – but it is better to use eval for this purpose.

q)value (*; 6; 7)
42
q)f:{x*y}
q)value (`f; 6; 7)
42

Important

The use of the value function is a powerful feature that allows q code to be written and executed on the fly. This can expose your program to potential attack unless done very carefully. If abused, it can quickly lead to unmaintainable code. (The spellchecker suggests "unmentionable" instead of "unmaintainable." How did it know?)

A.74 var

The aggregate var takes a numeric list and returns the mathematical variance of the items as a float.

q)var 42 45 37 38
10.25

The function var is equivalent to:

{(avg[x*x]) - (avg[x])*(avg[x])}

A.75 vs

The binary vs – 'vector from scalar' – has several overloads. It is usually written infix for ease of reading. Most of the overloads have corresponding forms for sv.

The first form takes a char or string x and a string y. It returns a list of strings containing the tokens of y as delimited by the specified x.

q)" " vs "Now is the time "
"Now"
"is"
"the"
"time"
""

q)", " vs "nuba, devi, lorenzo"
"nuba"
"devi"
"lorenzo"

Tip

You probably want to trim the input in the first example.

When x is an empty symbol and y is a symbol containing one of more ., vs returns a simple symbol list obtained by splitting y along the dots.

q)` vs `qalib.stat
`qalib`stat

Where x is the empty symbol `, and y is a string or bytestream, vs returns as a list of strings from y partitioned on embedded line terminators. (It recognizes both Unix \n and Windows \r\n terminators).

q)` vs "abc\ndef\nghi"
"abc"
"def"
"ghi"
q)` vs "x"$"abc\ndef\nghi"
"abc"
"def"
"ghi

When vs is used with an empty symbol x and a symbol representing a fully qualified file name y, it returns a simple list of two symbols in which the first item is the path and the second item is the file name. Note that in this usage, vs is not quite the inverse of sv.

q)` vs `:/Users/jaborror/Q4M/example.dat
`:/Users/jaborror/Q4M`example.dat

When y is a byte vector, x can be a delimiter byte or byte vector.

q)0x02 vs 0x0102010201
,0x01
,0x01
,0x01
q)0x0203 vs 0x000102030405
0x0001
0x0405
q)" "vs"x"$"a b" / type inferred from left hand side
,"a"
,"b"

When vs is used with x as 0b or 0x00 and y is a value of integral type, it returns a simple list whose items comprise the digits of the corresponding binary representation of source.

q)0x00 vs 4242
0x0000000000001092
q)10h$0x00 vs 8151631268726338926j
"q is fun"
q)0b vs 42
0000000000000000000000000000000000000000000000000000000000101010b

The 0b version can be used to display the internal representation of special values.

q)0b vs 0W
0111111111111111111111111111111111111111111111111111111111111111b
q)
q)0b vs -0W
1000000000000000000000000000000000000000000000000000000000000001b

A.76 wavg

The binary wavg takes two conforming numeric lists and returns the float average of y weighted by x in corresponding positions.

q)1 2 3 4 wavg 500 400 300 200
300f
q)(1 2;3 4) wavg (500 400; 300 200)
350 266.6667

The function wavg is equivalent to,

{(sum x*y)%sum x}

A.77 where

The unary where has two use cases.

The first returns the indices of 1b in a boolean list, or the keys associated to 1b in a dictionary with boolean values.

q)where 101010b
0 2 4
q)where `a`b`c`d`e`f!101010b
`a`c`e

This is useful when the boolean mapping is the result of a predicate.

q)L:"First, second, third"
q)where L=","
5 13

q)@[L; where L=","; :; "\t"]
"First\t second\t third"

q)where null ([a:1;b:0N;c:4;d:0N;f:6])
`b`d

In the more general case, the argument of where is a list x of non-negative integers, and the result is a list having x[i] copies of i for each index of x.

q)where 2 1 0 3 2
0 0 1 3 3 3 4 4
q)where 4#1
0 1 2 3

Zen Moment

The second form of where generalizes the form on a boolean list.

Even more generally, where works on dictionaries in an consistent way.

q)where`a`b`c!3 2 3
`a`a`a`b`b`c`c`c

A.78 within

The binary within is atomic in x and has y a list whose two items are comparable. It returns a boolean representing whether x is greater than or equal to y[0] and less than or equal to y[1]. It does type promotion on arguments.

q)3 within 2 5
1b
q)(til 7) within 2 5
0011110b
q)"c" within "az"
1b
q)2025.03.14 within 2025.02.01 2025.03.21
0b
q)`ab within `a`b
1b
q)100 within "aj"
1b

Tip

Ensure the items in the second argument are in increasing order or you will get no matches.

A.79 wsum

The binary wsum takes two conforming numeric lists and returns the float sum of the items of y weighted by the items of the x.

q)1 2 3 4 wsum 500 400 300 200
3000f

The function wsum is equivalent to,

{sum x*y}

Tip

This is the vector dot product.

A.80 xbar

The binary xbar takes a non-negative numeric atom x and is atomic in the numeric y. It returns the largest integral multiple of x that is less than or equal to y. Visually, the result is the left endpoint of the band of width x that contains y. Since xbar is atomic in the second parameter, this is an effective way to bin the items in a numeric list.

q)1 xbar 0 .5 1 1.5 2 2.5 3 3.5
0 0 1 1 2 2 3 3f
q)2 xbar 0 .5 1 1.5 2 2.5 3 3.5
0 0 0 0 2 2 2 2f

Since a q month is the count of months since the millennium, you can use xbar to determine quarters. Recall that a month is equal to the first day of the month.

q)`date$3 xbar `month$2025.11.19      / beginning of that quarter
2025.10.01
q)`date$3+3 xbar `month$2025.11.19    / beginning of next quarter
2026.01.01
q)-1+`date$3+3 xbar `month$2025.11.19 / end of that quarter
2025.12.31

A.81 xrank

The binary xrank takes x a positive integer and is uniform on the list y. It returns a list of integers containing the x-quantile into which each item of y falls, considering y as a distribution. For example, choosing x to be 4 returns quartiles and 100 yields percentiles.

q)4 xrank 30 10 40 20 90
1 0 2 0 3
q)100 xrank 200?1000.
338 55 54 40 18 30 83 56 74 42 52 61 9 20 35 64 55 73 22 73 50 66 97 ..