SQL 資料類型規則
適用于: Databricks SQL Databricks Runtime
Azure Databricks 會使用數個規則來解決資料類型之間的衝突:
您也可以在許多類型之間明確轉換:
類型升級
類型升級是將類型轉換成相同類型系列的另一種類型的程式,其中包含原始類型的所有可能值。
因此,類型升級是安全的作業。 例如 TINYINT
,範圍從 -128
到 127
。 其所有可能的值都可以安全地升階為 INTEGER
。
類型優先順序清單
類型優先順序清單會定義指定的資料類型值是否可以隱含地升級為另一個資料類型。
資料類型 | 優先順序清單 (範圍從最窄到最寬的) |
---|---|
TINYINT | TINYINT - SMALLINT - > INT - >> BIGINT - > DECIMAL - > FLOAT (1) - > DOUBLE |
SMALLINT | SMALLINT - INT - > BIGINT - >> DECIMAL - > FLOAT (1) - > DOUBLE |
Int | INT - BIGINT - > DECIMAL - >> FLOAT (1) - > DOUBLE |
BIGINT | BIGINT - DECIMAL - >> FLOAT (1) - > DOUBLE |
十進位 | DECIMAL - > FLOAT (1) - > DOUBLE |
浮動 | FLOAT (1) - > DOUBLE |
雙 | 雙 |
日期 | DATE - > TIMESTAMP |
時間 戳 | 時間 戳 |
陣 列 | ARRAY (2) |
二 進 制 | 二 進 制 |
布林 | 布林 |
區間 | 區間 |
地圖 | MAP (2) |
字串 | 字串 |
結構 | STRUCT (2) |
(1) 針對 最不常見的類型解析 FLOAT,會略過以避免遺失精確度。
(2) 對於複雜類型,優先順序規則會以遞迴方式套用至其元件元素。
字串和 Null
特殊規則適用于 STRING
和 不具 NULL
類型的 :
NULL
可以升階為任何其他類型。STRING
可以升階為BIGINT
、BINARY
、BOOLEAN
、DATE
、DOUBLE
、INTERVAL
和TIMESTAMP
。 如果實際字串值無法轉換成 最低通用類型 Azure Databricks,就會引發執行階段錯誤。 升級至INTERVAL
字串值時,必須符合間隔單位。
類型優先順序圖表
這是優先順序階層的圖形描述,結合 類型優先順序清單 和 字串和 Nulls 規則。
最不常見的類型解析
一組型別中最不常見的型別是類型優先順序圖表中所有元素都能從 類型優先順序圖表 連線到的最窄型別。
最不常見的類型解析是用來:
- 決定是否可以使用較窄型別的引數來叫用預期指定型別參數的函式。
- 衍生函式的引數類型,該函式需要多個參數的共用引數類型,例如 聯合、 in、 least或 greatest。
- 針對算數運算或比較等運算子衍生運算元類型。
- 衍生案例 運算式等運算式的結果類型。
- 衍生 陣列 和 對應 建構函式的專案、索引鍵或實值型別。
- 衍生 UNION、INTERSECT 或 EXCEPT set 運算子的結果類型。
如果最通用的類型解析為 FLOAT
,則會套用特殊規則。 如果任何參與型別是確切的數數值型別, (TINYINT
、 SMALLINT
、 INTEGER
、 BIGINT
或 DECIMAL
) 會推送最不常見的類型, DOUBLE
以避免遺失數位。
隱含下播和跨播
Azure Databricks 只會在函式和運算子叫用上採用這些形式的隱含轉型,而且只有在可以明確判斷意圖的位置。
隱含下播
隱含向下傳播會自動將較寬的類型轉換成較窄的類型,而不需要明確指定轉換。 向下傳播很方便,但如果實際值無法在窄型別中表示,則會有非預期執行時間錯誤的風險。
向下傳播會以反向順序套用 類型優先順序清單 。
隱含跨播
隱含交叉傳播會將某個類型系列的值轉換成另一個類型系列,而不需要明確指定轉換。
Azure Databricks 支援下列來源的隱含交叉傳送:
- 除了 以外的
BINARY
任何簡單型別,到STRING
除外。 STRING
任何簡單類型的 。
- 除了 以外的
在函式調用上轉型
假設有已解析的函式或運算子,下列規則會依每個參數和引數組的順序套用:
如果支援的參數類型屬於引數 的類型優先順序圖表,Azure Databricks 會將引數 升 階為該參數類型。
在大部分情況下,函式描述會明確指出支援的型別或鏈結,例如「任何數數值型別」。
例如, sin (expr) 運作
DOUBLE
,但會接受任何數值。如果預期的參數類型為 ,
STRING
且引數為簡單類型 Azure Databricks 會將引數 交叉傳送 至字串參數類型。例如, 子字串 (str、start、len) 預期
str
為STRING
。 相反地,您可以傳遞數值或日期時間類型。如果引數類型為 ,
STRING
且預期的參數類型為簡單型別,Azure Databricks 會將字串引數 交叉傳送 至最廣泛的支援參數類型。例如, date_add (日期、) 預期
DATE
為 和INTEGER
。如果您使用兩
STRING
個 s 來叫date_add()
用,Azure Databricks 會將第一個STRING
交叉傳送至DATE
,而第二STRING
個INTEGER
會交叉傳送至 。如果函式需要數數值型別,例如
INTEGER
或DATE
型別,但引數是較通用的類型,例如DOUBLE
或TIMESTAMP
,則 Azure Databricks 會隱含 地將引數向下傳播 至該參數類型。例如, date_add (日期、) 預期
DATE
為 和INTEGER
的天數。如果您使用 和
BIGINT
叫date_add()
用TIMESTAMP
,Azure Databricks 會藉由移除時間元件和 ,BIGINT
將 向下傳播TIMESTAMP
DATE
至INTEGER
。否則,Azure Databricks 會引發錯誤。
例子
只要聯合函式共用最不通用的類型,聯合函式就會接受任何一組引數類型。
結果類型是引數的最低常見類型。
-- The least common type of TINYINT and BIGINT is BIGINT
> SELECT typeof(coalesce(1Y, 1L, NULL));
BIGINT
-- INTEGER and DATE do not share a precedence chain or support crosscasting in either direction.
> SELECT typeof(coalesce(1, DATE'2020-01-01'));
Error: Incompatible types [INT, DATE]
-- Both are ARRAYs and the elements have a least common type
> SELECT typeof(coalesce(ARRAY(1Y), ARRAY(1L)))
ARRAY<BIGINT>
-- The least common type of INT and FLOAT is DOUBLE
> SELECT typeof(coalesce(1, 1F))
DOUBLE
> SELECT typeof(coalesce(1L, 1F))
DOUBLE
> SELECT typeof(coalesce(1BD, 1F))
DOUBLE
-- The least common type between an INT and STRING is BIGINT
> SELECT typeof(coalesce(5, '6'));
BIGINT
-- The least common type is a BIGINT, but the value is not BIGINT.
> SELECT coalesce('6.1', 5);
Error: 6.1 is not a BIGINT
-- The least common type between a DECIMAL and a STRING is a DOUBLE
> SELECT typeof(coalesce(1BD, '6'));
DOUBLE
子字串函式預期字串的類型 STRING
引數,以及 INTEGER
開始和長度參數的引數。
-- Promotion of TINYINT to INTEGER
> SELECT substring('hello', 1Y, 2);
he
-- No casting
> SELECT substring('hello', 1, 2);
he
-- Casting of a literal string
> SELECT substring('hello', '1', 2);
he
-- Downcasting of a BIGINT to an INT
> SELECT substring('hello', 1L, 2);
he
-- Crosscasting from STRING to INTEGER
> SELECT substring('hello', str, 2)
FROM VALUES(CAST('1' AS STRING)) AS T(str);
he
-- Crosscasting from INTEGER to STRING
> SELECT substring(12345, 2, 2);
23
|| (CONCAT) 允許隱含交叉傳送至字串。
-- A numeric is cast to STRING
> SELECT 'This is a numeric: ' || 5.4E10;
This is a numeric: 5.4E10
-- A date is cast to STRING
> SELECT 'This is a date: ' || DATE'2021-11-30';
This is a date: 2021-11-30
date_add可以使用 或 BIGINT
叫用 TIMESTAMP
,因為隱含的下播。
> SELECT date_add(TIMESTAMP'2011-11-30 08:30:00', 5L);
2011-12-05
date_add 可以透過 叫用 , STRING
因為隱含的交叉傳送。
> SELECT date_add('2011-11-30 08:30:00', '5');
2011-12-05