业内公认的 OLAP 数据库黑马 ClickHouse 有哪些复合类型
《ClickHouse原理解析与应用实践》国内首本全方位介绍ClickHouse的技术书,欢迎参与文末赠书活动 。
ClickHouse 是一款由俄罗斯Yandex公司开源的OLAP数据库,拥有者卓越的性能表现,在官方公布的基准测试中,ClickHouse的平均响应速度是Vertica的2.63倍、InfiniDB的17倍、MonetDB的27倍、Hive的126倍、MySQL的429倍以及Greenplum的10倍。
自2016年开源以来,ClickHouse一直保持着飞速的发展,是目前业界公认的OLAP数据库黑马,已在头条、阿里、腾讯、新浪、青云等众多公司得以应用。
作为一款分析型数据库,ClickHouse提供了许多数据类型,它们可以划分为基础类型、复合类型和特殊类型。其中基础类型使ClickHouse具备了描述数据的基本能力,而另外两种类型则使ClickHouse的数据表达能力更加丰富立体。
本文主要来谈ClickHouse的复合类型,ClickHouse提供了数组、元组、枚举和嵌套四类复合类型。这些类型通常是其他数据库原生不具备的特性。拥有了复合类型之后,ClickHouse的数据模型表达能力更强了。
- Array
数组有两种定义形式,常规方式array(T):
SELECT array(1, 2) as a , toTypeName(a) ┌─a───┬─toTypeName(array(1, 2))─┐ │ [1,2] │ Array(UInt8) │ └─────┴────────────────┘
或者简写方式[T]:
SELECT [1, 2]
通过上述的例子可以发现,在查询时并不需要主动声明数组的元素类型。因为ClickHouse的数组拥有类型推断的能力,推断依据:以最小存储代价为原则,即使用最小可表达的数据类型。例如在上面的例子中,array(1, 2)会通过自动推断将UInt8作为数组类型。但是数组元素中如果存在Null值,则元素类型将变为Nullable,例如:
SELECT [1, 2, null] as a , toTypeName(a) ┌─a──────┬─toTypeName([1, 2, NULL])─┐ │ [1,2,NULL] │ Array(Nullable(UInt8)) │ └────────┴─────────────────┘
细心的读者可能已经发现,在同一个数组内可以包含多种数据类型,例如数组[1, 2.0]是可行的。但各类型之间必须兼容,例如数组[1, '2']则会报错。
在定义表字段时,数组需要指定明确的元素类型,例如:
CREATE TABLE Array_TEST ( c1 Array(String) ) engine = Memory
2. Tuple
元组类型由1~n个元素组成,每个元素之间允许设置不同的数据类型,且彼此之间不要求兼容。元组同样支持类型推断,其推断依据仍然以最小存储代价为原则。与数组类似,元组也可以使用两种方式定义,常规方式tuple(T):
SELECT tuple(1,'a',now()) AS x, toTypeName(x) ┌─x─────────────────┬─toTypeName(tuple(1, 'a', now()))─┐ │ (1,'a','2019-08-28 21:36:32') │ Tuple(UInt8, String, DateTime) │ └───────────────────┴─────────────────────┘
或者简写方式(T):
SELECT (1,2.0,null) AS x, toTypeName(x) ┌─x──────┬─toTypeName(tuple(1, 2., NULL))───────┐ │ (1,2,NULL) │ Tuple(UInt8, Float64, Nullable(Nothing)) │ └───────┴──────────────────────────┘
在定义表字段时,元组也需要指定明确的元素类型:
CREATE TABLE Tuple_TEST ( c1 Tuple(String,Int8) ) ENGINE = Memory;
元素类型和泛型的作用类似,可以进一步保障数据质量。在数据写入的过程中会进行类型检查。例如,写入INSERT INTO Tuple_TEST VALUES( ('abc' , 123) )是可行的,而写入INSERT INTO Tuple_TEST VALUES( ('abc' , 'efg') )则会报错。
3. Enum
ClickHouse支持枚举类型,这是一种在定义常量时经常会使用的数据类型。ClickHouse提供了Enum8和Enum16两种枚举类型,它们除了取值范围不同之外,别无二致。枚举固定使用(String:Int) Key/Value键值对的形式定义数据,所以Enum8和Enum16分别会对应(String:Int8)和(String:Int16),例如:
CREATE TABLE Enum_TEST ( c1 Enum8('ready' = 1, 'start' = 2, 'success' = 3, 'error' = 4) ) ENGINE = Memory;
在定义枚举集合的时候,有几点需要注意。首先,Key和Value是不允许重复的,要保证唯一性。其次,Key和Value的值都不能为Null,但Key允许是空字符串。在写入枚举数据的时候,只会用到Key字符串部分,例如:
INSERT INTO Enum_TEST VALUES('ready'); INSERT INTO Enum_TEST VALUES('start');
数据在写入的过程中,会对照枚举集合项的内容逐一检查。如果Key字符串不在集合范围内则会抛出异常,比如执行下面的语句就会出错:
INSERT INTO Enum_TEST VALUES('stop');
可能有人会觉得,完全可以使用String代替枚举,为什么还需要专门的枚举类型呢?这是出于性能的考虑。因为虽然枚举定义中的Key属于String类型,但是在后续对枚举的所有操作中(包括排序、分组、去重、过滤等),会使用Int类型的Value值。
4. Nested
嵌套类型,顾名思义是一种嵌套表结构。一张数据表,可以定义任意多个嵌套类型字段,但每个字段的嵌套层级只支持一级,即嵌套表内不能继续使用嵌套类型。对于简单场景的层级关系或关联关系,使用嵌套类型也是一种不错的选择。例如,下面的nested_test是一张模拟的员工表,它的所属部门字段就使用了嵌套类型:
CREATE TABLE nested_test ( name String, age UInt8 , dept Nested( id UInt8, name String ) ) ENGINE = Memory;
ClickHouse的嵌套类型和传统的嵌套类型不相同,导致在初次接触它的时候会让人十分困惑。以上面这张表为例,如果按照它的字面意思来理解,会很容易理解成nested_test与dept 是一对一的包含关系,其实这是错误的。不信可以执行下面的语句,看看会是什么结果:
INSERT INTO nested_test VALUES ('nauu',18, 10000, '研发部'); Exception on client: Code: 53. DB::Exception: Type mismatch in IN or VALUES section. Expected: Array(UInt8). Got: UInt64
注意上面的异常信息,它提示期望写入的是一个Array数组类型。
现在大家应该明白了,嵌套类型本质是一种多维数组的结构。嵌套表中的每个字段都是一个数组,并且行与行之间数组的长度无须对齐。所以需要把刚才的INSERT语句调整成下面的形式:
INSERT INTO nested_test VALUES ('bruce' , 30 , [10000,10001,10002], ['研发部','技术支持中心','测试部']); --行与行之间,数组长度无须对齐 INSERT INTO nested_test VALUES ('bruce' , 30 , [10000,10001], ['研发部','技术支持中心']);
需要注意的是,在同一行数据内每个数组字段的长度必须相等。例如,在下面的示例中,由于行内数组字段的长度没有对齐,所以会抛出异常:
INSERT INTO nested_test VALUES ('bruce' , 30 , [10000,10001], ['研发部','技术支持中心', '测试部']); DB::Exception: Elements 'dept.id' and 'dept.name' of Nested data structure 'dept' (Array columns) have different array sizes..
在访问嵌套类型的数据时需要使用点符号,例如:
SELECT name, dept.id, dept.name FROM nested_test ┌─name─┬─dept.id──┬─dept.name─────────────┐ │ bruce │ [16,17,18] │ ['研发部','技术支持中心','测试部'] │ └────┴───────┴────────────────────┘
关于作者:
朱凯,ClickHouse贡献者之一,ClickHouse布道者,资深架构师,十多年IT从业经验,对大数据领域主流技术与解决方案有深入研究,擅长分布式系统的架构设计与整合。曾主导过多款大数据平台级产品的规划、设计与研发工作,一线实战经验丰富。现就职于远光软件股份有限公司,任大数据事业部平台开发部总经理。著有《企业级大数据平台构建:架构与实现》 《ClickHouse原理解析与应用实践》等书。
点击图片了解详情
国内首本全方位讲解ClickHouse的技术书,这是一本可帮助读者深度理解并全面掌握ClickHouse运行原理并进行实践开发的工具书,涵盖了ClickHouse的时代背景、发展历程、核心概念、基础功能、运行原理、实践指导等多个维度的内容。一本书帮你驾驭ClickHouse。
本书作者朱凯老师将于7月25日20:00 —21:00 空降直播间,与大家漫谈ClickHouse在实时分析系统中的定位与作用。直播间还有限量正版图书免费送,欢迎扫码观看。
点击图片观看直播
【赠书福利】
欢迎留言谈谈你对ClickHouse的看法与认知,我们将从留言中随机挑取7名幸运读者,分别包邮赠送一本《ClickHouse原理解析与应用实践》。活动截止到7月25日20点。快来参与吧。

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。
持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。
转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。
- 上一篇
ImageMagick 7.0.10-24 发布,多功能图片处理软件
ImageMagick 7.0.10-24 现已正式发布,该版本可以在Linux,Windows,Mac Os X,iOS,AndroidOS 等平台上运行。 ImageMagick 是一个用来创建、编辑、合成图片的软件。它可以读取、转换、写入超过 200 种格式的图片,包括 PNG、JPEG、GIF、HEIC、TIFF、DPX、EXR、WebP、Postscript、PDF 和 SVG 等等。 ImageMagick 可被用于图片切割、颜色替换、各种效果的应用,图片的旋转、组合,文本,直线, 多边形,椭圆,曲线,附加到图片伸展旋转等。支持Linux、Windows、Mac OS X、iOS、Android OS 平台。 7.0.10-24 版本的更新内容包括有: 添加对-white-balance 命令行选项的支持。 globbing 时发现隐藏文件(例如 *.jpg)(请参阅 https://github.com/ImageMagick/ImageMagick/discussions/2239)。 新的 inverse-log evaluate operator 详细更新内容,以及...
- 下一篇
一种面向非自回归神经机器翻译的多模错误恢复学习机制
本文基于ACL 2020论文《Learning to Recover from Multi-Modality Errors for Non-Autoregressive Neural Machine Translation》撰写,论文作者为腾讯微信AI团队。 导语 非自回归神经机器翻译(non-autoregressive neural machine translation,简称非自回归翻译)是近年来兴起的一种新的机器翻译方法。为了提升翻译速度,其抛弃了目标语言词间的依赖关系,并行生成所有目标词,显著提升了翻译速度。但由于同一段原文经常有多种可行的潜在译文,使得非自回归翻译模型在解码时会出现不同位置的目标语言词是从不同的潜在译文中选取的问题,被称为多峰问题(multi-modality problem)。该问题通常表现为重复翻译和漏译现象,对非自回归翻译模型的翻译质量具有不利影响。为了缓解该问题,本文提出了一种新的模型RecoverSAT。该模型该译文拆成多个片段并逐段生成,在每个片段内部采用自回归生成方式,而段间则采用非自回归方式。进一步的,通过引入动态停止机制和段删除机制,该方法...
相关文章
文章评论
共有0条评论来说两句吧...
文章二维码
点击排行
推荐阅读
最新文章
- SpringBoot2整合Thymeleaf,官方推荐html解决方案
- Jdk安装(Linux,MacOS,Windows),包含三大操作系统的最全安装
- CentOS7设置SWAP分区,小内存服务器的救世主
- SpringBoot2初体验,简单认识spring boot2并且搭建基础工程
- SpringBoot2全家桶,快速入门学习开发网站教程
- Docker安装Oracle12C,快速搭建Oracle学习环境
- SpringBoot2整合MyBatis,连接MySql数据库做增删改查操作
- Eclipse初始化配置,告别卡顿、闪退、编译时间过长
- MySQL8.0.19开启GTID主从同步CentOS8
- CentOS8,CentOS7,CentOS6编译安装Redis5.0.7