ClickHouse 集成Bitmap(2022-01-16更新)

ClickHouse 继承Bitmap

  • 1、精确去重计数性能测试
    • 1.1、创建一张test表
    • 1.2、往test表插入1亿条数据
    • 1.3、进行精确去重计数性能测试
  • 2、Bitmap位存储和位计算
  • 3、位图函数
    • groupBitmapState
    • bitmapBuild
    • bitmapToArray
    • bitmapSubsetInRange
    • bitmapSubsetLimit
    • bitmapContains
    • bitmapHasAny
    • bitmapHasAll
    • bitmapAnd
    • bitmapOr
    • bitmapXor
    • bitmapAndnot
    • bitmapMin
    • bitmapMax
    • bitmapCardinality
    • bitmapAndCardinality
    • bitmapOrCardinality
    • bitmapXorCardinality
    • bitmapAndnotCardinality

1、精确去重计数性能测试

1.1、创建一张test表

create table test(
    user_id UInt32,
    test_Date DateTime,
    part UInt8
)ENGINE = MergeTree
PARTITION BY part
ORDER BY part
SETTINGS index_granularity = 8192

1.2、往test表插入1亿条数据

insert into test SELECT *,1 as part FROM generateRandom('userid UInt32, test_Date Date') LIMIT 100000000

1.3、进行精确去重计数性能测试

1亿条数据,去重计算出9千多万整形数值。

  • 非精确去重函数:uniq、uniqHLL12、uniqCombined
  • 精确去重函数:uniqExact、groupBitmap
函数 时长(秒) 去重后个数 误差个数 误差率
uniq(user_id) 0.324 98517062 326237 0.33%
uniqHLL12(user_id) 0.967 99480495 -637196 -0.64%
uniqCombined(user_id) 0.957 98600278 243021 0.25%
uniqExact(user_id) 8.259 98843299 0 0%
groupBitmap(user_id) 16.740 98843299 0 0%

ClickHouse 集成Bitmap(2022-01-16更新)_第1张图片
ClickHouse 集成Bitmap(2022-01-16更新)_第2张图片
ClickHouse 集成Bitmap(2022-01-16更新)_第3张图片
ClickHouse 集成Bitmap(2022-01-16更新)_第4张图片
ClickHouse 集成Bitmap(2022-01-16更新)_第5张图片
注意:
①uniq、uniqHLL12、uniqCombined等函数是非精确去重函数,只适合于快速查询一些大概的统计结果。精确的去重统计不能用这些去重函数。
②groupBitmap仅支持整形值去重, uniqExact支持任意类型去重。

2、Bitmap位存储和位计算

bitmap位图运算为啥这个快。举个例子:我们知道,每个bit位表示一个数字id,假设有1亿个的用户id,那么只需要1亿bit位,约119m大小 = (1 * 10^9 / 8 / 1024 / 1024)。所以说,这是一种非常高效的计算方法,在计算目标用户的基数时有着得天独厚的优势。
ClickHouse 集成Bitmap(2022-01-16更新)_第6张图片
通过单个bitmap可以完成精确去重操作,通过多个bitmap的and、or、xor、andnot等位操作可以完成经典的留存分析、漏斗分析、用户画像分析等场景的计算。

3、位图函数

ClickHouse 集成Bitmap(2022-01-16更新)_第7张图片

位图对象有两种构造方法。一个是由聚合函数groupBitmapState构造的,另一个是由Array Object构造的。同时还可以将位图对象转化为数组对象。

我们使用RoaringBitmap实际存储位图对象,当基数小于或等于32时,它使用Set保存。当基数大于32时,它使用RoaringBitmap保存。这也是为什么低基数集的存储更快的原因。

groupBitmapState

将某一列压缩为一个位图。可以理解为把某一列打包成一个压缩包。

groupBitmapState(column)

参数
· column - 表的列名

示例

select groupBitmapState(列名) from '表名'

bitmapBuild

从无符号整数数组构建位图对象。将列表中的无符号整数数组打包,仅限于无符号整数数组,字符串等格式不接受。

bitmapBuild(array)

参数
· array - 无符号整数数组.

示例

SELECT bitmapBuild([1, 2, 3]) AS bit

bitmapToArray

将位图转换为整数数组。

bitmapToArray(bitmap)

参数

· bitmap - 位图对象.

示例

SELECT bitmapToArray(bitmapBuild([1, 2, 3])) AS array

在这里插入图片描述

bitmapSubsetInRange

将位图指定范围(包含range_start,不包含range_end)转换为另一个位图。

bitmapSubsetInRange(bitmap, range_start, range_end)

参数
· bitmap - 位图对象.
· range_start - 范围起始点(含).
· range_end - 范围结束点(不含).

示例

SELECT bitmapToArray(bitmapSubsetInRange(bitmapBuild([1,2,3,4,5,6,7,8,50,100,200,500]), toUInt32(8), toUInt32(200))) AS bsr;

在这里插入图片描述

bitmapSubsetLimit

将位图指定范围(起始点和数目上限)转换为另一个位图。

bitmapSubsetLimit(bitmap, range_start, limit)

参数

· bitmap - 位图对象.
· range_start - 范围起始点(含).
· limit - 子位图基数上限.

示例

SELECT bitmapToArray(bitmapSubsetLimit(bitmapBuild([1,2,3,4,5,6,7,8,50,100,200,500]), toUInt32(8), toUInt32(3))) AS bsl;

在这里插入图片描述

bitmapContains

检查位图是否包含指定元素。如果包含则返回1,否则返回0。

bitmapContains(haystack, needle)

参数
· haystack - 位图对象.
· needle - 元素,类型UInt32.

示例

SELECT bitmapContains(bitmapBuild([1,5,7,9]), toUInt32(9)) as T,bitmapContains(bitmapBuild([1,5,7,9]), toUInt32(8)) AS F

在这里插入图片描述

bitmapHasAny

如果位图有任何公共元素则返回1,否则返回0。对于空位图,返回0。

bitmapHasAny(bitmap,bitmap)

参数
· bitmap - bitmap对象。
示例

SELECT bitmapHasAny(bitmapBuild([1,2,3]),bitmapBuild([3,4,5])) AS T,bitmapHasAny(bitmapBuild([1,2,3]),bitmapBuild([4,5,6])) AS F

在这里插入图片描述

bitmapHasAll

如果第一个位图包含第二个位图的所有元素,则返回1,否则返回0。如果第二个参数是空位图,则返回1。

bitmapHasAll(bitmap,bitmap)

参数
bitmap - bitmap 对象。

示例

SELECT bitmapHasAll(bitmapBuild([1,2,3]),bitmapBuild([1,2])) AS T,bitmapHasAll(bitmapBuild([1,2,3]),bitmapBuild([3,4,5])) AS F

在这里插入图片描述

bitmapAnd

为两个位图对象进行与操作,返回一个新的位图对象。

bitmapAnd(bitmap1,bitmap2)

参数

· bitmap1 - 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapToArray(bitmapAnd(bitmapBuild([1,2,3,4,5]),bitmapBuild([3,4,5,6,7]))) AS ba

在这里插入图片描述
- 如图所示,所得结果,为中间红色部分。注意,如果不用bitmapToArray展开,那么原本的bitmapAnd所算出来的结果会是一个包含结果(3,4,5)的位图。
ClickHouse 集成Bitmap(2022-01-16更新)_第8张图片

bitmapOr

为两个位图对象进行或操作,返回一个新的位图对象。

bitmapOr(bitmap1,bitmap2)

参数

· bitmap1 - 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapToArray(bitmapOr(bitmapBuild([1,2,3,4,5]),bitmapBuild([3,4,5,6,7]))) AS bo

在这里插入图片描述
- 如图所示,所得结果,为所有红色的部分。注意,如果不用bitmapToArray展开,那么原本的bitmapAnd所算出来的结果会是一个包含结果(1,2,3,4,5,6,7)的位图。
ClickHouse 集成Bitmap(2022-01-16更新)_第9张图片

bitmapXor

为两个位图对象进行异或操作,返回一个新的位图对象。

bitmapXor(bitmap1,bitmap2)

参数
· bitmap1 - 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapToArray(bitmapXor(bitmapBuild([1,2,3,4,5]),bitmapBuild([3,4,5,6,7]))) AS bx

在这里插入图片描述
- 如图所示,所得结果,为左右两边红色部分。注意,如果不用bitmapToArray展开,那么原本的bitmapAnd所算出来的结果会是一个包含结果(1,2,6,7)的位图。
ClickHouse 集成Bitmap(2022-01-16更新)_第10张图片

bitmapAndnot

计算两个位图的差异,返回一个新的位图对象。

bitmapAndnot(bitmap1,bitmap2)

参数
· bitmap1 - 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapToArray(bitmapAndnot(bitmapBuild([1,2,3,4,5]),bitmapBuild([3,4,5,6,7]))) AS ban

在这里插入图片描述
- 如图所示,所得结果,为左边红色部分。注意,如果不用bitmapToArray展开,那么原本的bitmapAnd所算出来的结果会是一个包含结果(1,2)的位图。
ClickHouse 集成Bitmap(2022-01-16更新)_第11张图片

bitmapMin

返回一个UInt64类型的数值,表示位图中的最小值。如果位图为空则返回UINT32_MAX。

bitmapMin(bitmap)

参数
· bitmap - 位图对象。

示例

SELECT bitmapMin(bitmapBuild([1, 2, 3, 4, 5])) AS bm

在这里插入图片描述

bitmapMax

返回一个UInt64类型的数值,表示位图中的最大值。如果位图为空则返回0。

bitmapMax(bitmap)

参数
· bitmap - 位图对象。

示例

SELECT bitmapMax(bitmapBuild([1, 2, 3, 4, 5])) AS bmax

在这里插入图片描述

bitmapCardinality

返回一个UInt64类型的数值,表示位图对象的基数。这里提醒一下,这个统计是自动去重的,如果不需要自动去重,则不可以使用这个函数。

bitmapCardinality(bitmap)

参数
· bitmap - 位图对象。

示例

SELECT bitmapCardinality(bitmapBuild([1, 2, 3, 4, 5])) AS res

在这里插入图片描述

bitmapAndCardinality

为两个位图对象进行与操作,返回结果位图的基数。

bitmapAndCardinality(bitmap1,bitmap2)

参数
· bitmap1 - 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapAndCardinality(bitmapBuild([1,2,3]),bitmapBuild([3,4,5])) AS bmc;

- 因为位图1和位图2的公共部分为(1),所以结果为1。对比于上面的bitmapAnd,多加的Cardinality是去重后做统计的操作。
在这里插入图片描述

bitmapOrCardinality

为两个位图进行或运算,返回结果位图的基数。

bitmapOrCardinality(bitmap1,bitmap2)

参数
· bitmap1 – 位图对象。
· bitmap2 – 位图对象。

示例

SELECT bitmapOrCardinality(bitmapBuild([1,2,3]),bitmapBuild([3,4,5])) AS boc;
  • 因为位图1和位图2的运算结果为(1,2,3,4,5),所以结果为5。对比于上面的bitmapOr,多加的Cardinality是去重后做统计的操作。
    在这里插入图片描述

bitmapXorCardinality

为两个位图进行异或运算,返回结果位图的基数。

bitmapXorCardinality(bitmap1,bitmap2)

参数
· bitmap1 - 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapXorCardinality(bitmapBuild([1,2,3]),bitmapBuild([3,4,5])) AS bxc;
  • 因为位图1和位图2的运算结果为(1,2,4,5),所以结果为4。对比于上面的bitmapXor,多加的Cardinality是去重后做统计的操作。
    在这里插入图片描述

bitmapAndnotCardinality

计算两个位图的差异,返回结果位图的基数。

bitmapAndnotCardinality(bitmap1,bitmap2)

参数
· bitmap1 – 位图对象。
· bitmap2 - 位图对象。

示例

SELECT bitmapAndnotCardinality(bitmapBuild([1,2,3]),bitmapBuild([3,4,5])) AS bac;
  • 因为位图1和位图2的运算结果为(1,2),所以结果为2。对比于上面的bitmapAndnot,多加的Cardinality是去重后做统计的操作。
    在这里插入图片描述

你可能感兴趣的:(ClickHouse,python)