Skip to main content

Queries

This page uses Wasm code blocks so you can run the examples directly in the browser.

Queries filter out and transform objects fulfilling some specific properties from collections of objects.

Example:

The following query returns the name and values of the constants in the table Constants whose closest integer is 3:

select name, value
from Constants
where round(value)=3
does this query fail?

This query requires that you have defined the Constants table. This was done in the previous section Basic functions. So if the query fail you might need to go back and define the Constants table again.

OSQL queries can filter, transform, and generate objects of any kind, not only strings and numbers stored in tables. You can make queries over any kind of objects by specifying their types in the from clause of the select statement.

Examples:

The following query computes the set of divisors for the integer 143:

select d
from Integer d, Integer n
where d in range(2,ceiling(n/2))
and 0 = mod(n,d)
and n = 143

This query selects the odd elements among the integers between 10 and 15:

select i
from Integer i
where i in range(10,15)
and odd(i)
Note

SQL's select statement is a special case of OSQL queries. A restriction with SQL's select statement is that variables in queries must be bound only to rows in tables. In OSQL queries, variables can be bound to any kind of objects, e.g. strings, numbers, vectors, matrices, tensors, bags, streams, records or user defined objects. Combined with functions, this makes analytical models in different domains very easy to express with OSQL.

The SQL subset of OSQL is introduced in the SQL Tutorial. You can skip that tutorial if you are already familiar with SQL.

OSQL functions can be defined by queries.

Example:

This function over numbers computes the divisors of any integer n:

create function divisors(Integer n) -> Bag of Integer
as select d
from Integer d
where d in range(2,ceiling(n/2))
and 0 = mod(n,d)

The following query returns the divisors of 143:

divisors(143)

In general, queries can be made over various kinds of collections, not only sets and bags.

Examples:

The following set query returns the set prime numbers in the vector collection [197,143,2]:

select n
from Integer n
where n in [197,143,2]
and notany(divisors(n))

The following query returns a vector of prime numbers in [197,143,2]:

select Vector of n
from Integer n
where n in [197,143,2]
and notany(divisors(n))

The following query returns a stream of prime numbers in [197,143,2]:

select Stream of n
from Integer n
where n in [197,143,2]
and notany(divisors(n))

In the tutorial Streams it will be shown how to specify OSQL queries over live streams.

General queries over sets and bags are documented in Queries.

Queries to filter and transform elements in vectors and tensors are documented in Vector queries.

Case rules​

Case rules define functions and formulas that have different definitions depending on their arguments.

Example:

The signum of a number can be defined as:

create function signum(Real x) -> Integer
as case when x > 0 then 1
when x = 0 then 0
else -1 end
signum(-3.1)

The built-in function sign(x) does the same.

Another example of a function defined in terms of case rules is the built in function atan2(y,x):

sourcecode("atan2")
atan2(1,2)

In general, case rules compute values conditioned on values of variables. The case rules compute these values without executing any actions (side effects). This is different from conditional statements in conventional programming languages such as if {condition} do-something; else do-something-else; where different side effects (actions) are executed based on a condition.

Case rules can be used in queries, for example:

select case when x <= -40 then "too cold"
when x < 0 then "freezing"
when x < 18 then "cold"
when x < 23 then "plesant"
when x < 40 then "hot"
else "too hot"
end
from Real x
where x in 10*range(-4,4)

This illustrates how case rules can be used for specifying decision rules based on values of variables.

Tests in case statements succeed unless they return null.

Example:

case when sqrt(-1) then 1 else 0 end

AND, OR, NOTANY and SOME​

In the where clause of select statement clauses connected with and operators specify restrictions on the query result (its solution space). Similarly, or clauses extend the solution space.

Example:

The following query which returns the set of values of the vector [1,2,3,4,5] that are less than 3 or larger than 4:

select i
from Integer i
where i in [1,2,3,4,5]
and (i<3 or i>4)

Notice that or has higher priority than and in queries, so parentheses may be needed if both and and or are used in the same query.

To negate disjunctive expressions we can use the aggregate function notany(Bag b)->Boolean that returns true is the bag b is empty:

Example:

select i
from Integer i
where i in [1,2,3,4,5]
and notany(i<3 or i>4)

The aggregate function some(Bag)->Boolean test whether there is some value in a bag.

Example:

some(range(1,10000000000))

Argmin and argmax​

OSQL queries can be used to implement the argmax operation by finding the vector index that gives the maximum value of a vector.

Example:

The following query finds the index of the maximum value of the vector [4,3,9,1,8,5]:

select i
from Integer i, Vector v
where v = [4,3,9,1,8,5]
and v[i] = max(v)

Similarly you can use min to find the index that gives the minimum value of a vector.

Example:

select i
from Integer i, Vector v
where v = [4,3,9,1,8,5]
and v[i] = min(v)

Should there be more than one index that satifies the relation, then all of them are returned as a bag.

Example:

select i
from Integer i, Vector v
where v = [4,3,9,1,9,5]
and v[i] = max(v)

For details on how to make general queries go to Queries in the reference documentation.

The next tutorial shows how to develop models, undo changes, and save the database of models on disk.