数据库表的列式存储(Column-oriented Storage)是优化分析查询性能方面的一个重要因素,因为它将大大降低总体磁盘 I/O 要求并减少需从磁盘加载的数据量。在典型的关系数据库表中,每个行均包含一条记录的字段值。在行式数据库存储中,数据块按顺序存储每个连续列(构成整个行)的值。如果数据块大小小于记录的大小,整个记录的存储可采用多个数据块。如果块大小大于记录的大小,整个记录的存储可能采用 1 个以上的数据块,从而导致磁盘空间的使用低效。在线事务处理 (OLTP) 应用程序中,大多数事务涉及频繁读取和写入整个记录的所有值,通常一次读取和写入一条记录或几条记录。最终,行式存储已针对 OLTP 数据库进行优化。
使用列式存储,每个数据块可为多个行存储一个列的值。由于每个块可保留相同类型的数据,因此块数据可使用专为列数据类型选择的压缩方案,进一步减少磁盘空间和 I/O。
磁盘上用于存储数据的空间节省将继续存在,以便检索数据并将其存储在内存中。由于许多数据库操作一次只需访问或操作一个或几个列,您可通过仅检索查询实际所需的列的数据块来节省内存空间。其中,OLTP 事务通常涉及少量记录的一个行中的大多数列或所有列,数据仓库查询通常仅读取大量行的几个列。这意味着,读取相同数目的行的相同数目的列字段值需要一小部分 I/O 操作并使用处理行式块所需的内存的一部分。实际上,通过使用具有大量列和行的表,可大幅提高效率。例如,假定一个表包含 100 个列。使用 5 个列的查询仅需读取表中 5% 的数据。对于大型数据库,可为数十亿或甚至数万亿记录实现此节省。相反,一个行式数据库将读取包含 95 个不需要的列的数据块。
列式存储的优点如下:
- 极高的装载速度(最高可以等于所有硬盘IO 的总和,基本是极限了)
- 适合大量的数据而不是小数据
- 实时加载数据仅限于增加(删除和更新需要解压缩Block 然后计算然后重新压缩储存)
- 高效的压缩率,不仅节省储存空间也节省计算内存和CPU。
- 非常适合做聚合操作。
列式存储的缺点如下:
- 不适合扫描小量数据
- 不适合随机的更新
- 批量更新情况各异,有的优化的比较好的列式数据库(比如Vertica)表现比较好,有些没有针对更新的数据库表现比较差。
- 不适合做含有删除和更新的实时操作。
资料来源:
列式存储 https://docs.amazonaws.cn/redshift/latest/dg/c_columnar_storage_disk_mem_mgmnt.html
处理海量数据:列式存储综述(存储篇) https://zhuanlan.zhihu.com/p/35622907
浅析列式数据库的特点 https://searchdatabase.techtarget.com.cn/7-20958/