Pandas教学-10:apply与map的典型案例

📅 发布时间:2026/10/13 9:24:36
Pandas教学-10:apply与map的典型案例
# -*- coding: utf-8 -*- 案例员工年终奖核算 演示 map 与 apply 的典型用法 知识点 1. Series.map(字典) —— 值映射把部门别名统一成标准名称 2. Series.map(函数) —— 逐格文本清洗全角转半角、去空格 3. Series.apply(函数) —— 逐元素套用判断规则绩效等级 - 描述 4. DataFrame.apply(函数, axis1) —— 逐行跨列计算算年终奖 5. map 与 replace 的差异map 未命中变 NaNreplace 未命中原样保留 运行后 直接在控制台打印清洗与计算后的结果无需 Excel 文件 import unicodedata import pandas as pd def build_data(): 构造一份“脏”数据部门别名混用、姓名带空格与全角英文 return pd.DataFrame({ 姓名: [ 张三, 李四 , , 赵六, 钱七], 部门: [技术, 研发部, tech, 市场, 人事部], 绩效: [A, B, A, C, B], 月薪: [20000, 15000, 30000, 12000, 18000], }) # 部门别名 - 标准名称以后新增别名只改这里 DEPT_MAP { 技术: 技术部, 研发部: 技术部, tech: 技术部, 市场: 市场部, 营销部: 市场部, marketing: 市场部, 人事部: 人事部, hr: 人事部, } # 绩效等级 - 年终奖系数月薪的倍数 BONUS_MAP {A: 3.0, B: 2.0, C: 1.0} def clean_name(x): 全角转半角 去首尾空格 - Wang Wu return unicodedata.normalize(NFKC, str(x)).strip() def perf_to_grade(p): 绩效字母 - 中文描述 if p A: return 优秀 elif p B: return 良好 else: return 待改进 def calc_bonus(row): row 是整行一个 Series可同时读取‘绩效’与‘月薪’ return round(row[月薪] * BONUS_MAP[row[绩效]], 2) def main(): df build_data() # ---------- 1. map 用法①字典映射部门别名归一 ---------- df[部门] df[部门].map(DEPT_MAP) # ---------- 2. map 用法②传函数逐格做文本清洗 ---------- df[姓名] df[姓名].map(clean_name) # ---------- 3. apply 用法①Series.apply逐元素套复杂规则 ---------- df[绩效描述] df[绩效].apply(perf_to_grade) # ---------- 4. apply 用法②DataFrame.apply(axis1)逐行算年终奖 ---------- df[年终奖] df.apply(calc_bonus, axis1) print( 核算结果 ) print(df.to_string(indexFalse)) # # 课堂练习题目 # ---------------------------------------------------------------------- # 练习1把第 3 步的 apply 改成 map(lambda ...)验证结果是否相同。 # 练习2把第 1 步的 map(DEPT_MAP) 改成 replace(DEPT_MAP) # 并让数据里出现一个映射表没有的部门观察两者差异。 # 练习3再加一列“综合评级”绩效描述为“优秀”且月薪 25000 # 记为“核心骨干”否则为“普通员工”。 # # # 参考答案讲课用学生可先自行完成后对照 # ---------------------------------------------------------------------- # 练习1 参考 # df[绩效描述] df[绩效].map(lambda p: 优秀 if p A # else 良好 if p B else 待改进) # # 结论传函数时 map 与 apply 结果完全一致 # # 二者真正的差别在“能否直接吃字典”map 可以apply 不行。 # # 练习2 参考 # s pd.Series([技术, 财务部]) # “财务部”不在映射表里 # print(s.map(DEPT_MAP).tolist()) # [技术部, nan] # print(s.replace(DEPT_MAP).tolist()) # [技术部, 财务部] # # 结论map 未命中 - NaN可用来发现遗漏的别名 # # replace 未命中 - 原样保留做标准化更安全。 # # 练习3 参考 # def level(row): # if row[绩效描述] 优秀 and row[月薪] 25000: # return 核心骨干 # return 普通员工 # # df[综合评级] df.apply(level, axis1) # # 结果仅 “Wang Wu”优秀且月薪 30000被评为“核心骨干”。 # if __name__ __main__: main()