跳到正文

更多文章

影响力日常操作系统:21天习惯养成计划 从技能雇佣者到价值创造者 互惠账户的运营 影响力的三层架构 组织的注意力经济学
从字节跳动SQL面试题看数据思维:如何用中间表设计优雅解决亿级数据问题

本文来源于数据从业者全栈知识库,更多体系化内容请访问知识库。

一道看似简单的SQL题,背后考察的是你对数据仓库分层设计的理解,特别是中间表的设计能力。

引子:那道让人”脑雾”的面试题

最近,一位朋友分享了他在字节跳动面试大数据开发工程师的经历。面试官给了一道SQL题:

场景:抖音流量日志表visit_log,包含用户ID(uid)和访问时间戳(timestamp),按日期(date)分区。数据规模:日增百亿级记录。

需求

  1. 计算T日的用户7日留存率
  2. 统计每个用户近1/7/30/365天的访问天数
  3. 找出近7天内访问间隔在24小时内的用户

朋友说:“我当时就写了个JOIN,面试官问:‘你们生产环境真的会这么查询吗?没有中间表吗?’ 我就懵了…”

关键洞察:面试官真正想了解的是,你是否知道如何设计中间表来支撑业务查询,而不是每次都从原始日志计算。

一、为什么直接查询原始表是错误的?

生产环境的残酷现实

-- 没有人会在生产环境这么写
SELECT COUNT(DISTINCT a.uid)
FROM visit_log a
JOIN visit_log b ON a.uid = b.uid
WHERE a.date = 'T' AND b.date BETWEEN 'T+1' AND 'T+7'

问题不仅是性能:

  • 原始日志表数据量巨大,查询成本极高
  • 每次查询都要重新计算,浪费资源
  • 无法支撑复杂的业务需求
  • 数据口径不统一,容易出错

数据仓库的核心理念:空间换时间

层级表类型数据特点查询场景
ODS原始日志最细粒度,数据量大几乎不直接查询
DWD明细事实表清洗后的明细少量明细查询
DWS轻度汇总表用户粒度汇总常规分析查询
ADS应用层表高度聚合报表直接查询

二、核心解决方案:设计合理的中间表

方案一:用户状态快照表(最常用)

-- 每日创建用户状态快照表(T+1凌晨运行)
CREATE TABLE dws_user_daily_snapshot (
uid BIGINT COMMENT '用户ID',
date STRING COMMENT '快照日期',
-- 核心状态字段
first_visit_date STRING COMMENT '首次访问日期',
last_visit_date STRING COMMENT '最后访问日期',
total_visit_days INT COMMENT '累计访问天数',
-- 近期活跃度指标(这些字段直接支撑业务查询)
visits_last_1d INT COMMENT '近1天访问天数',
visits_last_7d INT COMMENT '近7天访问天数',
visits_last_30d INT COMMENT '近30天访问天数',
visits_last_365d INT COMMENT '近365天访问天数',
-- 访问间隔特征
last_visit_gap_hours INT COMMENT '最近两次访问间隔小时数',
is_frequent_user INT COMMENT '是否24小时内多次访问用户',

PRO 会员专属

本文为 PRO 会员专属内容,成为会员即可阅读全文。

PRO ¥199/年 · Pro 专属文章 + 2300+ 知识文档 + 会员社群

Elazer (石头)
Elazer (石头)

11 年数据老兵,从分析师到架构专家。用真实经历帮数据人少走弯路。

加入免费社群

和数据从业者一起交流成长

了解详情 →

成为会员

解锁全部内容 + 知识库

查看权益 →
← 上一篇 即时零售盈利拐点预测:单位经济模型优化路径 下一篇 → 给不同阶段学习者的真诚建议