Une instruction SQL Cloud Spanner comprend une série de jetons. Les jetons incluent les éléments suivants : identifiants, identifiants entre guillemets, littéraux, mots clés, opérateurs et caractères spéciaux. Vous pouvez séparer les jetons par un espace blanc (par exemple, une espace, un retour arrière, une tabulation, un retour à la ligne) ou des commentaires.
Identifiants
Les identifiants sont des noms associés à des colonnes, des tables et d'autres objets de base de données. Ils peuvent être entre guillemets ou sans guillemets.
- Les identifiants peuvent être utilisés dans les expressions de chemin, qui renvoient une valeur
STRUCT
. - Certains identifiants sont sensibles à la casse et d'autres non. Pour en savoir plus, consultez la section Sensibilité à la casse.
- Les identifiants sans guillemets doivent commencer par une lettre ou un trait de soulignement. Les autres caractères peuvent être des lettres, des chiffres ou des traits de soulignement.
- Les identifiants entre guillemets doivent être délimités par des accents graves (`).
- Les identifiants entre guillemets peuvent contenir n'importe quel caractère (tel que des espaces ou des symboles).
- Ils ne peuvent cependant pas être vides.
- Les identifiants entre guillemets ont les mêmes séquences d'échappement que les littéraux de chaîne.
- Un mot clé réservé doit être un identifiant entre guillemets s'il s'agit d'un mot clé autonome ou du premier composant d'une expression de chemin. Lorsqu'il n'est pas le premier composant d'une expression de chemin (donc à partir du deuxième composant), il peut ne pas être entre guillemets.
Exemples
Les identifiants suivants sont valides :
Customers5
`5Customers`
dataField
_dataField1
ADGROUP
`tableName~`
`GROUP`
Les expressions de chemin suivantes contiennent des identifiants valides :
foo.`GROUP`
foo.GROUP
foo().dataField
list[OFFSET(3)].dataField
list[ORDINAL(3)].dataField
@parameter.dataField
Les identifiants suivants ne sont pas valides :
5Customers
_dataField!
GROUP
5Customers
commence par un chiffre, et non par une lettre ou un trait de soulignement. _dataField!
contient le caractère spécial "!" qui ne correspond pas à une lettre, un chiffre ou un trait de soulignement.
GROUP
est un mot clé réservé et ne peut donc être utilisé comme identifiant s'il n'est pas délimité par des accents graves.
Littéraux
Un littéral représente une valeur constante d'un type de données intégré. Certains types de données, mais pas tous, peuvent être exprimés sous forme de littéraux.
Littéraux de chaîne et d'octets
Les littéraux de chaîne et d'octets doivent être placés entre guillemets simples ('
) ou doubles ("
), ou bien entre guillemets triples avec des groupes de trois guillemets simples ('''
) ou doubles ("""
).
Littéraux entre guillemets :
Littéral | Exemples | Description |
---|---|---|
Chaîne entre guillemets |
|
Les chaînes entre guillemets simples (' ) peuvent contenir des guillemets doubles (" ) non échappés, et inversement. Les barres obliques inverses ( \ ) introduisent des séquences d'échappement. Consultez le tableau des séquences d'échappement ci-dessous.Les chaînes entre guillemets ne peuvent pas contenir de retour à la ligne, même lorsqu'elles sont précédées d'une barre oblique inverse ( \ ). |
Chaîne entre guillemets triples |
|
Les retours à la ligne et les guillemets intégrés sont autorisés sans échappement (voir le quatrième exemple). Les barres obliques inverses ( \ ) introduisent des séquences d'échappement. Consultez le tableau des séquences d'échappement ci-dessous.Une barre oblique inverse ( \ ) non échappée ne peut pas être placée à la fin d'une ligne.Marquez la fin de la chaîne par trois guillemets non échappés consécutifs correspondant aux guillemets de début. |
Chaîne brute |
|
Les littéraux entre guillemets (simples, doubles ou triples) qui comportent le préfixe de littéral de chaîne brute (r ou R ) sont interprétés comme des chaînes brutes ou d'expressions régulières.Les barres obliques inverses ( \ ) ne font pas office de caractères d'échappement. Si une barre oblique inverse suivie d'un autre caractère figure à l'intérieur du littéral de chaîne, les deux caractères sont conservés.Une chaîne brute ne peut pas se terminer par un nombre impair de barres obliques inverses. Les chaînes brutes sont utiles pour créer des expressions régulières. |
Les caractères de préfixe (r
, R
, b
et B)
) sont facultatifs pour les chaînes entre guillemets simples, doubles ou triples. Ils indiquent que ces dernières correspondent respectivement à des chaînes brutes/d'expressions régulières ou à une séquence d'octets. Par exemple, les chaînes b'abc'
et b'''abc'''
sont toutes deux interprétées comme des octets. Les caractères de préfixe ne sont pas sensibles à la casse.
Littéraux entre guillemets comportant des préfixes :
Littéral | Exemple | Description |
---|---|---|
Bytes |
|
Les littéraux entre guillemets (simples, doubles ou triples) qui comportent le préfixe de littéral d'octets (b ou B ) sont interprétés comme des octets. |
Octets bruts |
|
Les préfixes r et b peuvent être combinés dans n'importe quel ordre. Par exemple, rb'abc*' correspond à br'abc*' . |
Le tableau ci-dessous répertorie toutes les séquences d'échappement valides permettant de représenter des caractères non alphanumériques dans des littéraux de chaîne et d'octets. Toute séquence ne figurant pas dans ce tableau génère une erreur.
Séquence d'échappement | Description |
---|---|
\a |
Caractère d'appel audible |
\b |
Retour arrière |
\f |
Saut de page |
\n |
Retour à la ligne |
\r |
Retour chariot |
\t |
Tabulation |
\v |
Tabulation verticale |
\\ |
Barre oblique inverse (\ ) |
\? |
Point d'interrogation (? ) |
\" |
Guillemet double (" ) |
\' |
Guillemet simple (' ) |
\` |
Accent grave (` ) |
\ooo |
Échappement octal, avec exactement trois chiffres (dans la plage 0 à 7). Décodage sous la forme d'un seul caractère Unicode (dans les littéraux de chaîne) ou d'un octet (dans les littéraux d'octets). |
\xhh ou \Xhh |
Échappement hexadécimal, avec exactement deux chiffres hexadécimaux (0 à 9, A à F, ou a à f). Décodage sous la forme d'un seul caractère Unicode (dans les littéraux de chaîne) ou d'un octet (dans les littéraux d'octets). Exemples :
|
\uhhhh |
Échappement Unicode, avec la lettre minuscule "u" et exactement quatre chiffres hexadécimaux. Valable uniquement dans les littéraux de chaîne ou les identifiants. La plage D800 à DFFF n'est pas autorisée, car elle correspond à des valeurs Unicode de substitution. |
\Uhhhhhhhh |
Échappement Unicode, avec la lettre majuscule "U" et exactement huit chiffres hexadécimaux. Valable uniquement dans les littéraux de chaîne ou les identifiants. La plage D800 à DFFF n'est pas autorisée, car elle correspond à des valeurs Unicode de substitution. De plus, les valeurs supérieures à 10FFFF ne sont pas autorisées. |
Littéraux entiers
Les littéraux entiers correspondent à une séquence de chiffres décimaux (0 à 9) ou à une valeur hexadécimale précédée du préfixe "0x
" ou "0X
". Les nombres entiers peuvent être précédés du préfixe "+
" ou "-
" pour représenter respectivement des valeurs positives et négatives.
Exemples :
123
0xABC
-123
Un littéral entier est interprété comme un type de données INT64
.
Littéraux numériques (NUMERIC)
Vous pouvez créer des littéraux numériques (NUMERIC) à l'aide du mot clé NUMERIC
, suivi d'une valeur à virgule flottante entre guillemets.
Exemples :
SELECT NUMERIC '0';
SELECT NUMERIC '123456';
SELECT NUMERIC '-3.14';
SELECT NUMERIC '-0.54321';
SELECT NUMERIC '1.23456e05';
SELECT NUMERIC '-9.876e-3';
Littéraux à virgule flottante
Options de syntaxe :
[+-]DIGITS.[DIGITS][e[+-]DIGITS]
[DIGITS].DIGITS[e[+-]DIGITS]
DIGITSe[+-]DIGITS
DIGITS
représente un ou plusieurs chiffres décimaux (0 à 9). e
désigne le marqueur d'exposant (e ou E).
Exemples :
123.456e-67
.1E4
58.
4e2
Les littéraux numériques qui contiennent un symbole décimal ou un marqueur d'exposant sont supposés être de type "double".
La conversion implicite des littéraux à virgule flottante en type "float" est possible si la valeur est comprise dans la plage valide de valeurs à virgule flottante.
Il n'existe pas de représentation littérale de NaN ou de l'infini. Toutefois, les chaînes suivantes qui ne sont pas sensibles à la casse peuvent être explicitement converties en valeurs de type "float" :
- "NaN"
- "inf" ou "+inf"
- "-inf"
Littéraux de tableau
Les littéraux de tableau correspondent à des listes d'éléments séparés par une virgule et placés entre crochets. Le mot clé ARRAY
est facultatif. Un type d'élément explicite T est également facultatif.
Exemples :
[1, 2, 3]
['x', 'y', 'xy']
ARRAY[1, 2, 3]
ARRAY<string>['x', 'y', 'xy']
ARRAY<int64>[]
Littéraux de structure
Syntaxe :
(elem[, elem...])
où elem
est un élément de la structure. elem
doit correspondre à un type de données littéral, et non à une expression ou à un nom de colonne.
Le type de résultat est un type de structure anonyme (les structures n'étant pas des types nommés) comportant des champs anonymes dont les types correspondent à ceux des expressions d'entrée.
Exemple | Type de sortie |
---|---|
(1, 2, 3) |
STRUCT<int64,int64,int64> |
(1, 'abc') |
STRUCT<int64,string> |
Littéraux de date
Syntaxe :
DATE 'YYYY-M[M]-D[D]'
Les littéraux de date contiennent le mot clé DATE
, suivi d'un littéral de chaîne qui est conforme au format de date canonique et délimité par des guillemets simples. Ils acceptent une plage comprise entre 1 et 9 999 (inclus). Les dates situées en dehors de cette plage ne sont pas valides.
Par exemple, le littéral de date suivant représente le 27 septembre 2014 :
DATE '2014-09-27'
Les littéraux de chaîne au format de date canonique sont également convertis implicitement en littéraux de type DATE lorsqu'ils sont utilisés là où une expression de type DATE est attendue. Prenons l'exemple de la requête suivante :
SELECT * FROM foo WHERE date_col = "2014-09-27"
Le littéral de chaîne "2014-09-27"
est converti implicitement en littéral de date.
Littéraux d'horodatage
Syntaxe :
TIMESTAMP 'YYYY-[M]M-[D]D [[H]H:[M]M:[S]S[.DDDDDD] [timezone]]'
Les littéraux d'horodatage contiennent le mot clé TIMESTAMP
ainsi qu'un littéral de chaîne qui est conforme au format d'horodatage canonique et délimité par des guillemets simples.
Ils acceptent une plage comprise entre 1 et 9 999 (inclus). Les horodatages situés en dehors de cette plage ne sont pas valides.
Un littéral d'horodatage peut inclure un suffixe numérique pour indiquer le fuseau horaire :
TIMESTAMP '2014-09-27 12:30:00.45-08'
Si ce suffixe est absent, le fuseau horaire par défaut (America/Los_Angeles) est utilisé.
Par exemple, l'horodatage suivant correspond au 27 septembre 2014 à 12h30 dans le fuseau horaire par défaut (America/Los_Angeles) :
TIMESTAMP '2014-09-27 12:30:00.45'
Pour plus d'informations sur les fuseaux horaires, consultez la section Fuseau horaire.
Les littéraux de chaîne utilisant le format d'horodatage canonique, y compris ceux comportant des noms de fuseau horaire, sont convertis implicitement en littéraux d'horodatage lorsqu'ils sont utilisés là où une expression d'horodatage est attendue. Par exemple, dans la requête suivante, le littéral de chaîne "2014-09-27 12:30:00.45 America/Los_Angeles"
est converti implicitement en littéral d'horodatage :
SELECT * FROM foo
WHERE timestamp_col = "2014-09-27 12:30:00.45 America/Los_Angeles"
Un littéral d'horodatage peut inclure les caractères facultatifs suivants :
T
out
: option de temps. À utiliser comme séparateur entre la date et l'heure.Z
ouz
: option du fuseau horaire par défaut. Vous ne pouvez pas l'utiliser avec[timezone]
.
Si vous utilisez l'un de ces caractères, vous ne pouvez pas insérer d'espace ni avant, ni après. Les exemples suivants sont valides :
TIMESTAMP '2017-01-18T12:34:56.123456Z'
TIMESTAMP '2017-01-18t12:34:56.123456'
TIMESTAMP '2017-01-18 12:34:56.123456z'
TIMESTAMP '2017-01-18 12:34:56.123456Z'
Fuseau horaire
Étant donné que les littéraux d'horodatage doivent être mappés avec un instant précis, un fuseau horaire est nécessaire pour les interpréter correctement. Si aucun fuseau horaire n'est spécifié dans le littéral lui-même, la valeur de fuseau horaire par défaut, qui est définie par l'implémentation du langage SQL de Cloud Spanner, est utilisée.
Le langage SQL de Cloud Spanner représente les fuseaux horaires par des chaînes au format canonique présenté ci-dessous, qui représente le décalage par rapport au temps universel coordonné (UTC).
Format :
(+|-)H[H][:M[M]]
Exemples :
'-08:00'
'-8:15'
'+3:00'
'+07:30'
'-7'
Les fuseaux horaires peuvent également être exprimés à l'aide de noms de type chaîne figurant dans la base de données tz. Pour obtenir des informations de référence moins complètes, mais plus simples, consultez l'article Wikipedia List of tz database time zones (Liste des fuseaux horaires de la base de données tz). Les noms de fuseaux horaires canoniques utilisent le format <continent/[region/]city>
(par exemple, America/Los_Angeles
).
Exemple :
TIMESTAMP '2014-09-27 12:30:00 America/Los_Angeles'
TIMESTAMP '2014-09-27 12:30:00 America/Argentina/Buenos_Aires'
Sensibilité à la casse
Le langage SQL de Cloud Spanner respecte les règles ci-dessous concernant la sensibilité à la casse.
Catégorie | Sensibilité à la casse | Remarques |
---|---|---|
Mots clés | Non | |
Noms des fonctions | Non | |
Noms de table | Voir les remarques | Les noms de table ne sont généralement pas sensibles à la casse. La sensibilité à la casse peut toutefois s'appliquer lors de l'interrogation d'une base de données utilisant des noms de table sensibles à la casse. |
Noms de colonne | Non | |
Valeurs de chaîne | Oui | |
Comparaisons de chaînes | Oui | |
Alias utilisés dans une requête | Non | |
Correspondances d'expressions régulières | Voir les remarques | Les correspondances d'expressions régulières sont par défaut sensibles à la casse, sauf si l'expression elle-même spécifie qu'elle ne doit pas l'être. |
Correspondances LIKE |
Oui |
Mots clés réservés
Les mots clés correspondent à un groupe de jetons qui ont une signification particulière dans le langage SQL de Cloud Spanner et présentent les caractéristiques suivantes :
- Ils ne peuvent pas être utilisés comme identifiants, sauf s'ils sont délimités par des accents graves (`).
- Ils ne sont pas sensibles à la casse.
Le langage SQL de Cloud Spanner utilise les mots clés réservés ci-dessous.
ALL AND ANY ARRAY AS ASC ASSERT_ROWS_MODIFIED AT BETWEEN BY CASE CAST COLLATE CONTAINS CREATE CROSS CUBE CURRENT DEFAULT DEFINE DESC DISTINCT ELSE END |
ENUM ESCAPE EXCEPT EXCLUDE EXISTS EXTRACT FALSE FETCH FOLLOWING FOR FROM FULL GROUP GROUPING GROUPS HASH HAVING IF IGNORE IN INNER INTERSECT INTERVAL INTO |
IS JOIN LATERAL LEFT LIKE LIMIT LOOKUP MERGE NATURAL NEW NO NOT NULL NULLS OF ON OR ORDER OUTER OVER PARTITION PRECEDING PROTO RANGE |
RECURSIVE RESPECT RIGHT ROLLUP ROWS SELECT SET SOME STRUCT TABLESAMPLE THEN TO TREAT TRUE UNBOUNDED UNION UNNEST USING WHEN WHERE WINDOW WITH WITHIN |
Points-virgules de fin
Vous pouvez éventuellement utiliser un point-virgule de fin (;
) lorsque vous envoyez une instruction de chaîne de requête via une interface de programmation d'application (API).
Dans une requête contenant plusieurs instructions, ces dernières doivent être séparées par un point-virgule. Toutefois, celui-ci est généralement facultatif pour l'instruction finale. Certains outils interactifs requièrent que les instructions incluent un point-virgule de fin.
Virgules de fin
Vous pouvez éventuellement utiliser une virgule de fin (,
) à la fin d'une liste de colonnes dans une instruction SELECT
. Vous pouvez avoir une virgule finale en raison de la création automatisée d'une liste de colonnes.
Exemple
SELECT name, release_date, FROM Books
Paramètres de requête
Vous pouvez utiliser des paramètres de requête pour remplacer des expressions arbitraires. Toutefois, vous ne pouvez pas utiliser les paramètres de requête en remplacement d'identifiants, de noms de colonne, de noms de table ou d'autres parties d'une requête. Les paramètres de requête sont définis en dehors de l'instruction de requête.
Les API clientes permettent de lier des noms de paramètres à des valeurs. Le moteur de requête remplace un paramètre par une valeur liée au moment de l'exécution.
Paramètres de requête nommés
Syntaxe :
@parameter_name
Un paramètre de requête nommé est désigné à l'aide d'un identifiant précédé du caractère @
.
Exemple :
Cet exemple renvoie toutes les lignes où LastName
est égal à la valeur du paramètre de requête nommé myparam
.
SELECT * FROM Roster WHERE LastName = @myparam
Astuces
@{ hint [, ...] }
hint:
[engine_name.]hint_name = value
L'objectif d'une optimisation est de modifier la stratégie d'exécution d'une requête sans modifier le résultat de la requête. Les optimisations n'affectent généralement pas la sémantique des requêtes, mais peuvent avoir des conséquences sur les performances. Ces types d'optimisations sont disponibles :
- Optimisations relatives aux JOINTURES
- Optimisations relatives aux INSTRUCTIONS
- Optimisations relatives aux TABLES
La syntaxe d'optimisation nécessite le caractère @
suivi d'accolades.
Vous pouvez créer une optimisation ou un groupe d'optimisations. Le préfixe facultatif engine_name.
permet à plusieurs moteurs de définir des optimisations avec le même hint_name
.
Ceci est important si vous devez suggérer différentes stratégies d'exécution spécifiques au moteur ou si différents moteurs prennent en charge différentes optimisations.
Vous pouvez attribuer des identifiants et des littéraux aux optimisations.
- Les identifiants sont utiles pour les optimisations destinées à agir comme des énumérations.
Vous pouvez utiliser un identifiant pour éviter d'utiliser une chaîne entre guillemets.
Dans l'AST résolue, les optimisations d'identifiants sont représentées sous forme de littéraux de chaîne. Par conséquent,
@{hint="abc"}
est identique à@{hint=abc}
. Les optimisations d'identifiant peuvent également être utilisées pour les optimisations qui prennent un nom de tableau ou une colonne en tant qu'identifiant unique. - Les littéraux NULL sont autorisés et sont déduits sous forme d'entiers.
Les optimisations sont destinées à s'appliquer uniquement au nœud auquel elles sont associées, et non à un champ d'application plus large.
Par exemple, une optimisation sur un JOIN
au milieu de la clause FROM
est destiné à s'appliquer uniquement à ce JOIN
, et non aux autres JOIN
de la clause FROM
.
Les optimisations au niveau de l'instruction peuvent être utilisées pour les optimisations qui modifient l'exécution d'une instruction complète, par exemple un budget de mémoire global ou un délai.
Exemples
Dans cet exemple, un littéral est attribué à une optimisation. Cette optimisation n'est utilisée qu'avec deux moteurs de base de données appelés database_engine_a
et database_engine_b
.
La valeur de l'optimisation est différente pour chaque moteur de base de données.
@{ database_engine_a.file_count=23, database_engine_b.file_count=10 }
Dans cet exemple, un identifiant est attribué à une optimisation. Il existe des identifiants uniques pour chaque type d'optimisation. Vous pouvez afficher la liste des types d'optimisation au début de cette rubrique.
@{ JOIN_METHOD=HASH_JOIN }
Comments
Les commentaires sont des séquences de caractères ignorées par l'analyseur. Le langage SQL de Cloud Spanner accepte les types de commentaires ci-dessous.
Commentaires sur une seule ligne
Utilisez un commentaire sur une seule ligne si vous souhaitez qu'il apparaisse seul sur une ligne.
Exemples
# this is a single-line comment
SELECT book FROM library;
-- this is a single-line comment
SELECT book FROM library;
/* this is a single-line comment */
SELECT book FROM library;
SELECT book FROM library
/* this is a single-line comment */
WHERE book = "Ulysses";
Commentaires intégrés
Utilisez un commentaire intégré si vous souhaitez qu'il apparaisse sur la même ligne qu'une instruction. Un commentaire précédé de #
ou --
doit apparaître à droite d'une instruction.
Exemples
SELECT book FROM library; # this is an inline comment
SELECT book FROM library; -- this is an inline comment
SELECT book FROM library; /* this is an inline comment */
SELECT book FROM library /* this is an inline comment */ WHERE book = "Ulysses";
Commentaires multilignes
Utilisez un commentaire multiligne si vous souhaitez qu'il s'étende sur plusieurs lignes. Les commentaires multilignes imbriqués ne sont pas acceptés.
Exemples
SELECT book FROM library
/*
This is a multiline comment
on multiple lines
*/
WHERE book = "Ulysses";
SELECT book FROM library
/* this is a multiline comment
on two lines */
WHERE book = "Ulysses";