SQL
Identifiers
Similarly to other SQL dialects and programming languages, identifiers in DuckDB's SQL are subject to several rules.  
* Unquoted identifiers need to conform to a number of rules:
* They must not be a reserved keyword (see [`duckdb_keywords()`](#docs:sql:meta:duckdb_table_functions::duckdb_keywords)), e.g., `SELECT 123 AS SELECT` will fail.
* They must not start with a number or special character, e.g., `SELECT 123 AS 1col` is invalid.
* They cannot contain whitespaces (including tabs and newline characters).
* Identifiers can be quoted using double-quote characters (` "`). Quoted identifiers can use any keyword, whitespace or special character, e.g., `"SELECT"` and `" § 🦆 ¶ "` are valid identifiers.
* Double quotes can be escaped by repeating the quote character, e.g., to create an identifier named `IDENTIFIER "X"`, use `"IDENTIFIER ""X"""`.  
#### Deduplicating Identifiers {#docs:sql:dialect:keywords_and_identifiers::deduplicating-identifiers}  
In some cases, duplicate identifiers can occur, e.g., column names may conflict when unnesting a nested data structure.
In these cases, DuckDB automatically deduplicates column names by renaming them according to the following rules:  
* For a column named `⟨name⟩`, the first instance is not renamed.
* Subsequent instances are renamed to `⟨name⟩_⟨count⟩`, where `⟨count⟩` starts at 1.  
For example:  
```sql
SELECT *
FROM (SELECT UNNEST({'a': 42, 'b': {'a': 88, 'b': 99}}, recursive := true));
```  
| a  | a_1 | b  |
|---:|----:|---:|
| 42 | 88  | 99 |