原文towardsdatascience.com/slowly-changing-dimensions-6a08dc0386aehttps://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/3fd91913dd5df5eacb4f8909d2381f65.pngPawel Czerwinski 在 Unsplash 上的照片在当今动态和竞争的环境中现代组织在他们的数据资产上大量投资。这种投资确保了整个组织范围内的团队——从领导层、产品、工程、财务、市场营销到人力资源——都能做出明智的决策。因此数据团队在使组织能够依赖数据驱动的决策过程方面发挥着关键作用。然而仅仅拥有一个强大且可扩展的数据平台是不够的从存储的数据中提取有价值的洞察力是至关重要的。这正是数据建模发挥作用的地方。从本质上讲数据建模定义了数据是如何存储、组织和访问的以促进洞察力和分析的提取。数据建模的主要目标是确保满足数据需求和需求以有效地支持业务和产品。数据团队努力为组织提供解锁其数据全部潜力的能力但通常会遇到一个与数据结构相关的大挑战这样相关的团队才能进行有意义的分析。这就是为什么在设计数据仓库时建模维度是最重要的方面之一。维度和数据建模随着组织的发展和适应不断变化的需求早期数据模型的简单性往往让位于复杂性。没有适当的建模这种复杂性会迅速失控导致在管理和从数据中提取价值方面的低效和挑战。维度是数据建模的关键组成部分因为它们提供了一个结构化的框架允许数据团队组织他们的数据。本质上维度代表了可以从不同的角度分析和理解数据的不同视角。简而言之维度提供了一个透镜通过这个透镜可以解释数据从而促进决策过程。无论是分析销售趋势、用户参与模式、客户细分还是产品性能维度在衡量和理解数据的各个方面都发挥着关键作用。为了说明这一点让我们考虑一个在不同国家或市场中提供多种产品的企业。以下图表展示了一个代表模型的立方体包含三个维度产品、市场和时间。通过整合这些维度企业可以提取不同的度量标准来指导决策过程。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/8fd12c634354024562847b84b8c60a1e.png数据维度建模 – 来源作者从本质上讲维度以以下几种关键方式帮助组织组织数据维度简化了数据组织并使数据导航更加直观。通过将数据分类到不同的视角中维度促进了相关信息的更容易访问和检索。建立清晰的关系维度与事实表定义了清晰的关系事实表通常存储度量、交易或事件。这些关系使得将上下文与定量数据无缝集成成为可能确保了对潜在信息的全面理解。增强分析能力维度通过允许数据用户提取见解并构建有意义的报告或仪表板来增强分析能力。通过在不同维度上切片、切块和深入挖掘数据组织可以对其运营的各个方面获得更深入的洞察。提高系统性能维度在提高数据系统性能方面发挥着至关重要的作用。通过有效地结构化数据和优化查询维度可以以成本效益高和及时的方式促进有价值见解的提取从而最终增强决策过程。维度确实是数据建模的一个关键方面它们有可能显著影响数据产品的有效性。然而由于数据的动态性它们也带来独特的挑战。数据不是静态的它随时间不断变化。因此实施确保变化被准确捕捉并无缝集成到数据模型中的技术变得越来越重要。理解缓慢变化维度SlowlyChangingDimensions (SCDs) 是数据仓库设计背景下的一个基础概念对数据分析团队的操作能力有直接影响。SCDs缓慢变化维度是一个概念用于解决如何捕捉和存储维度随时间变化的数据。简单来说缓慢变化维度提供了一个框架使数据团队能够在数据仓库中跟踪数据的历史性。未以既正确又符合业务和产品需求的方式建模 SCD 可能导致严重后果。它可能导致无法准确捕获历史数据危及组织报告关键指标的能力。这构成了重大风险因为它破坏了从数据中得出的分析洞察的可靠性和完整性。在更技术性的术语中SCDs 具有相同的自然键和一组可能或可能不随时间变化的数据属性。团队处理这些记录的方式可能决定了是否追踪历史性进而决定了是否可以提取相关的业务指标。此外数据仓库中 SCD 的实现也可能对数据平台的其他方面产生重大影响。例如未能正确建模 SCD 可能导致非幂等数据管道的创建这反过来又可能在数据管理中引入各种挑战。慢变化维度的五种类型处理随时间数据变化带来的挑战涉及采用称为 SCD 类型的各种方法。SCD 类型 0保留原始慢变化维度的第一种类型称为 SCD 类型 0处理的是随时间保持静态的数据。此类数据的例子包括出生日期、国家保险号码或美国人的社会保障号码以及日期维度。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/2b0aee6d92a745f3a8218668fe002f1b.pngSCD 类型 0 适用于属性随时间不变化的数据记录 - 来源作者SCD 类型 1覆盖类型 1 指的是每次发生变化时都会被覆盖的数据记录。这意味着历史记录不会被保留使得无法追踪随时间的变化。在实施此维度之前确定这些属性的历史数据是否必要至关重要。否则历史数据的丢失可能会限制团队的分析能力。例如让我们考虑一家向客户运送产品的企业需要存储送货地址。从运营的角度来看企业只需要客户的最新地址进行配送。然而如果企业还希望分析客户随时间地址变化的频率SCD 类型 1 可能不适用。此类类型不保留历史变化可能会阻碍此类洞察的提取。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/4ca744d994f20d8e502b62c34a604d89.png在 SCD 类型 1 中数据记录中的属性被覆盖历史性不被保留 - 来源作者SCD 类型 2创建新记录SCD 类型 2 涉及每次发生变更时创建一个新记录。这意味着对于相同的自然键会生成一个具有不同代理键的新记录来表示变更。这是 SCD 类型 2 保留历史数据的方式。通过将每个自然键与至少一个代理键关联系统保留随时间变化的变更记录。这种方法允许跟踪历史变化同时保持数据演化的清晰谱系。 自然键与代理键的快速回顾自然键这通常是一个列或一组列它们已经存在于表中即它们是数据模型中实体的属性并且可以用来在表中唯一标识一条记录。代理键这通常是一个系统生成的值——例如 UUID、序列号或唯一标识符——它没有业务意义仅用于在表中唯一标识一条记录。在实践中这意味着与 SCD 类型 1 中覆盖现有记录不同在维度表中添加一条新记录并为其分配自己的代理键。这种方法确保历史数据保持完整和可访问以便进行分析。例如在一个客户更新其地址的场景中而不是修改现有的客户记录而是在维度表中添加一条新记录。这种方法使企业能够分析过去和现在的客户详情从而有助于洞察趋势、行为和历史模式。实现 SCD 类型 2 有几种方法每种方法都有其保留历史数据的方法其中一些包括有效时间间隔的时间戳列一种常见的方法是利用两个时间戳列来表示有效时间间隔。这种方法被广泛使用因为它能够追踪变化发生的时间并促进有效的时间窗口分析。通过记录开始和结束时间戳可以更容易地理解每个数据版本的持续时间。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/5d7de1952d8f2738dd92f868bf01196b.png在 SCD 类型 2 中当发生变更时创建新记录。历史记录被保留——来源作者有效日期和标志列另一种方法是将两种列结合使用一个有效日期列表示变更何时生效一个标志列表示记录的当前有效性状态。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/40904ba926973b8215c450be68a152e8.png在 SCD 类型 2 中当发生变更时创建新记录。历史记录被保留——来源作者SCD 类型 3添加新属性SCD Type 3 通过引入一个新列来保留有限的历史数据来跟踪维度中的变更。具体来说这种类型可以捕获每条记录的一个变更。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/47398c989e03867286163a793a22763c.png在 SCD Type 3 中当发生变更时创建一个新属性。历史性仅保留一个变更。与之前讨论的类型不同SCD Type 3 为至少在一个属性上发生变化的记录维护了相同的自然和代理键。这种方法在主要键必须保持不变并对应单个自然键的场景中特别有用。此外当只需要记录一次变更或保证记录不会进行多次更新时SCD Type 3 是合适的。SCD Type 4历史表符合 SCD Type 4 的维度存储在两个****不同的表中。第一个表维护记录的当前状态而称为历史表的第二个表则保留所有不再有效的过去变更。此外历史表还包括一个额外的属性来表示每个记录创建时的时戳。回到我们的例子每当发生变更时最新记录会在主表中更新同时将条目附加到历史表中并附带有效的时戳属性。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/7ff5b411415b4d27147001e2c3b40f45.png在 SCD Type 4 中记录的当前和历史状态被持久化在两个不同的表中 - 来源作者与 SCD Type 2 不同在 SCD Type 2 中通过向维度表添加新条目来管理历史记录SCD Type 4 解决了快速变化的维度带来的可扩展性问题。在这种方法中预期将频繁发生变化的列被重新定位到单独的历史表中。在数据仓库中实现缓慢变化维度在数据仓库设计的情况下早期考虑缓慢变化维度的建模至关重要。正如之前所强调的在维度内有效捕获历史变化对组织的分析能力有重大影响。选择适当的 SCD 类型不是一个一刀切的决定它取决于业务和技术需求。因此第一步是确定需要保留历史记录的维度。虽然某些维度可能不需要捕获变更但其他维度则要求保留历史记录。如果关于是否应捕获某些维度的历史变更存在不确定性建议谨慎行事并选择维护历史数据的 SCD 类型。除非数据摄取管道和作业可以完全重放这在我的经验中并不总是如此否则这种方法特别谨慎。在未捕获变更且数据摄取管道缺乏可重放性的情况下永久丢失历史数据的风险变得明显。这种损失可能会严重限制组织进行回顾性分析和从历史趋势和模式中提取有价值见解的能力。因此仔细考虑和采取主动措施对于确保数据仓库中历史数据完整性的保护至关重要。选择合适的 SCD 类型应根据维度的性质和预期的变更频率来确定。需要注意的是不同的维度可能需要不同的 SCD 类型。然而实施多种SCD类型意味着团队将需要管理几种不同的模式这需要仔细考虑。虽然这可能会引入复杂性但确保跨各种维度准确表示和维护历史数据至关重要。如前所述这些决策位于业务和技术需求交汇处。因此不仅需要数据工程师参与还需要数据分析师和数据分析工程师参与定义实际业务需求。这种协作方法确保了技术可行性和业务目标都得到有效解决。https://github.com/OpenDocCN/towardsdatascience-blog-zh-2024/raw/master/docs/img/af6bbb186c40f23412cf54e76969b063.png数据工程师、分析师和数据分析工程师之间的协作对于确定建模缓慢变化维度的最有效方法至关重要——来源作者在捕捉到业务需求后摄取过程中的技术实现必须适应已确定的要求。这确保了数据摄取过程与既定的业务需求有效对齐并满足。现在在技术方面有一些需要考虑的因素。ELT 管道从外部源以批量方式摄取数据的一种方法是通过ELT 管道。本质上ELT 管道通过从源提取数据将其加载到目标系统中然后对摄取的原始数据进行转换来工作。根据特定缓慢变化维度的建模方式ELT管道需要相应地表现以遵守由相应的SCD类型指定的要求。SCD 类型 0管道只需加载新记录因为现有记录没有更新。SCD 类型 1管道不需要保留历史性可以使用MERGE INTO查询来插入新记录并覆盖匹配指定自然键的现有记录。SCD 类型 2管道需要为维度表上的每次更改插入新记录以及指示特定记录有效时间窗口的附加时间戳列。MERGE INTO查询可以简化插入新记录的过程并更新不再有效的现有记录的有效结束日期。SCD 类型 3管道可以使用MERGE INTO查询来插入新记录和/或更新现有记录以添加已更改的属性当前值。SCD 类型 4ELT 管道现在需要在两个表中添加或更新记录。根据您实现 SCD 类型 4 的方式您需要相应地调整管道的操作。UDPATE以及因此的MERGE INTO在此类 SCD 中不太适用。因此您可以编写一个查询将新记录插入由当前维度状态组成的表中并捕获历史表中的历史变化。上述步骤可以在摄取时保留您首选的 SCD 类型。然而许多团队需要在更多数据模型中应用维度建模。在 ELT 管道中实现转换步骤的常用工具是 数据构建工具 (dbt)。除了确保源表遵守处理缓慢变化维度的预定策略外考虑保留由后续转换产生其他数据模型中的历史数据也很重要。dbt 提供 快照这是一种捕获可变表随时间变化的机制。dbt 快照固有地实现了 SCD 类型 2 功能使它们成为管理转换数据集中历史数据的便捷解决方案。数据捕获CDC如前所述ELT 管道通常用于批量摄取数据。这意味着源中发生的变化将由 ELT 管道以较慢的速度捕获因为这些作业被安排在每小时、每天甚至每周/每月的日程上。变更数据捕获模式可以用于捕获和摄取接近实时数据变化。这是一个常用的设计模式旨在保持源和目标系统同步同时保留随时间发生的历史变化。在技术术语上CDC 可以帮助我们确定何时创建或更改了记录。通过 CDC 摄取的每条记录通常都会指示何时发生更改新记录的属性是什么以及它相关的操作类型即INSERT、UPDATE或DELETE。尽管 CDC 可以用于几乎所有的 SCD 类型但根据我的经验它被广泛采用作为建模 SCD 类型 2 的一部分。SCD 对数据管道幂等性的影响当构建数据****管道时确保它们是幂等的至关重要。用于捕获变化维度的方法可能会显著影响团队构建幂等管道和工作流程的能力这些管道和工作流程从数据仓库中消耗数据。关于幂等数据管道的快速复习幂等管道对于相同的输入无论何时或运行多少次它总是产生相同的结果。SCD 类型 0由于这些维度不会随时间变化因此实际上不会影响数据管道的幂等性。SCD 类型 1在此类型中仅保留属性的最新值。因此从使用 SCD 类型 1 建模的源消耗数据的管道不是幂等的。每次发生更改且管道重新运行时都会生成不同的输出。SCD 类型 2当谈到构建幂等管道时这种类型可能是完美的。然而在使用起始和结束有效性区间时需要小心。SCD 类型 3这种 SCD 类型可以被认为是部分幂等的但由于它只捕获到一次数据变更我会将其视为非幂等的除非可以保证属性不会改变超过一次。最后的想法有效地捕获和管理数据维度中的变化是设计良好的数据仓库的基本要素。因此了解每个维度应该如何建模考虑到属性变化的频率和性质至关重要。此外认识到 ELT 管道或 CDC 等流程的更广泛影响至关重要。这些流程可以显著影响维度数据随时间演变的方式。需要强调的是没有一种适合所有情况的解决方案。相反决策应基于组织独特的业务和分析需求。保留并适当建模历史数据更改是数据工程团队的核心责任。这不仅确保了数据完整性还最大限度地提高了有效利用组织数据的能力。