数据类型
boolean
只有True
和False
两个值的布尔类型。
举例
SELECT True, False, boolean(3.6), boolean(-3), boolean(0)
输出结果为
true false CAST(3.6 AS BOOLEAN) CAST(-3 AS BOOLEAN) CAST(0 AS BOOLEAN)
True False True True False
可以看到非0的数值类型都可以转换为True
。
tinyint
长度为一个字节的有符号整型。
范围
[-128, 127]
举例
SELECT cast(128 as tinyint)
输出结果为
CAST(128 AS TINYINT)
-128
smallint
长度为两个字节的有符号整型。
范围
[-32768, 32767]
举例
SELECT smallint(32769)
输出结果为
CAST(32768 AS SMALLINT)
-32768
int
长度为四个字节的有符号整型。
范围
[-2147483648, 2147483647]
举例
SELECT int(2147483648), int(2147483647)
输出结果为
CAST(2147483648 AS INT) CAST(2147483647 AS INT)
-2147483648 2147483647
bigint
长度为8个字节的有符号整型。
范围
[-9223372036854775808, 9223372036854775807]
举例
SELECT bigint(9223372036854775808), bigint(9223372036854775807)
输出结果为
CAST(9223372036854775808 AS BIGINT) CAST(9223372036854775807 AS BIGINT)
-9223372036854775808 9223372036854775807
float
长度为4字节的浮点类型。
范围
-3.40E+38 ~ +3.40E+38
举例
SELECT float(3), float(3.4e38), float(-3.5e38)
输出结果为
CAST(3 AS FLOAT) CAST(3.4E+38 AS FLOAT) CAST(-3.5E+38 AS FLOAT)
3.0 3.400000e+38 -Infinity
double
长度为8字节的浮点类型。
范围
-1.79E+308 ~ +1.79E+308
举例
SELECT double(3), double(-1.79E+308), float(1.8E+308)
输出结果为
CAST(3 AS DOUBLE) CAST(-1.79E+308 AS DOUBLE) CAST(1.8E+308 AS FLOAT)
3.0 -1.790000e+308 Infinity
decimal
decimal(p, s)
保证精度的小数类型。p
代表一共有多少个有效数字,s
代表小数点后最多有多少数字。所以s
的值必须小于等于p
。比如3.14159
一共有6位有效数字,小数点后有5位数字。p
的默认值为10,s
的默认值为0。p
和s
都可以省略,也可以单独省略s
。
范围
p
的范围为1 ~ 38
,s
的范围为0 ~ p
。
举例
SELECT cast(13.4 as decimal(10)), cast(13.4 as decimal(10,1)), decimal(3.14)
输出结果为
CAST(13.4 AS DECIMAL(10,0)) CAST(13.4 AS DECIMAL(10,1)) CAST(3.14 AS DECIMAL(10,0))
13 13.4 3
string
UTF8编码的字符串,这里没有像其他数据库那样的定长、变长之分。另外,常见的文件格式,比如csv,Parquet,ORC等都是支持变长字符串的。
举例
SELECT string(3), string(Array(3.4)), "中文"
输出结果为
CAST(3 AS STRING) CAST(array(3.4) AS STRING) 中文
3 [3.4] 中文
char, varchar
这两个类型主要用来兼容Hive中的类型,在实际运算时,都会自动转换为string
类型。所以不建议在Pingo中建表时使用这两个类型。
举例
SELECT cast("abcdef" as varchar(3)), cast("123456" as char(3))
输出结果为
CAST(abcdef AS STRING) CAST(123456 AS STRING)
abcdef 123456
可以看到长度参数都被自动忽略了。
binary
字节数组,类似于c语言中的char数组或者传统数据库中的blob类型,可以表示任意一块二进制数据。
举例
SELECT binary("中文"), character_length("中文"), character_length(binary("中文"))
输出结果为
CAST(中文 AS BINARY) length(中文) length(CAST(中文 AS BINARY))
5Lit5paH 2 6
可以看到用SQL输出binary
类型时,是自动进行了base64编码。character_length(binary("中文"))
值为6的原因是,字符串"中文"
UTF8编码后的二进制数据是6个字节,也就是说binary
类型在内存中运算时是对实际二进制数据进行操作的。
date
日期类型,在内存中是用4字节的整数表示。不过在输出的时候都会格式化成类似2019-06-30
这样的格式。
范围
"0001-01-01" ~ "9999-12-31"
举例
SELECT current_date(), date("2019-6"), date_add('2019-07-31', 1)
输出结果为
current_date() CAST(2019-6 AS DATE) date_add(CAST(2019-07-31 AS DATE), 1)
2019-06-24 2019-06-01 2019-08-01
除本例用到的两个函数外,Spark支持了非常丰富的日期相关函数,可以参考操作符和内置函数。
timestamp
表示时间戳的类型,类似java中的java.sql.Timestamp
类型,在内存使用8字节的整数表示。不过在输出的时候都会格式化成类似2019-06-24T00:38:45.462+08:00
的格式。
举例
SELECT current_timestamp(), timestamp("2019-6")
输出结果为
current_timestamp() CAST(2019-6 AS TIMESTAMP)
2019-06-24T00:40:28.354+08:00 2019-06-01T00:00:00.000+08:00
Array
Array<ElementType>
数组类型,ElementType
为元素类型,可以是本节中的任意类型。
举例
比如可以这样创建字段类型为不同Array
类型的表。
CREATE TABLE test_array (f1 Array<int>, f2 Array<string>, f3 Array<Array<float>>)
下面是操作Array
类型的一个简单例子。
SELECT array(2, 4), array('x', 'y'), array_contains(array('a', 'b'), 'a')
输出结果为
array(2, 4) array(x, y) array_contains(array(a, b), a)
[2, 4] [x, y] True
Map
Map<KeyType, ValueType>
映射类型,KeyType
和ValueType
分别为键、值的类型,可以是本节中的任意类型。不过KeyType
为复合类型时是没有意义的。
举例
比如可以这样创建不同Map
类型字段的表。
CREATE TABLE test_map (f1 Map<int, string>, f2 Map<string, Array<double>>);
下面是操作Map
类型的一个简单例子。
SELECT map('x', 3, current_date(), 'y')
输出结果为
map(CAST(x AS STRING), CAST(3 AS STRING), CAST(current_date() AS STRING), CAST(y AS STRING))
{'x': '3', '2019-06-24': 'y'}
Struct
Struct<fieldName_1:FieldType_1, ..., fieldName_n:FieldType_n>
复合结构类型,可以指定任意个数的字段。字段名必须是字符串,字段类型可以是本节中的人任意类型。
举例
比如可以这样创建一个含有Struct
字段类型的表。
CREATE TABLE test_struct (f1 Struct<a:string, b:Struct<c:Array<string>, d:double>>)
使用如下语句可以查询字段信息。
SELECT f1.b.c[0] from test_struct
下面是一个操作Struct
类型的简单例子。
SELECT to_json(struct('x', 3)), named_struct('b', Array('a'), 'y', 3.14)
输出结果为
structstojson(named_struct(col1, x, col2, 3)) named_struct(b, array(a), y, 3.14)
{"col1":"x","col2":3} {'b': ['a'], 'y': 3.14}
其实Struct
类型更多是使用在Spark DataFrame中,比如下面这个Scala语言的例子。
import org.apache.spark.sql.types._
import org.apache.spark.sql.Row
val rdd = sc.textFile("/tmp/person.log").map{line=>
val items = line.split(" ")
Row(items(0).toInt, items(1).trim, items(2).toInt)
}
val schema = StructType(List(
StructField("id", IntegerType, true),
StructField("name", StringType, true),
StructField("age", IntegerType, true)
))
spark.createDataFrame(rdd, schema).registerTempTable("t_person")
spark.sql("SELECT * FROM t_person ORDER BY age DESC LIMIT 2").show()
使用测试数据的输出结果为
+---+-----+---+
| id| name|age|
+---+-----+---+
|334|jerry| 45|
|123| tom| 24|
+---+-----+---+