[ Web Proxy ]
URL:
Viewing: https://cloud.google.com/bigquery/docs/reference/standard-sql/operators#comparison_operators [Back]  [Original]

Operators  |  BigQuery  |  Google Cloud Documentation Skip to main content
Google Cloud Documentation [Google Cloud Documentation]
Send feedback

Operators Stay organized with collections Save and categorize content based on your preferences.

GoogleSQL for BigQuery supports operators. Operators are represented by special characters or keywords; they don't use function call syntax. An operator manipulates any number of data inputs, also called operands, and returns a result.

Common conventions:

Operator precedence

The following table lists all GoogleSQL operators from highest to lowest precedence, i.e., the order in which they will be evaluated within a statement.

Order of Precedence Operator Input Data Types Name Operator Arity
1 Field access operator STRUCT
JSON
Field access operator Binary
  Array subscript operator ARRAY Array position. Must be used with OFFSET or ORDINAL—see Array Functions . Binary
  JSON subscript operator JSON Field name or array position in JSON. Binary
2 + All numeric types Unary plus Unary
  - All numeric types Unary minus Unary
  ~ Integer or BYTES Bitwise not Unary
3 * All numeric types Multiplication Binary
  / All numeric types Division Binary
  || STRING, BYTES, or ARRAY<T> Concatenation operator Binary
4 + All numeric types, DATE with INT64 , INTERVAL Addition Binary
  - All numeric types, DATE with INT64 , INTERVAL Subtraction Binary
5 << Integer or BYTES Bitwise left-shift Binary
  >> Integer or BYTES Bitwise right-shift Binary
6 & Integer or BYTES Bitwise and Binary
7 ^ Integer or BYTES Bitwise xor Binary
8 | Integer or BYTES Bitwise or Binary
9 (Comparison Operators) = Any comparable type. See Data Types for a complete list. Equal Binary
  < Any comparable type. See Data Types for a complete list. Less than Binary
  > Any comparable type. See Data Types for a complete list. Greater than Binary
  <= Any comparable type. See Data Types for a complete list. Less than or equal to Binary
  >= Any comparable type. See Data Types for a complete list. Greater than or equal to Binary
  !=, <> Any comparable type. See Data Types for a complete list. Not equal Binary
  [NOT] LIKE STRING and BYTES Value does [not] match the pattern specified Binary
  Quantified LIKE STRING and BYTES Checks a search value for matches against several patterns. Binary
  [NOT] BETWEEN Any comparable types. See Data Types for a complete list. Value is [not] within the range specified Binary
  [NOT] IN Any comparable types. See Data Types for a complete list. Value is [not] in the set of values specified Binary
  IS [NOT] DISTINCT FROM All Value is [not] DISTINCT FROM Binary
  IS [NOT] NULL All Value is [not] NULL Unary
  IS [NOT] TRUE BOOL Value is [not] TRUE. Unary
  IS [NOT] FALSE BOOL Value is [not] FALSE. Unary
10 NOT BOOL Logical NOT Unary
11 AND BOOL Logical AND Binary
12 OR BOOL Logical OR Binary

For example, the logical expression:

x OR y AND z

is interpreted as:

( x OR ( y AND z ) )

Operators with the same precedence are left associative. This means that those operators are grouped together starting from the left and moving right. For example, the expression:

x AND y AND z

is interpreted as:

( ( x AND y ) AND z )

The expression:

x * y / z

is interpreted as:

( ( x * y ) / z )

All comparison operators have the same priority, but comparison operators aren't associative. Therefore, parentheses are required to resolve ambiguity. For example:

(x < y) IS FALSE

Operator list

Name Summary
Field access operator Gets the value of a field.
Array subscript operator Gets a value from an array at a specific position.
Struct subscript operator Gets the value of a field at a selected position in a struct.
JSON subscript operator Gets a value of an array element or field in a JSON expression.
Arithmetic operators Performs arithmetic operations.
Date arithmetics operators Performs arithmetic operations on dates.
Datetime subtraction Computes the difference between two datetimes as an interval.
Interval arithmetic operators Adds an interval to a datetime or subtracts an interval from a datetime.
Bitwise operators Performs bit manipulation.
Logical operators Tests for the truth of some condition and produces TRUE, FALSE, or NULL.
Graph logical operators Tests for the truth of a condition in a graph label and produces either TRUE or FALSE.
Graph predicates Tests for the truth of a condition for a graph element and produces TRUE, FALSE, or NULL.
ALL_DIFFERENT predicate In a graph, checks to see if the elements in a list are all different.
IS DESTINATION predicate In a graph, checks to see if a node is or isn't the destination of an edge.
IS SOURCE predicate In a graph, checks to see if a node is or isn't the source of an edge.
SAME predicate In a graph, checks if all graph elements in a list bind to the same node or edge.
Comparison operators Compares operands and produces the results of the comparison as a BOOL value.
EXISTS operator Checks if a subquery produces one or more rows.
IN operator Checks for an equal value in a set of values.
IS operators Checks for the truth of a condition and produces either TRUE or FALSE.
IS DISTINCT FROM operator Checks if values are considered to be distinct from each other.
LIKE operator Checks if values are like or not like one another.
Quantified LIKE operator Checks a search value for matches against several patterns.
Concatenation operator Combines multiple values into one.
WITH expression Creates variables for re-use and produces a result expression.

Field access operator

expression.fieldname[. ...]

Description

Gets the value of a field. Alternatively known as the dot operator. Can be used to access nested fields. For example, expression.fieldname1.fieldname2.

Input values:

Note: If the field to access is within a STRUCT, you can use the struct subscript operator to access the field by its position within the STRUCT instead of by its name. Accessing by a field by position is useful when fields are un-named or have ambiguous names.

Return type

Example

In the following example, the field access operations are .address and .country.

SELECT
  STRUCT(
    STRUCT('Yonge Street' AS street, 'Canada' AS country)
      AS address).address.country

/*---------+
 | country |
 +---------+
 | Canada  |
 +---------*/

Array subscript operator

Note: Syntax characters enclosed in double quotes ("") are literal and required.
array_expression "[" array_subscript_specifier "]"

array_subscript_specifier:
  { index | position_keyword(index) }

position_keyword:
  { OFFSET | SAFE_OFFSET | ORDINAL | SAFE_ORDINAL }

Description

Gets a value from an array at a specific position.

Input values:

Tip: To access the first or last element in an array, use the ARRAY_FIRST or ARRAY_LAST function.

Return type

T where array_expression is ARRAY<T>.

Examples

In following query, the array subscript operator is used to return values at specific position in item_array. This query also shows what happens when you reference an index (6) in an array that's out of range. If the SAFE prefix is included, NULL is returned, otherwise an error is produced.

SELECT
  ["coffee", "tea", "milk"] AS item_array,
  ["coffee", "tea", "milk"][0] AS item_index,
  ["coffee", "tea", "milk"][OFFSET(0)] AS item_offset,
  ["coffee", "tea", "milk"][ORDINAL(1)] AS item_ordinal,
  ["coffee", "tea", "milk"][SAFE_OFFSET(6)] AS item_safe_offset

/*---------------------+------------+-------------+--------------+------------------+
 | item_array          | item_index | item_offset | item_ordinal | item_safe_offset |
 +---------------------+------------+-------------+--------------+------------------+
 | [coffee, tea, milk] | coffee     | coffee      | coffee       | NULL             |
 +----------------------------------+-------------+--------------+------------------*/

When you reference an index that's out of range in an array, and a positional keyword that begins with SAFE isn't included, an error is produced. For example:

-- Error. Array index 6 is out of bounds.
SELECT ["coffee", "tea", "milk"][6] AS item_offset
-- Error. Array index 6 is out of bounds.
SELECT ["coffee", "tea", "milk"][OFFSET(6)] AS item_offset

Struct subscript operator

Note: Syntax characters enclosed in double quotes ("") are literal and required.
struct_expression "[" struct_subscript_specifier "]"

struct_subscript_specifier:
  { index | position_keyword(index) }

position_keyword:
  { OFFSET | ORDINAL }

Description

Gets the value of a field at a selected position in a struct.

Input types

Note: The struct subscript operator doesn't support SAFE positional keywords at this time.

Examples

In following query, the struct subscript operator is used to return values at specific locations in item_struct using position keywords. This query also shows what happens when you reference an index (6) in an struct that's out of range.

SELECT
  STRUCT<INT64, STRING, BOOL>(23, "tea", FALSE)[0] AS field_index,
  STRUCT<INT64, STRING, BOOL>(23, "tea", FALSE)[OFFSET(0)] AS field_offset,
  STRUCT<INT64, STRING, BOOL>(23, "tea", FALSE)[ORDINAL(1)] AS field_ordinal

/*-------------+--------------+---------------+
 | field_index | field_offset | field_ordinal |
 +-------------+--------------+---------------+
 | 23          | 23           | 23            |
 +-------------+--------------+---------------*/

When you reference an index that's out of range in a struct, an error is produced. For example:

-- Error: Field ordinal 6 is out of bounds in STRUCT
SELECT STRUCT<INT64, STRING, BOOL>(23, "tea", FALSE)[6] AS field_offset
-- Error: Field ordinal 6 is out of bounds in STRUCT
SELECT STRUCT<INT64, STRING, BOOL>(23, "tea", FALSE)[OFFSET(6)] AS field_offset

JSON subscript operator

Note: Syntax characters enclosed in double quotes ("") are literal and required.
json_expression "[" array_element_id "]"
json_expression "[" field_name "]"

Description

Gets a value of an array element or field in a JSON expression. Can be used to access nested data.

Input values:

Return type

JSON

Example

In the following example:

SELECT json_value.class.students[0]['name'] AS first_student
FROM
  UNNEST(
    [
      JSON '{"class" : {"students" : [{"name" : "Jane"}]}}',
      JSON '{"class" : {"students" : []}}',
      JSON '{"class" : {"students" : [{"name" : "John"}, {"name": "Jamie"}]}}'])
    AS json_value;

/*-----------------+
 | first_student   |
 +-----------------+
 | "Jane"          |
 | NULL            |
 | "John"          |
 +-----------------*/

Arithmetic operators

All arithmetic operators accept input of numeric type T, and the result type has type T unless otherwise indicated in the description below:

Name Syntax
Addition X + Y
Subtraction X - Y
Multiplication X * Y
Division X / Y
Unary Plus + X
Unary Minus - X
Note: Divide by zero operations return an error. To return a different result, consider the IEEE_DIVIDE or SAFE_DIVIDE functions.

Result types for Addition, Subtraction and Multiplication:

INPUTINT64NUMERICBIGNUMERICFLOAT64
INT64INT64NUMERICBIGNUMERICFLOAT64
NUMERICNUMERICNUMERICBIGNUMERICFLOAT64
BIGNUMERICBIGNUMERICBIGNUMERICBIGNUMERICFLOAT64
FLOAT64FLOAT64FLOAT64FLOAT64FLOAT64

Result types for Division:

INPUTINT64NUMERICBIGNUMERICFLOAT64
INT64FLOAT64NUMERICBIGNUMERICFLOAT64
NUMERICNUMERICNUMERICBIGNUMERICFLOAT64
BIGNUMERICBIGNUMERICBIGNUMERICBIGNUMERICFLOAT64
FLOAT64FLOAT64FLOAT64FLOAT64FLOAT64

Result types for Unary Plus:

INPUTINT64NUMERICBIGNUMERICFLOAT64
OUTPUTINT64NUMERICBIGNUMERICFLOAT64

Result types for Unary Minus:

INPUTINT64NUMERICBIGNUMERICFLOAT64
OUTPUTINT64NUMERICBIGNUMERICFLOAT64

Date arithmetics operators

Operators '+' and '-' can be used for arithmetic operations on dates.

date_expression + int64_expression
int64_expression + date_expression
date_expression - int64_expression

Description

Adds or subtracts int64_expression days to or from date_expression. This is equivalent to DATE_ADD or DATE_SUB functions, when interval is expressed in days.

Return Data Type

DATE

Example

SELECT DATE "2020-09-22" + 1 AS day_later, DATE "2020-09-22" - 7 AS week_ago

/*------------+------------+
 | day_later  | week_ago   |
 +------------+------------+
 | 2020-09-23 | 2020-09-15 |
 +------------+------------*/

Datetime subtraction

date_expression - date_expression
timestamp_expression - timestamp_expression
datetime_expression - datetime_expression

Description

Computes the difference between two datetime values as an interval.

Return Data Type

INTERVAL

Example

SELECT
  DATE "2021-05-20" - DATE "2020-04-19" AS date_diff,
  TIMESTAMP "2021-06-01 12:34:56.789" - TIMESTAMP "2021-05-31 00:00:00" AS time_diff

/*-------------------+------------------------+
 | date_diff         | time_diff              |
 +-------------------+------------------------+
 | 0-0 396 0:0:0     | 0-0 0 36:34:56.789     |
 +-------------------+------------------------*/

Interval arithmetic operators

Addition and subtraction

date_expression + interval_expression = DATETIME
date_expression - interval_expression = DATETIME
timestamp_expression + interval_expression = TIMESTAMP
timestamp_expression - interval_expression = TIMESTAMP
datetime_expression + interval_expression = DATETIME
datetime_expression - interval_expression = DATETIME

Description

Adds an interval to a datetime value or subtracts an interval from a datetime value.

Example

SELECT
  DATE "2021-04-20" + INTERVAL 25 HOUR AS date_plus,
  TIMESTAMP "2021-05-02 00:01:02.345+00" - INTERVAL 10 SECOND AS time_minus;

/*-------------------------+--------------------------------+
 | date_plus               | time_minus                     |
 +-------------------------+--------------------------------+
 | 2021-04-21 01:00:00     | 2021-05-02 00:00:52.345+00     |
 +-------------------------+--------------------------------*/

Multiplication and division

interval_expression * integer_expression = INTERVAL
interval_expression / integer_expression = INTERVAL

Description

Multiplies or divides an interval value by an integer.

Example

SELECT
  INTERVAL '1:2:3' HOUR TO SECOND * 10 AS mul1,
  INTERVAL 35 SECOND * 4 AS mul2,
  INTERVAL 10 YEAR / 3 AS div1,
  INTERVAL 1 MONTH / 12 AS div2

/*----------------+--------------+-------------+--------------+
 | mul1           | mul2         | div1        | div2         |
 +----------------+--------------+-------------+--------------+
 | 0-0 0 10:20:30 | 0-0 0 0:2:20 | 3-4 0 0:0:0 | 0-0 2 12:0:0 |
 +----------------+--------------+-------------+--------------*/

Bitwise operators

All bitwise operators return the same type and the same length as the first operand.

Name Syntax Input Data Type Description
Bitwise not ~ X Integer or BYTES Performs logical negation on each bit, forming the ones' complement of the given binary value.
Bitwise or X | Y X: Integer or BYTES
Y: Same type as X
Takes two bit patterns of equal length and performs the logical inclusive OR operation on each pair of the corresponding bits. This operator throws an error if X and Y are bytes of different lengths.
Bitwise xor X ^ Y X: Integer or BYTES
Y: Same type as X
Takes two bit patterns of equal length and performs the logical exclusive OR operation on each pair of the corresponding bits. This operator throws an error if X and Y are bytes of different lengths.
Bitwise and X & Y X: Integer or BYTES
Y: Same type as X
Takes two bit patterns of equal length and performs the logical AND operation on each pair of the corresponding bits. This operator throws an error if X and Y are bytes of different lengths.
Left shift X << Y X: Integer or BYTES
Y: INT64
Shifts the first operand X to the left. This operator returns 0 or a byte sequence of b'\x00' if the second operand Y is greater than or equal to the bit length of the first operand X (for example, 64 if X has the type INT64). This operator throws an error if Y is negative.
Right shift X >> Y X: Integer or BYTES
Y: INT64
Shifts the first operand X to the right. This operator doesn't perform sign bit extension with a signed type (i.e., it fills vacant bits on the left with 0). This operator returns 0 or a byte sequence of b'\x00' if the second operand Y is greater than or equal to the bit length of the first operand X (for example, 64 if X has the type INT64). This operator throws an error if Y is negative.

Logical operators

GoogleSQL supports the AND, OR, and NOT logical operators. Logical operators allow only BOOL or NULL input and use three-valued logic to produce a result. The result can be TRUE, FALSE, or NULL:

x y x AND y x OR y
TRUE TRUE TRUE TRUE
TRUE FALSE FALSE TRUE
TRUE NULL NULL TRUE
FALSE TRUE FALSE TRUE
FALSE FALSE FALSE FALSE
FALSE NULL FALSE NULL
NULL TRUE NULL TRUE
NULL FALSE FALSE NULL
NULL NULL NULL NULL
x NOT x
TRUE FALSE
FALSE TRUE
NULL NULL

The order of evaluation of operands to AND and OR can vary, and evaluation can be skipped if unnecessary.

Examples

The examples in this section reference a table called entry_table:

/*-------+
 | entry |
 +-------+
 | a     |
 | b     |
 | c     |
 | NULL  |
 +-------*/
SELECT 'a' FROM entry_table WHERE entry = 'a'

-- a => 'a' = 'a' => TRUE
-- b => 'b' = 'a' => FALSE
-- NULL => NULL = 'a' => NULL

/*-------+
 | entry |
 +-------+
 | a     |
 +-------*/
SELECT entry FROM entry_table WHERE NOT (entry = 'a')

-- a => NOT('a' = 'a') => NOT(TRUE) => FALSE
-- b => NOT('b' = 'a') => NOT(FALSE) => TRUE
-- NULL => NOT(NULL = 'a') => NOT(NULL) => NULL

/*-------+
 | entry |
 +-------+
 | b     |
 | c     |
 +-------*/
SELECT entry FROM entry_table WHERE entry IS NULL

-- a => 'a' IS NULL => FALSE
-- b => 'b' IS NULL => FALSE
-- NULL => NULL IS NULL => TRUE

/*-------+
 | entry |
 +-------+
 | NULL  |
 +-------*/

Graph logical operators

GoogleSQL supports the following logical operators in element pattern label expressions:

Name Syntax Description
NOT !X Returns TRUE if X isn't included, otherwise, returns FALSE.
OR X | Y Returns TRUE if either X or Y is included, otherwise, returns FALSE.
AND X & Y Returns TRUE if both X and Y are included, otherwise, returns FALSE.

Graph predicates

GoogleSQL supports the following graph-specific predicates in graph expressions. A predicate can produce TRUE, FALSE, or NULL.

ALL_DIFFERENT predicate

ALL_DIFFERENT(element, element[, ...])

Description

In a graph, checks to see if the elements in a list are all different. Returns TRUE if none of the elements in the list equal one another, otherwise FALSE.

Definitions

Details

Produces an error if element is NULL.

Return type

BOOL

Examples

GRAPH graph_db.FinGraph
MATCH
  (a1:Account)-[t1:Transfers]->(a2:Account)-[t2:Transfers]->
  (a3:Account)-[t3:Transfers]->(a4:Account)
WHERE a1.id < a4.id
RETURN
  ALL_DIFFERENT(t1, t2, t3) AS results

/*---------+
 | results |
 +---------+
 | FALSE   |
 | TRUE    |
 | TRUE    |
 +---------*/

IS DESTINATION predicate

node IS [ NOT ] DESTINATION [ OF ] edge

Description

In a graph, checks to see if a node is or isn't the destination of an edge. Can produce TRUE, FALSE, or NULL.

Arguments:

Examples

GRAPH graph_db.FinGraph
MATCH (a:Account)-[transfer:Transfers]-(b:Account)
WHERE a IS DESTINATION of transfer
RETURN a.id AS a_id, b.id AS b_id

/*-------------+
 | a_id | b_id |
 +-------------+
 | 16   | 7    |
 | 16   | 7    |
 | 20   | 16   |
 | 7    | 20   |
 | 16   | 20   |
 +-------------*/
GRAPH graph_db.FinGraph
MATCH (a:Account)-[transfer:Transfers]-(b:Account)
WHERE b IS DESTINATION of transfer
RETURN a.id AS a_id, b.id AS b_id

/*-------------+
 | a_id | b_id |
 +-------------+
 | 7    | 16   |
 | 7    | 16   |
 | 16   | 20   |
 | 20   | 7    |
 | 20   | 16   |
 +-------------*/

IS SOURCE predicate

node IS [ NOT ] SOURCE [ OF ] edge

Description

In a graph, checks to see if a node is or isn't the source of an edge. Can produce TRUE, FALSE, or NULL.

Arguments:

Examples

GRAPH graph_db.FinGraph
MATCH (a:Account)-[transfer:Transfers]-(b:Account)
WHERE a IS SOURCE of transfer
RETURN a.id AS a_id, b.id AS b_id

/*-------------+
 | a_id | b_id |
 +-------------+
 | 20   | 7    |
 | 7    | 16   |
 | 7    | 16   |
 | 20   | 16   |
 | 16   | 20   |
 +-------------*/
GRAPH graph_db.FinGraph
MATCH (a:Account)-[transfer:Transfers]-(b:Account)
WHERE b IS SOURCE of transfer
RETURN a.id AS a_id, b.id AS b_id

/*-------------+
 | a_id | b_id |
 +-------------+
 | 7    | 20   |
 | 16   | 7    |
 | 16   | 7    |
 | 16   | 20   |
 | 20   | 16   |
 +-------------*/

SAME predicate

SAME (element, element[, ...])

Description

In a graph, checks if all graph elements in a list bind to the same node or edge. Returns TRUE if the elements bind to the same node or edge, otherwise FALSE.

Arguments:

Details

Produces an error if element is NULL.

Example

The following query returns the source and destination IDs for transfers between different accounts:

GRAPH graph_db.FinGraph
MATCH (src:Account)<-[transfer:Transfers]-(dest:Account)
WHERE NOT SAME(src, dest)
RETURN src.id AS source_id, dest.id AS destination_id

/*----------------------------+
 | source_id | destination_id |
 +----------------------------+
 | 7         | 20             |
 | 16        | 7              |
 | 16        | 7              |
 | 16        | 20             |
 | 20        | 16             |
 +----------------------------*/

Comparison operators

Compares operands and produces the results of the comparison as a BOOL value. These comparison operators are available:

Name Syntax Description
Less Than X < Y Returns TRUE if X is less than Y. This operator supports specifying collation.
Less Than or Equal To X <= Y Returns TRUE if X is less than or equal to Y. This operator supports specifying collation.
Greater Than X > Y Returns TRUE if X is greater than Y. This operator supports specifying collation.
Greater Than or Equal To X >= Y Returns TRUE if X is greater than or equal to Y. This operator supports specifying collation.
Equal X = Y Returns TRUE if X is equal to Y. This operator supports specifying collation.
Not Equal X != Y
X <> Y
Returns TRUE if X isn't equal to Y. This operator supports specifying collation.
BETWEEN X [NOT] BETWEEN Y AND Z

Returns TRUE if X is [not] within the range specified. The result of X BETWEEN Y AND Z is equivalent to Y <= X AND X <= Z but X is evaluated only once in the former. This operator supports specifying collation.

LIKE X [NOT] LIKE Y See the LIKE operator for details.
IN Multiple See the IN operator for details.
IS DISTINCT FROM x IS [NOT] DISTINCT FROM y See the IS DISTINCT FROM operator for details.

The following rules apply to operands in a comparison operator:

The following rules apply when comparing these data types:

EXISTS operator

EXISTS( subquery )

Description

Returns TRUE if the subquery produces one or more rows. Returns FALSE if the subquery produces zero rows. Never returns NULL. To learn more about how you can use a subquery with EXISTS, see EXISTS subqueries.

Examples

In this example, the EXISTS operator returns FALSE because there are no rows in Words where the direction is south:

WITH Words AS (
  SELECT 'Intend' as value, 'east' as direction UNION ALL
  SELECT 'Secure', 'north' UNION ALL
  SELECT 'Clarity', 'west'
 )
SELECT EXISTS( SELECT value FROM Words WHERE direction = 'south' ) as result;

/*--------+
 | result |
 +--------+
 | FALSE  |
 +--------*/

IN operator

The IN operator supports the following syntax:

search_value [NOT] IN value_set

value_set:
  {
    (expression[, ...])
    | (subquery)
    | UNNEST(array_expression)
  }

Description

Checks for an equal value in a set of values. Semantic rules apply, but in general, IN returns TRUE if an equal value is found, FALSE if an equal value is excluded, otherwise NULL. NOT IN returns FALSE if an equal value is found, TRUE if an equal value is excluded, otherwise NULL.

This operator supports collation, but these limitations apply:

Semantic rules

When using the IN operator, the following semantics apply in this order:

When using the NOT IN operator, the following semantics apply in this order:

For example:

The semantics of:

x IN (y, z, ...)

are defined as equivalent to:

(x = y) OR (x = z) OR ...

and the subquery and array forms are defined similarly.

x NOT IN ...

is equivalent to:

NOT(x IN ...)

The UNNEST form treats an array scan like UNNEST in the FROM clause:

x [NOT] IN UNNEST(<array expression>)

This form is often used with array parameters. For example:

x IN UNNEST(@array_parameter)

See the Arrays topic for more information on how to use this syntax.

IN can be used with multi-part keys by using the struct constructor syntax. For example:

(Key1, Key2) IN ( (12,34), (56,78) )
(Key1, Key2) IN ( SELECT (table.a, table.b) FROM table )

See the Struct Type topic for more information.

Return Data Type

BOOL

Examples

You can use these WITH clauses to emulate temporary tables for Words and Items in the following examples:

WITH Words AS (
  SELECT 'Intend' as value UNION ALL
  SELECT 'Secure' UNION ALL
  SELECT 'Clarity' UNION ALL
  SELECT 'Peace' UNION ALL
  SELECT 'Intend'
 )
SELECT * FROM Words;

/*----------+
 | value    |
 +----------+
 | Intend   |
 | Secure   |
 | Clarity  |
 | Peace    |
 | Intend   |
 +----------*/
WITH
  Items AS (
    SELECT STRUCT('blue' AS color, 'round' AS shape) AS info UNION ALL
    SELECT STRUCT('blue', 'square') UNION ALL
    SELECT STRUCT('red', 'round')
  )
SELECT * FROM Items;

/*----------------------------+
 | info                       |
 +----------------------------+
 | {blue color, round shape}  |
 | {blue color, square shape} |
 | {red color, round shape}   |
 +----------------------------*/

Example with IN and an expression:

SELECT * FROM Words WHERE value IN ('Intend', 'Secure');

/*----------+
 | value    |
 +----------+
 | Intend   |
 | Secure   |
 | Intend   |
 +----------*/

Example with NOT IN and an expression:

SELECT * FROM Words WHERE value NOT IN ('Intend');

/*----------+
 | value    |
 +----------+
 | Secure   |
 | Clarity  |
 | Peace    |
 +----------*/

Example with IN, a scalar subquery, and an expression:

SELECT * FROM Words WHERE value IN ((SELECT 'Intend'), 'Clarity');

/*----------+
 | value    |
 +----------+
 | Intend   |
 | Clarity  |
 | Intend   |
 +----------*/

Example with IN and an UNNEST operation:

SELECT * FROM Words WHERE value IN UNNEST(['Secure', 'Clarity']);

/*----------+
 | value    |
 +----------+
 | Secure   |
 | Clarity  |
 +----------*/

Example with IN and a struct:

SELECT
  (SELECT AS STRUCT Items.info) as item
FROM
  Items
WHERE (info.shape, info.color) IN (('round', 'blue'));

/*------------------------------------+
 | item                               |
 +------------------------------------+
 | { {blue color, round shape} info } |
 +------------------------------------*/

IS operators

IS operators return TRUE or FALSE for the condition they are testing. They never return NULL, even for NULL inputs, unlike the IS_INF and IS_NAN functions defined in Mathematical Functions. If NOT is present, the output BOOL value is inverted.

Function Syntax Input Data Type Result Data Type Description
X IS TRUE BOOL BOOL Evaluates to TRUE if X evaluates to TRUE. Otherwise, evaluates to FALSE.
X IS NOT TRUE BOOL BOOL Evaluates to FALSE if X evaluates to TRUE. Otherwise, evaluates to TRUE.
X IS FALSE BOOL BOOL Evaluates to TRUE if X evaluates to FALSE. Otherwise, evaluates to FALSE.
X IS NOT FALSE BOOL BOOL Evaluates to FALSE if X evaluates to FALSE. Otherwise, evaluates to TRUE.
X IS NULL Any value type BOOL Evaluates to TRUE if X evaluates to NULL. Otherwise evaluates to FALSE.
X IS NOT NULL Any value type BOOL Evaluates to FALSE if X evaluates to NULL. Otherwise evaluates to TRUE.
X IS UNKNOWN BOOL BOOL Evaluates to TRUE if X evaluates to NULL. Otherwise evaluates to FALSE.
X IS NOT UNKNOWN BOOL BOOL Evaluates to FALSE if X evaluates to NULL. Otherwise, evaluates to TRUE.

IS DISTINCT FROM operator

expression_1 IS [NOT] DISTINCT FROM expression_2

Description

IS DISTINCT FROM returns TRUE if the input values are considered to be distinct from each other by the GROUP BY clause. Otherwise, returns FALSE.

a IS DISTINCT FROM b being TRUE is equivalent to:

a IS DISTINCT FROM b is equivalent to NOT (a = b), except for the following cases:

You can use this operation with fields in a complex data type, but not on the complex data types themselves. These complex data types can't be compared directly:

Input values:

Return type

BOOL

Examples

These return TRUE:

SELECT 1 IS DISTINCT FROM 2
SELECT 1 IS DISTINCT FROM NULL
SELECT 1 IS NOT DISTINCT FROM 1
SELECT NULL IS NOT DISTINCT FROM NULL

These return FALSE:

SELECT NULL IS DISTINCT FROM NULL
SELECT 1 IS DISTINCT FROM 1
SELECT 1 IS NOT DISTINCT FROM 2
SELECT 1 IS NOT DISTINCT FROM NULL

LIKE operator

expression [NOT] LIKE pattern

Description

LIKE returns TRUE if the string in the first operand expression matches a pattern specified by the second operand pattern, otherwise returns FALSE.

NOT LIKE returns TRUE if the string in the first operand expression doesn't match a pattern specified by the second operand pattern, otherwise returns FALSE.

Expressions can contain these characters:

This operator supports collation, but caveats apply:

Return type

BOOL

Examples

The following examples illustrate how you can check to see if the string in the first operand matches a pattern specified by the second operand.

-- Returns TRUE
SELECT 'apple' LIKE 'a%';
-- Returns FALSE
SELECT '%a' LIKE 'apple';
-- Returns FALSE
SELECT 'apple' NOT LIKE 'a%';
-- Returns TRUE
SELECT '%a' NOT LIKE 'apple';
-- Produces an error
SELECT NULL LIKE 'a%';
-- Produces an error
SELECT 'apple' LIKE NULL;

The following example illustrates how to search multiple patterns in an array to find a match with the LIKE operator:

WITH Words AS
 (SELECT 'Intend with clarity.' as value UNION ALL
  SELECT 'Secure with intention.' UNION ALL
  SELECT 'Clarity and security.')
SELECT value
FROM Words WHERE
  EXISTS(
    SELECT value FROM UNNEST(['%ity%', '%and%']) AS pattern
    WHERE value LIKE pattern
  );

/*------------------------+
 | value                  |
 +------------------------+
 | Intend with clarity.   |
 | Clarity and security.  |
 +------------------------*/

The following examples illustrate how collation can be used with the LIKE operator.

-- Returns FALSE
'Foo' LIKE '%foo%'
-- Returns TRUE
COLLATE('Foo', 'und:ci') LIKE COLLATE('%foo%', 'und:ci');
-- Returns TRUE
COLLATE('Foo', 'und:ci') = COLLATE('foo', 'und:ci');
-- Produces an error
COLLATE('Foo', 'und:ci') LIKE COLLATE('%foo%', 'binary');
-- Produces an error
COLLATE('Foo', 'und:ci') LIKE COLLATE('%f_o%', 'und:ci');
-- Returns TRUE
COLLATE('Foo_', 'und:ci') LIKE COLLATE('%foo\\_%', 'und:ci');

There are two capital forms of . We can use either SS or as upper case. While the difference between and is case difference (tertiary difference), the difference between sharp s and ss is secondary and considered not equal using the und:ci collator. For example:

-- Returns FALSE
'MASSE' LIKE 'Mae';
-- Returns FALSE
COLLATE('MASSE', 'und:ci') LIKE '%Mae%';
-- Returns FALSE
COLLATE('MASSE', 'und:ci') = COLLATE('Mae', 'und:ci');

The kana differences in Japanese are considered as tertiary or quaternary differences, and should be considered as equal in the und:ci collator with secondary strength.

For example:

-- Returns FALSE
'\u3042' LIKE '%\u30A2%';
-- Returns TRUE
COLLATE('\u3042', 'und:ci') LIKE COLLATE('%\u30A2%', 'und:ci');
-- Returns TRUE
COLLATE('\u3042', 'und:ci') = COLLATE('\u30A2', 'und:ci');

When comparing two strings, the und:ci collator compares the collation units based on the specification of the collation. Even though the number of code points is different, the two strings are considered equal when the collation units are considered the same.

In the following examples, the difference between '\u0061\u030A' and '\u00C5' is tertiary.

-- Returns FALSE
'\u0061\u030A' LIKE '%\u00C5%';
-- Returns TRUE
COLLATE('\u0061\u030A', 'und:ci') LIKE '%\u00C5%';
-- Returns TRUE
COLLATE('\u0061\u030A', 'und:ci') = COLLATE('\u00C5', 'und:ci');

In the following example, '\u0083' is a NO BREAK HERE character and is ignored.

-- Returns FALSE
'\u0083' LIKE '';
-- Returns TRUE
COLLATE('\u0083', 'und:ci') LIKE '';

Quantified LIKE operator

The quantified LIKE operator supports the following syntax:

search_value [NOT] LIKE quantifier patterns

quantifier:
 { ANY | SOME | ALL }

patterns:
  {
    (expression[, ...])
    UNNEST(array_expression)
  }

Description

Checks search_value for matches against several patterns. Each comparison is case-sensitive. Wildcard searches are supported. Semantic rules apply, but in general, LIKE returns TRUE if a matching pattern is found, FALSE if a matching pattern isn't found, or otherwise NULL. NOT LIKE returns FALSE if a matching pattern is found, TRUE if a matching pattern isn't found, or otherwise NULL.

Collation caveats

Collation is supported, but with the following caveats:

Semantics rules

When using the quantified LIKE operator with ANY or SOME, the following semantics apply in this order:

  1. Returns FALSE if patterns is empty.
  2. Returns NULL if search_value is NULL.
  3. Returns TRUE search_value LIKE pattern is TRUE for at least one value in patterns.
  4. Returns NULL if a pattern in patterns is NULL.
  5. Returns FALSE.

When using the quantified LIKE operator with ALL, the following semantics apply in this order:

  1. Returns TRUE if patterns is empty.
  2. Returns NULL if search_value is NULL.
  3. Returns FALSE if search_value LIKE pattern is FALSE for at least one value in patterns.
  4. Returns NULL if a pattern in patterns is NULL.
  5. Returns TRUE.

When using the quantified NOT LIKE operator with ANY or SOME, the following semantics apply in this order:

  1. Returns FALSE if patterns is empty.
  2. Returns NULL if search_value is NULL.
  3. Returns TRUE if search_value LIKE pattern is FALSE for at least one value in patterns.
  4. Returns NULL if a pattern in patterns is NULL.
  5. Returns FALSE.

When using the quantified NOT LIKE operator with ALL, the following semantics apply in this order:

  1. Returns TRUE if patterns is empty.
  2. For pattern_array, returns TRUE if patterns is empty.
  3. Returns NULL if search_value is NULL.
  4. Returns FALSE if search_value LIKE pattern is TRUE for at least one value in patterns.
  5. Returns NULL if a pattern in patterns is NULL.
  6. Returns TRUE.

Return Data Type

BOOL

Examples

You can use these WITH clauses to emulate temporary tables for Words in the following examples:

WITH Words AS
 (SELECT 'Intend with clarity.' as value UNION ALL
  SELECT 'Secure with intention.' UNION ALL
  SELECT 'Clarity and security.')

/*------------------------+
 | value                  |
 +------------------------+
 | Intend with clarity.   |
 | Secure with intention. |
 | Clarity and security.  |
 +------------------------*/

The following example checks to see if the Intend% or %intention% pattern exists in a value and produces that value if either pattern is found:

SELECT * FROM Words WHERE value LIKE ANY ('Intend%', '%intention%');

/*------------------------+
 | value                  |
 +------------------------+
 | Intend with clarity.   |
 | Secure with intention. |
 +------------------------*/

The following example checks to see if the %ity% pattern exists in a value and produces that value if the pattern is found.

Example with LIKE ALL:

SELECT * FROM Words WHERE value LIKE ALL ('%ity%');

/*-----------------------+
 | value                 |
 +-----------------------+
 | Intend with clarity.  |
 | Clarity and security. |
 +-----------------------*/

The following example checks to see if the %ity% pattern exists in a value produces that value if the pattern isn't found:

SELECT * FROM Words WHERE value NOT LIKE ('%ity%');

/*------------------------+
 | value                  |
 +------------------------+
 | Secure with intention. |
 +------------------------*/

You can pass in an array for patterns. For example:

SELECT * FROM Words WHERE value LIKE ANY UNNEST(['%ion%', '%and%']);

/*------------------------+
 | value                  |
 +------------------------+
 | Secure with intention. |
 | Clarity and security.  |
 +------------------------*/

The following queries illustrate some of the semantic rules for the quantified LIKE operator:

SELECT
  NULL LIKE ANY ('a', 'b'), -- NULL
  'a' LIKE ANY ('a', 'c'), -- TRUE
  'a' LIKE ANY ('b', 'c'), -- FALSE
  'a' LIKE ANY ('a', NULL), -- TRUE
  'a' LIKE ANY ('b', NULL), -- NULL
  NULL NOT LIKE ANY ('a', 'b'), -- NULL
  'a' NOT LIKE ANY ('a', 'b'), -- TRUE
  'a' NOT LIKE ANY ('a', '%a%'), -- FALSE
  'a' NOT LIKE ANY ('a', NULL), -- NULL
  'a' NOT LIKE ANY ('b', NULL); -- TRUE
SELECT
  NULL LIKE SOME ('a', 'b'), -- NULL
  'a' LIKE SOME ('a', 'c'), -- TRUE
  'a' LIKE SOME ('b', 'c'), -- FALSE
  'a' LIKE SOME ('a', NULL), -- TRUE
  'a' LIKE SOME ('b', NULL), -- NULL
  NULL NOT LIKE SOME ('a', 'b'), -- NULL
  'a' NOT LIKE SOME ('a', 'b'), -- TRUE
  'a' NOT LIKE SOME ('a', '%a%'), -- FALSE
  'a' NOT LIKE SOME ('a', NULL), -- NULL
  'a' NOT LIKE SOME ('b', NULL); -- TRUE
SELECT
  NULL LIKE ALL ('a', 'b'), -- NULL
  'a' LIKE ALL ('a', '%a%'), -- TRUE
  'a' LIKE ALL ('a', 'c'), -- FALSE
  'a' LIKE ALL ('a', NULL), -- NULL
  'a' LIKE ALL ('b', NULL), -- FALSE
  NULL NOT LIKE ALL ('a', 'b'), -- NULL
  'a' NOT LIKE ALL ('b', 'c'), -- TRUE
  'a' NOT LIKE ALL ('a', 'c'), -- FALSE
  'a' NOT LIKE ALL ('a', NULL), -- FALSE
  'a' NOT LIKE ALL ('b', NULL); -- NULL

The following queries illustrate some of the semantic rules for the quantified LIKE operator and collation:

SELECT
  COLLATE('a', 'und:ci') LIKE ALL ('a', 'A'), -- TRUE
  'a' LIKE ALL (COLLATE('a', 'und:ci'), 'A'), -- TRUE
  'a' LIKE ALL ('%A%', COLLATE('a', 'und:ci')); -- TRUE
-- ERROR: BYTES and STRING values can't be used together.
SELECT b'a' LIKE ALL (COLLATE('a', 'und:ci'), 'A');

Concatenation operator

The concatenation operator combines multiple values into one.

Function Syntax Input Data Type Result Data Type
STRING || STRING [ || ... ] STRING STRING
BYTES || BYTES [ || ... ] BYTES BYTES
ARRAY<T> || ARRAY<T> [ || ... ] ARRAY<T> ARRAY<T>
Note: The concatenation operator is translated into a nested CONCAT function call. For example, 'A' || 'B' || 'C' becomes CONCAT('A', CONCAT('B', 'C')).

WITH expression

WITH(variable_assignment[, ...], result_expression)

variable_assignment:
  variable_name AS expression

Description

Creates one or more variables. Each variable can be used in subsequent expressions within the WITH expression. Returns the value of result_expression.

Return Type

Requirements and Caveats

Examples

The following example first concatenates variable a with b, then variable b with c:

SELECT WITH(a AS '123',               -- a is '123'
            b AS CONCAT(a, '456'),    -- b is '123456'
            c AS '789',               -- c is '789'
            CONCAT(b, c)) AS result;  -- b + c is '123456789'

/*-------------+
 | result      |
 +-------------+
 | '123456789' |
 +-------------*/

In the following example, the volatile expression RAND() is evaluated once. The value of the result expression is always 0.0:

SELECT WITH(a AS RAND(), a - a);

/*---------+
 | result  |
 +---------+
 | 0.0     |
 +---------*/

Aggregate or analytic function results can be stored in variables.

SELECT WITH(s AS SUM(input), c AS COUNT(input), s/c)
FROM UNNEST([1.0, 2.0, 3.0]) AS input;

/*---------+
 | result  |
 +---------+
 | 2.0     |
 +---------*/

Variables can't be used in aggregate or analytic function call arguments.

SELECT WITH(diff AS a - b, AVG(diff))
FROM UNNEST([
              STRUCT(1 AS a, 2 AS b),
              STRUCT(3 AS a, 4 AS b),
              STRUCT(5 AS a, 6 AS b)
            ]);

-- ERROR: WITH variables like 'diff' can't be used in aggregate or analytic
-- function arguments.

A WITH expression is different from a WITH clause. The following example shows a query that uses both:

WITH my_table AS (
  SELECT 1 AS x, 2 AS y
  UNION ALL
  SELECT 3 AS x, 4 AS y
  UNION ALL
  SELECT 5 AS x, 6 AS y
)
SELECT WITH(a AS SUM(x), b AS COUNT(x), a/b) AS avg_x, AVG(y) AS avg_y
FROM my_table
WHERE x > 1;

/*-------+-------+
 | avg_x | avg_y |
 +-------+-------+
 | 4     | 5     |
 +-------+-------*/
Send feedback

Except as otherwise noted, the content of this page is licensed under the Creative Commons Attribution 4.0 License, and code samples are licensed under the Apache 2.0 License. For details, see the Google Developers Site Policies. Java is a registered trademark of Oracle and/or its affiliates.

Last updated 2026-08-11 UTC.

Need to tell us more? [[["Easy to understand","easyToUnderstand","thumb-up"],["Solved my problem","solvedMyProblem","thumb-up"],["Other","otherUp","thumb-up"]],[["Hard to understand","hardToUnderstand","thumb-down"],["Incorrect information or sample code","incorrectInformationOrSampleCode","thumb-down"],["Missing the information/samples I need","missingTheInformationSamplesINeed","thumb-down"],["Other","otherDown","thumb-down"]],["Last updated 2026-08-11 UTC."],[],[]]

Web Proxy Viewer  |  New URL  |  Original Page