如何用SQL筛选跨多行满足双条件的客户记录
客户多行为记录表筛选实现方案
基础表结构说明
待处理的客户行为存储表共包含3个字段:
id:客户唯一标识type:行为分类字段event:行为事件字段
表中单个客户对应多行独立的行为记录,需按指定规则完成两层过滤。
核心筛选规则
- 客户级过滤:仅保留同时满足两个跨行列条件的客户,即该客户的所有记录中,既存在
type="medium"的行,也存在event="gym"的行,两个条件无需在同一行命中。不满足该要求的客户,其名下所有记录全量剔除。 - 行级过滤:对通过客户级校验的客户,仅保留其名下*行内满足
type="medium"或event="gym"*的记录,其余不符合单条件的行全部剔除。 - 结果校验参考:按样例逻辑,id为2的客户因不存在
type="medium"的记录会被全量剔除,最终保留id为1、3的客户下共4条符合行级要求的记录。
代码实现
SQL 实现(通用绝大多数OLAP/OLTP数据库引擎)
-- 先通过聚合筛选出符合双条件的有效客户id,再关联原表做行级过滤 WITH valid_customer AS ( SELECT id FROM user_behavior GROUP BY id HAVING SUM(CASE WHEN type = 'medium' THEN 1 ELSE 0 END) > 0 AND SUM(CASE WHEN event = 'gym' THEN 1 ELSE 0 END) > 0 ) SELECT t.* FROM user_behavior t INNER JOIN valid_customer vc ON t.id = vc.id WHERE t.type = 'medium' OR t.event = 'gym';
该写法逻辑拆分清晰,无复杂嵌套,在MySQL、Hive、Spark SQL、PostgreSQL等主流引擎中均可直接运行,执行效率稳定。
Pandas 实现(适用于本地离线数据处理场景)
import pandas as pd # 加载原始行为数据 df = pd.read_csv("user_behavior.csv") # 第一步:筛选同时满足两个跨行列条件的有效客户id valid_ids = df.groupby("id").apply( lambda group: (group["type"] == "medium").any() and (group["event"] == "gym").any() ) valid_ids = valid_ids[valid_ids].index # 第二步:过滤无效客户,同时过滤有效客户下不符合单条件的行 final_result = df[ df["id"].isin(valid_ids) & ((df["type"] == "medium") | (df["event"] == "gym")) ]
内容的提问来源于stack exchange,提问作者Steven
相关产品推荐
相关产品推荐

