如何使用循环函数批量UNION ALL非连续命名的feature日期数据表
批量合并
feature_日期格式表的可行方案 核心原则:不要自行生成连续日期、维护节假日列表匹配表名,直接从数据库系统元数据里捞真实存在的、符合命名规则的表再做拼接,从根源避免表不存在触发的报错,也不需要额外维护节假日规则。
方案1:纯SQL动态拼接实现(推荐,适合数仓/MySQL/PostgreSQL等场景,性能最优)
不需要写复杂循环,直接通过元数据生成可执行的UNION ALL语句即可,逻辑分两步:
- 从系统内置的
information_schema.tables元数据表中,过滤出所有表名匹配feature_+8位日期格式的业务表 - 给所有符合要求的表拼接
SELECT * FROM 表名片段,中间用UNION ALL连接,生成完整合并语句后直接执行
以MySQL为例的实现代码:
-- 替换为自己的业务库名、最终合并结果的表名 SET @target_db = '你的业务库名'; SET @result_table = 'feature_total_merged'; -- 动态拼接完整UNION ALL语句 SET @union_sql = ( SELECT CONCAT( 'CREATE TABLE ', @result_table, ' AS ', GROUP_CONCAT(CONCAT('SELECT * FROM ', table_name) SEPARATOR ' UNION ALL ') ) FROM information_schema.tables WHERE table_schema = @target_db -- 正则严格匹配表名规则,过滤无关表 AND table_name REGEXP '^feature_[0-9]{8}$' ); -- 执行生成的合并语句 PREPARE merge_stmt FROM @union_sql; EXECUTE merge_stmt; DEALLOCATE PREPARE merge_stmt;
适配说明:如果是Hive/Spark SQL等大数据引擎,把
GROUP_CONCAT替换为CONCAT_WS,执行语句部分替换为EXECUTE IMMEDIATE @union_sql即可,核心逻辑完全一致。
方案2:Python脚本循环合并(适合需要本地做二次数据处理的场景)
如果需要在合并后做额外的Python侧数据加工,可以按这个逻辑实现,依然是先捞真实表名再循环读取合并,不要自行生成日期列表:
import pandas as pd from sqlalchemy import create_engine # 替换为自己的数据库连接信息 db_engine = create_engine('mysql+pymysql://账号:密码@数据库地址:端口/业务库名') # 第一步:查询所有符合命名规则的真实表名 valid_tables = pd.read_sql( """ SELECT table_name FROM information_schema.tables WHERE table_schema = '你的业务库名' AND table_name REGEXP '^feature_[0-9]{8}$' """, db_engine )['table_name'].tolist() # 第二步:循环读取所有表后合并 df_collector = [] for table in valid_tables: # 也可以在这里加自定义的字段过滤、清洗逻辑 tmp = pd.read_sql(f"SELECT * FROM {table}", db_engine) df_collector.append(tmp) final_df = pd.concat(df_collector, ignore_index=True)
性能提示:如果1000张表总数据量超过千万级,不要用pandas本地合并,优先用方案1在数仓侧分布式执行,或者用PySpark替换pandas做分布式合并,避免内存溢出。
注意避坑
- 合并前建议先校验所有表的字段数量、字段名、字段类型一致性,避免UNION ALL时出现字段错位、类型不兼容报错
- 不要硬编码日期范围、维护节假日跳过规则,业务侧漏跑任务、临时补数都会导致表存在性和日期规则不一致,从元数据取表是最稳妥的方案
- 如果不需要全字段合并,可以把代码里的
SELECT *替换成实际需要的字段列表,减少数据扫描量提升速度
内容的提问来源于stack exchange,提问作者陳冠儒
相关产品推荐
相关产品推荐

