开始在Databricks中使用Liquid Clustering代替Partitioning来处理Delta表

利用Liquid Clustering 在Databricks 中处理 Delta 表,替代 Partitioning

通过引入名为Liquid Clustering的创新功能,Databricks在今年的Data + AI Summit中彻底改变了我们组织数据的方式。这是一种重新定义Delta表分区和聚类边界的创新特性。

分区和Z-Ordering

在Delta Databricks中,分区是将数据根据特定列组织成逻辑子集的过程,这样可以更容易地将数据拟合到子集中并优化查询性能。此外,Z-Ordering与分区结合使用来增强数据组织。这里,数据被按照优先的顺序排序和存储,从而优化查询性能。因此,分区和Z-Ordering一起帮助优化查询性能。

例如,在商业关系管理系统中 —

  • 销售数据按区域和子区域进行分区,以便数据可以分区为逻辑子集,便于访问数据。
  • 此外,分区的数据可以按照时间戳或账户ID进行Z-Ordering,以优化查询性能。

分区和Z-Ordering的问题

虽然分区和Z-Ordering可用于高效存储和检索,但在写入数据时可能会减慢处理速度,因为每次写入数据时需要重新组织数据。分区和Z-Ordering存在以下问题:

  • 偏斜分布和高基数:数据的不均匀分布可能导致数据的不均匀性,其中一些分区可能包含的数据显著多于其他分区。在Z-Ordering中,分区中具有高基数的列可能导致数据的不均匀分布。例如,一些地区可能包含较少的客户,而其他地区可能包含更多客户。
  • 更新时的开销:通过修改列对现有数据进行更新可能导致数据的重组,从而减慢处理速度。

因此,分区和Z-Ordering依赖于数据布局来执行数据优化。

Liquid Clustering如何实施拯救 —

Liquid Clustering不受固定数据布局的约束,它根据聚类键自动调整数据布局,无需重新编写数据,从而解决了开销问题。此外,Liquid Clustering根据数据模式动态聚类数据,并避免了出现在数据的偏斜分布中的分区问题。

Liquid Clustering肯定在以下情况下很有帮助

  • 具有偏斜分布或高基数列的表。
  • 增长迅速且需要维护和调优的表。
  • 具有并发写要求和随时间变化的访问模式的表。

使用Liquid Clustering

通过在创建表时使用“Cluster by”表达式,可以轻松启用Liquid Clustering。

CREATE TABLE table1(col0 int, col1 string) USING DELTA CLUSTER BY (col0);

我们可以修改现有表并启用聚类 —

ALTER TABLE table_name CLUSTER BY (new_column1, new_column2);

Liquid Clustering与分区和Z-Ordering不兼容,因此如果表已经进行了分区,则无法执行聚类。

完成聚类后,可以使用“Optimize”命令触发。

OPTIMIZE table_name;

Liquid Clustering适用于Databricks Runtime 13.3 LTS及更高版本

[1]Databricks为聚类表提供了基于行级并发性的支持,这可以减少并发写操作(包括OPTIMIZE、INSERT、MERGE、UPDATE和DELETE操作)之间的冲突次数。

向聚类表写入数据 —

大多数操作在写入时不会自动进行数据聚类。可以进行写入数据聚类的操作包括:

  • INSERT INTO 操作
  • CTAS 语句
  • COPY INTO 从 Parquet 格式
  • spark.write.format("delta").mode("append")

以下情况下不适用:

  • 如果写入操作的数据超过 512GB。
  • 如果 SELECT 子查询包含转换、过滤或连接操作。
  • 如果投影列与源表不同。

因为并非所有操作都适用于液体聚类,Databricks 建议频繁运行 OPTIMIZE,以确保所有数据都能有效地进行聚类。

液体聚类是增量的,意味着只有在需要时才会重写数据以适应需要进行聚类的数据。对于经常更新或插入的表,Databricks 建议每一到两个小时调度一个 OPTIMIZE 作业。由于液体聚类是增量的,大多数针对聚类表的 OPTIMIZE 作业运行速度很快。

选择聚类键

Databricks 建议根据常用的查询过滤条件选择聚类键。聚类键可以以任何顺序定义。如果两个列相关,只需要添加其中一个列作为聚类键。

注意:我们只能对收集了统计信息的 4 个聚类键进行操作,默认情况下,Delta 表中的前 32 列会收集它们的统计信息,可以通过表属性 delta.dataSkippingNumIndexedCols 来控制此数量。所有位置索引小于该属性值的列都会收集统计信息。

希望这对你有所帮助… 如果“是”,可以试一试…

在大部分的文章中,我使用了https://docs.databricks.com/en/delta/clustering.html#see-how-table-is-clustered作为参考。

愉快学习…