ClickHouse进阶(七):Clickhouse数据查询-1

进入正文前,感谢宝子们订阅专题、点赞、评论、收藏!关注IT贫道,获取高质量博客内容!

🏡个人主页:含各种IT体系技术,IT贫道_Apache Doris,大数据OLAP体系技术栈,Kerberos安全认证-CSDN博客

📌订阅:拥抱独家专题,你的订阅将点燃我的创作热情!

👍点赞:赞同优秀创作,你的点赞是对我创作最大的认可!

⭐️ 收藏:收藏原创博文,让我们一起打造IT界的荣耀与辉煌!

✏️评论:留下心声墨迹,你的评论将是我努力改进的方向!

 博主个人B栈地址:豹哥教你大数据的个人空间-豹哥教你大数据个人主页-哔哩哔哩视频


目录

​​​​​​​1. with子句

1.1 定义变量

1.2 调用函数

1.3 定义子查询

1.4 在子查询中重复使用with

2. From子句

​​​​​​​3. Sample子句

3.1 Sample factor

3.2 Sample rows

3.3 SAMPLE factor OFFSET n

​​​​​​​4. Array Join子句


可以从官网下载官网提供的数据集hits_v1和visits_v1,对应的下载路径为:https://datasets.clickhouse.com/hits/partitions/hits_v1.tar和https://datasets.clickhouse.com/visits/partitions/visits_v1.tar,下载之后对应两个压缩包:

hits_v1.tarvisits_v1.tar

将以上两个压缩包进行上传到node1节点/softwar目录下,并解压到目录”/var/lib/clickhouse”中。

[root@node1 ~]# cd /software/[root@node1 software]# tar xvf hits_v1.tar -C /var/lib/clickhouse[root@node1 software]# tar xvf visits_v1.tar -C /var/lib/clickhouse

重启node1节点上的clickhouse,查询数据:

[root@node1 ~]# service clickhouse-server restart[root@node1 ~]# clickhouse-clientnode1 :) show databases;┌─name─────┐│ datasets ││ default  ││ system   │└──────────┘#查询表 hits_v1中的数据量node1 :) select count(*) from datasets.hits_v1;┌─count()─┐│ 8873898 │└─────────┘#查询表 visits_v1中的数据量node1 :) select count(*) from datasets.visits_v1;┌─count()─┐│ 1676861 │└─────────┘

clickhouse完全使用SQL作为查询语言,能够以Selete查询语句从数据库中查询数据,虽然clickhouse拥有优秀的查询性能,但是我们也不能滥用查询,掌握clickhouse支持的各种查询子句很有必要,使用不恰当的SQL语句进行查询不仅带来低性能,还可能带来系统不可预知的错误。例如:我们使用select * 查询数据时,通配符*对列式存储的clickhouse没有一点好处,针对一张拥有133个列的数据表hits_v1,查询2000行数据时,使用*与不使用*速度相差几乎300倍:

#使用*查询2000行数据node1 :) select * from datasets.hits_v1 limit 2000;2000 rows in set. Elapsed: 4.306 sec. Processed 2.00 thousand rows, 2.23 MB (464.50 rows/s., 518.76 KB/s.)#不使用*查询2000行数据node1 :) select WatchID from datasets.hits_v1 limit 2000;2000 rows in set. Elapsed: 0.016 sec. Processed 2.00 thousand rows, 16.00 KB (126.48 thousand rows/s., 1.01 MB/s.)

此外需要注意,clickhouse中对字段的解析大小写敏感,select a与select A表示的语义不同,下面我们学习下clickhouse中支持的查询语句。

​​​​​​​​​​​​​​1. with子句

clickhouse支持with子句以增强语句的表达,例如如下查询:

node1 :) SELECT pow(pow(2,2),3)┌─pow(pow(2, 2), 3)─┐│                64 │└───────────────────┘

我们可以通过使用with子句进行简化,提高可读性:

node1 :) WITH pow(2,2) AS a SELECT power(a,3)┌─pow(a, 3)─┐│        64 │└───────────┘

with的使用支持如下四种用法:

1.1 定义变量

可以通过with定义变量,这些变量在后续的查询子句中可以直接访问。例如:

node1 :) WITH 10 AS startSELECT numberFROM system.numbersWHERE number > startLIMIT 5┌─number─┐│     11 ││     12 ││     13 ││     14 ││     15 │└────────┘

1.2 调用函数

可以访问select子句中的列字段,并调用函数做进一步处理,处理之后的数据可以在select子句中继续使用。例如:

node1 :) WITH SUM(data_uncompressed_bytes) AS bytesSELECTdatabase,formatReadableSize(bytes) AS formatFROM system.columnsGROUP BY databaseORDER BY bytes DESC┌─database─┬─format─────┐│ datasets │ 7.40 GiB   ││ system   │ 197.27 MiB ││ default  │ 0.00 B     │└──────────┴────────────┘

1.3 定义子查询

可以使用with定义子查询,例如,借助子查询可以得出各database未压缩数据大小与数据总和大小的比例排名:

node1 :) WITH (SELECT SUM(data_uncompressed_bytes)FROM system.columns) AS total_bytesSELECTdatabase,(SUM(data_uncompressed_bytes) / total_bytes) * 100 AS database_disk_usageFROM system.columnsGROUP BY databaseORDER BY database_disk_usage DESC┌─database─┬─database_disk_usage─┐│ datasets │   97.31767735000648 ││ system   │   2.682322649993527 ││ default  │                   0 │└──────────┴─────────────────────┘

注意:在with中使用子查询时智能返回一行数据,如果结果集大于一行则报错。

1.4 在子查询中重复使用with

在子查询中可以嵌套使用With子句,例如,在计算出各database未压缩数据大小与数据总和的比例之后,又进行取整函数操作:

node1 :) WITH round(database_disk_usage) AS database_disk_usage_v1SELECTdatabase,database_disk_usage,database_disk_usage_v1FROM(WITH (SELECT SUM(data_uncompressed_bytes)FROM system.columns) AS total_bytesSELECTdatabase,(SUM(data_uncompressed_bytes) / total_bytes) * 100 AS database_disk_usageFROM system.columnsGROUP BY databaseORDER BY database_disk_usage DESC)┌─database─┬─database_disk_usage─┬─database_disk_usage_v1─┐│ datasets │    97.2911778785499 │                     97 ││ system   │  2.7088221214500954 │                      3 ││ default  │                   0 │                      0 │└──────────┴─────────────────────┴────────────────────────┘

2. From子句

From子句表示从何处读取数据,支持2种形式,由于From比较简单,这里不再举例,2种使用方式如下:

SELECT clo1 FROM tbl;
SELECT rst FROM (SELECT sum(col1) as rst FROM tbl)

from 关键字可以省略,此时会从虚拟表中取数,clickhouse中没有dual虚拟表,它的虚拟表是system.one,例如,以下两种查询等价:

SELECT 1;SELECT 1 FROM system.one;

另外,FROM 子句后还可以跟上final修饰符,可以配合COllapsingMergeTree和VersionedCollapsingMergeTree等表引擎进行查询操作,强制在查询过程中合并,由于Final修饰符会降低查询性能,所以尽量避免使用Final修饰符。

​​​​​​​3. Sample子句

Sample子句可以实现数据采样功能,使查询仅返回采样数据而非全部数据,从而减少查询负载。Sample采样机制是幂等机制,也就是说在数据不发生变化,使用相同的采样规则总是能够返回相同的数据。

sample子句只能用于MergeTree系列表引擎,并且要求在Create Table时声明sample by 抽样表达式。

例如,创建表 tbl 声明sample by抽样表达式:

CREATE TABLE tbl(id UInt32,name String,age UInt32,birthday DATE)ENGINE = MERGETREE()PARTITION BY toYYYYMM(birthday)ORDER BY (id,intHash32(age))SAMPLE BY intHash32(age)

以上创建sample by 采样表时注意:

  1. Sample by 所声明的表达式必须同时包含在主键的声明内。
  2. Sample Key 必须是Int类型,虽然在建表不报错,但是数据查询时报错。

另外,建表时没有声明Sample by,在使用sample 采样时会报错。

Sample目前支持三种语法,前面导入的datasets.hits_v1创建时指定了SAMPLE BY ,建表语句如下:

CREATE TABLE datasets.hits_v1(`WatchID` UInt64,`JavaEnable` UInt8,`Title` String,... ...)ENGINE = MergeTree()PARTITION BY toYYYYMM(EventDate)ORDER BY (CounterID, EventDate, intHash32(UserID))SAMPLE BY intHash32(UserID)

下面就以表hits_v1为例,来讲解sample三种用法。

3.1 Sample factor

Sample factor表示按因子系数采样,factor表示采样因子,取值0-1之间的小数,表示采样总体数据的比例。如果factor 设置为0或者1,则表示不采样。使用如下:

#按10%的因子采样数据
SELECT CounterID FROM datasets.hits_v1 SAMPLE 0.1;
839889 rows in set. Elapsed: 0.114 sec. Processed 7.36 million rows, 88.30 MB (64.46 million rows/s., 773.46 MB/s.)

3.2 Sample rows

Sample rows表示按照样本数量采样,其中rows表示大概采样多少行数据,是个近似值,取值必须大于1,如果rows行数大于表总数,效果等同于rows=1,即不采样。使用如下:

node1 :) SELECT count() FROM datasets.hits_v1 SAMPLE 10000;┌─count()─┐│    9251 │└─────────┘

3.3 SAMPLE factor OFFSET n

SAMPLE factor OFFSET n 表示按因子系数和偏移量采样,其中factor表示采样因子,即采样总数据的百分比,n表示偏移多少数据后才开始采样,它们两个取值都是0~1之间的小数。使用如下:

#偏移量0.5并按0.4的系数采样node1 :) SELECT CounterID FROM datasets.hits_v1 SAMPLE 0.4 OFFSET 0.5;3589194 rows in set.

偏移量0.5并按0.4的系数采样的采样为:从数据的二分之一处开始,按总数量的0.4采样数据。如果Sample比例采样出现了溢出,则数据会被自动截断,例如:

node1 :) SELECT CounterID FROM datasets.hits_v1 SAMPLE 0.4 OFFSET 0.9;892694 rows in set.

​​​​​​​4. Array Join子句

Array join 子句允许在数据表的内部,与数组类型的字段进行join操作,从而将一行数组展开为多行。

首先我们创建一张 MergeTree引擎表并加入数据,操作如下:

#创建表 mr_tblnode1 :) CREATE TABLE mr_tbl(`id` UInt8,`name` String,`age` Int,`local` Array(String))ENGINE = MergeTree()ORDER BY id#向表mr_tbl中插入数据node1 :) insert into table mr_tbl values (1,'zs',18,['beijing','shanghai']),(2,'ls',19,['guangzhou','hangzhou']),(3,'ww',20,[]);┌─id─┬─name─┬─age─┬─local────────────────────┐│  1 │ zs   │  18 │ ['beijing','shanghai']   ││  2 │ ls   │  19 │ ['guangzhou','hangzhou'] ││  3 │ ww   │  20 │ []                       │└────┴──────┴─────┴──────────────────────────┘

我们可以使用array join针对以上表数组字段一条膨胀成多条数据,类似Hive中的explode函数,在clickhouse中没有explode函数,可以使用array join 达到同样效果。

在使用Array join时,一条select语句中只能存在一个Array join(使用嵌套子查询除外),目前支持INNER和LEFT两种JOIN策略:

  • INNER ARRAY JOIN

Array join 默认使用的就是INNER JOIN 策略,使用如下:

node1 :) SELECT id,name,age,local FROM mr_tbl ARRAY JOIN local;┌─id─┬─name─┬─age─┬─local─────┐│  1 │ zs   │  18 │ beijing   ││  1 │ zs   │  18 │ shanghai  ││  2 │ ls   │  19 │ guangzhou ││  2 │ ls   │  19 │ hangzhou  │└────┴──────┴─────┴───────────┘

从以上查询结果来看,数据由原来的一行根据local列变成多行,并且排除掉了空数组对应的行。在使用Array Join时,如果我们在膨胀之后的数据结果中能够访问原有数组字段可以使用如下方式查询:

node1 :) SELECT id,name,age,local ,v FROM mr_tbl ARRAY JOIN local AS v;┌─id─┬─name─┬─age─┬─local────────────────────┬─v─────────┐│  1 │ zs   │  18 │ ['beijing','shanghai']   │ beijing   ││  1 │ zs   │  18 │ ['beijing','shanghai']   │ shanghai  ││  2 │ ls   │  19 │ ['guangzhou','hangzhou'] │ guangzhou ││  2 │ ls   │  19 │ ['guangzhou','hangzhou'] │ hangzhou  │└────┴──────┴─────┴──────────────────────────┴───────────┘
  • LEFT ARRAY JOIN

Array Join 子句支持LEFT连接策略,Left array join不会排除空数组,执行如下语句并查看结果。

node1 :) SELECT id,name,age,local FROM mr_tbl LEFT ARRAY JOIN local;┌─id─┬─name─┬─age─┬─local─────┐│  1 │ zs   │  18 │ beijing   ││  1 │ zs   │  18 │ shanghai  ││  2 │ ls   │  19 │ guangzhou ││  2 │ ls   │  19 │ hangzhou  ││  3 │ ww   │  20 │           │└────┴──────┴─────┴───────────┘

当同时对多个数组字段进行Array join 操作时,array join 对应的多个字段的数组长度必须相等,查询的计算逻辑是按行合并并不是产生笛卡尔积,举例如下:

#创建表 mr_tbl2node1 :) CREATE TABLE mr_tbl2(`id` UInt8,`name` String,`age` Int,`local` Array(String),`score` Array(UInt32))ENGINE = MergeTree()ORDER BY id#向表mr_tbl2中插入以下数据node1 :) insert into table mr_tbl2 values (1,'zs',18,['beijing','shanghai'],[100,200]),(2,'ls',19,['guangzhou','hangzhou'],[300,400]),(3,'ww',20,[],[]);┌─id─┬─name─┬─age─┬─local────────────────────┬─score─────┐│  1 │ zs   │  18 │ ['beijing','shanghai']   │ [100,200] ││  2 │ ls   │  19 │ ['guangzhou','hangzhou'] │ [300,400] ││  3 │ ww   │  20 │ []                       │ [] │└────┴──────┴─────┴──────────────────────────┴───────────┘#执行array join 语句,将数组中的数据一变多行node1 :) select id,name,age,local,local2,score,score2 from mr_tbl2 left array join local as local2 ,score as score2;


👨‍💻如需博文中的资料请私信博主。


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/128324.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

微信小程序云开发数据懒加载+打破云数据库返回数据条数限制

目录 数据懒加载 打破数据表返回条数限制 数据懒加载 show.wxml <view wx:for="{{Adata}}" wx:key="index" style="padding: 80rpx 10rpx 140rpx;border-bottom: rgb(109, 134, 134) 2px solid;"><view style="margin-left: 20…

springMVC基础技术使用

目录 1.常用注解 1.1RequestMapping 1.2.RequestParam 1.3.RequestBody 1.4.PathVariable 2.参数传递 2.1 slf4j-----日志 2.2基础类型 2.3复杂类型 2.4RequestParam 2.5PathVariable 2.6RequestBody 2.7请求方法&#xff08;增删改查&#xff09; 3.返回值 3.1void …

FPGA基本算术运算

FPGA基本算术运算 FPGA基本算术运算1 有符号数与无符号数2 浮点数及定点数I、定点数的加减法II、定点数的乘除法 3 仿真验证i、加减法验证ii、乘除法验证 FPGA基本算术运算 FPGA相对于MCU有并行计算、算法效率较高等优势&#xff0c;但同样由于没有成型的FPU等MCU内含的浮点数运…

python创建exe文件

1、搭建环境 pip install pyinstaller 2、准备测试代码 exe_test.py import timeprint("hello") print("hello") print("hello") print("hello")time.sleep(5) 注&#xff1a;添加sleep以便在执行exe文件的时候能看到结果 3、生…

个人能做股票期权吗?个人期权交易开户条件新规

个人投资者是可以交易股票期权的&#xff0c;不过期权交易通常需要投资者具备一定的投资经验和风险承受能力&#xff0c;因为期权交易涉及较高的风险和复杂性&#xff0c;下文为大家介绍个人能做股票期权吗&#xff1f;个人期权交易开户条件新规的内容。本文来自&#xff1a;期…

索尼 toio™ 应用创意开发征文|探索创新的玩乐世界——索尼 toio™

导语&#xff1a; 在技术的不断进步和发展中&#xff0c;玩具也逐渐融入了智能化的潮流。索尼 toio™作为一款前沿的智能玩具&#xff0c;给孩子和成人带来了全新的游戏体验。本文将介绍索尼 toio™的特点、功能和应用场景&#xff0c;让读者了解这个令人兴奋的创新产品。 1. 了…

【计算机网络】 ARP协议和DNS协议

文章目录 数据包在传输过程中的变化过程单播组播和广播ARP协议ARP代理免费ARP路由数据转发过程DNS协议 数据包在传输过程中的变化过程 在说ARP和DNS之前&#xff0c;我们需要知道数据包在传输过程的变化过程 从图片中可以看到&#xff0c;发送方的原数据最开始是在应用层&…

SpringAOP面向切面编程

文章目录 一. AOP是什么&#xff1f;二. AOP相关概念三. SpringAOP的简单演示四. SpringAOP实现原理 一. AOP是什么&#xff1f; AOP&#xff08;Aspect Oriented Programming&#xff09;&#xff1a;面向切面编程&#xff0c;它是一种编程思想&#xff0c;是对某一类事情的集…

最经典的解析LSA数据库(第六课)

初步认识OSPF的大致内容(第三课)_IHOPEDREAM的博客-CSDN博客 1 OSPF 工作过程 建立领居表 同步数据库 今天来 说一说数据库概念 计算路由表 2 什么是数据库&#xff1f; 数据库是一个组织化的数据集合&#xff0c;用于存储、管理和检索数据。它是一个可访问的集合&#x…

OpenCV项目实战(1)— 如何去截取视频中的帧

前言&#xff1a;Hello大家好&#xff0c;我是小哥谈。针对一段视频&#xff0c;如何去截取视频中的帧呢&#xff1f;本节课就给大家介绍两种方式&#xff0c;一种方式是按一定间隔来截取视频帧&#xff0c;另一种方式是截取视频的所有帧。希望大家学习之后能够有所收获&#x…

基于springboot实现的rabbitmq消息确认

概述 RabbitMQ的消息确认有两种。 一种是消息发送确认。这种是用来确认生产者将消息发送给交换器&#xff0c;交换器传递给队列的过程中&#xff0c;消息是否成功投递。发送确认分为两步&#xff0c;一是确认是否到达交换器&#xff0c;二是确认是否到达队列。 第二种是消费接…

入门力扣自学笔记277 C++ (题目编号:42)(动态规划)

42. 接雨水 题目&#xff1a; 给定 n 个非负整数表示每个宽度为 1 的柱子的高度图&#xff0c;计算按此排列的柱子&#xff0c;下雨之后能接多少雨水。 示例 1&#xff1a; 输入&#xff1a;height [0,1,0,2,1,0,1,3,2,1,2,1] 输出&#xff1a;6 解释&#xff1a;上面是由数组…

Redis——Java中的客户端和API

Java客户端 在大多数的业务实现中&#xff0c;我们还是使用编码去操作Redis&#xff0c;对于命令的学习只是知道这些数据库可以做什么操作&#xff0c;以及在后面学习到了Java的API之后知道什么方法对应什么命令即可。 官方推荐的Java的客户端网页链接如下&#xff1a; 爪哇…

强大易用的开源 建站工具Halo

特点 可插拔架构 Halo 采用可插拔架构&#xff0c;功能模块之间耦合度低、灵活性提高。支持用户按需安装、卸载插件&#xff0c;操作便捷。同时提供插件开发接口以确保较高扩展性和可维护性。 ☑ 支持在运行时安装和卸载插件 ☑ 更加方便地集成三方平台 ☑ 统一的可配置设置表…

Pytest系列-fixture的详细使用和结合conftest.py的详细使用(3)

介绍 前面一篇讲了setup、teardown可以实现在执行用例前或结束后加入一些操作&#xff0c;但这种都是针对整个脚本全局生效的。 Fixture是pytest的非常核心功能之一&#xff0c;在不改变被装饰函数的前提下对函数进行功能增强&#xff0c;经常用于自定义测试用例前置和后置工作…

网络原理

网络原理 传输层 UDP 特点 特点&#xff1a;无连接&#xff0c;不可靠&#xff0c;面向数据报&#xff0c;全双工 格式 怎么进行校验呢&#xff1f; 把UDP数据报中的源端口&#xff0c;目的端口&#xff0c;UDP报文长度的每个字节&#xff0c;都依次进行累加 把累加结果&a…

Kafka源码分析之网络通信

1、生产者网络设计 架构设计图 2、生产者消息缓存机制 1、RecordAccumulator 将消息缓存到RecordAccumulator收集器中, 最后判断是否要发送。这个加入消息收集器&#xff0c;首先得从 Deque 里找到自己的目标分区&#xff0c;如果没有就新建一个批量消息 Deque 加进入 2、消…

excel中的引用与查找函数篇1

1、COLUMN(reference)&#xff1a;返回与列号对应的数字 2、ROW(reference)&#xff1a;返回与行号对应的数字 参数reference表示引用/参考单元格&#xff0c;输入后引用单元格后colimn()和row()会返回这个单元格对应的列号和行号。若参数reference没有引用单元格&#xff0c;…

【APUE】标准I/O库

目录 1、简介 2、FILE对象 3、打开和关闭文件 3.1 fopen 3.2 fclose 4、输入输出流 4.1 fgetc 4.2 fputc 4.3 fgets 4.4 fputs 4.5 fread 4.6 fwrite 4.7 printf 族函数 4.8 scanf 族函数 5、文件指针操作 5.1 fseek 5.2 ftell 5.3 rewind 6、缓冲相关 6.…

软件测试/测试开发丨学会与 AI 对话,高效提升学习效率

点此获取更多相关资料 简介 ChatGPT 的主要优点之一是它能够理解和响应自然语言输入。在日常生活中&#xff0c;沟通本来就是很重要的一门课程&#xff0c;沟通的过程中表达越清晰&#xff0c;给到的信息越多&#xff0c;那么沟通就越顺畅。 和 ChatGPT 沟通也是同样的道理&…