Python 数据分析与可视化 Day 11 - 特征工程基础
✅ 今日目标
- 理解特征工程在数据分析和机器学习中的意义
- 掌握常见特征类型的处理方式:数值型、类别型、时间型
- 学习特征提取、转换、标准化、独热编码(One-Hot Encoding)等核心操作
- 为后续建模任务做好特征准备工作
📚 一、什么是特征工程?
特征工程是将原始数据转换为模型可学习的“特征向量”的过程,是机器学习效果好坏的核心因素之一。
常见任务包括:
- 缺失值处理(已学)
- 异常值处理(已学)
- 数值归一化、标准化
- 类别变量编码(如性别)
- 日期拆解(年月日、周几等)
- 派生变量(如是否及格、高分标签)
📘 二、类别变量编码(以“性别”为例)
1. Label Encoding(标签编码)
from sklearn.preprocessing import LabelEncoderdf = pd.read_csv("data/students_cleaned.csv")
le = LabelEncoder()
df["性别编码"] = le.fit_transform(df["性别"])
print(df[["性别", "性别编码"]].drop_duplicates())
⚠️ 只适用于有序类别;对无序分类不推荐(会引入数值大小误导)
2. One-Hot Encoding(独热编码)
df_onehot = pd.get_dummies(df, columns=["性别"])
print(df_onehot.head())
📘 三、数值特征转换
1. 标准化(Standardization)
from sklearn.preprocessing import StandardScalerscaler = StandardScaler()
df["成绩标准化"] = scaler.fit_transform(df[["成绩"]])
2. 归一化(MinMax)
from sklearn.preprocessing import MinMaxScalerscaler = MinMaxScaler()
df["成绩归一化"] = scaler.fit_transform(df[["成绩"]])
📘 四、派生特征举例
# 是否及格(True/False → 1/0)
df["是否及格"] = df["成绩"] >= 60
df["是否及格数值"] = df["是否及格"].astype(int)# 成绩分段
df["成绩等级"] = pd.cut(df["成绩"], bins=[0, 60, 80, 100], labels=["不及格", "良", "优"])
📘 五、时间特征提取(如加入考试时间)
df["考试时间"] = pd.to_datetime("2024-06-01")
df["考试月"] = df["考试时间"].dt.month
df["考试周"] = df["考试时间"].dt.isocalendar().week
df["考试星期"] = df["考试时间"].dt.day_name()
🧪 今日练习建议(可生成脚本:feature_engineering.py
)
-
对性别进行标签编码和 One-Hot 编码
-
对成绩做归一化和标准化
-
派生字段:“是否及格数值”、“成绩等级”
-
添加时间字段并提取月、周、星期等信息
-
查看不同特征对模型潜在价值的分析(可选)
代码示例:
import pandas as pd import numpy as np from sklearn.preprocessing import LabelEncoder, OneHotEncoder, StandardScaler, MinMaxScaler import os# 加载数据 data_path = "data/students_cleaned.csv" if not os.path.exists(data_path):raise FileNotFoundError("❌ 缺少数据文件:students_cleaned.csv,请先运行清洗脚本")df = pd.read_csv(data_path) print("✅ 原始数据预览:") print(df)# ================== 一、类别编码 ==================print("\n🔢 LabelEncoder 编码 '性别':") le = LabelEncoder() df["性别编码"] = le.fit_transform(df["性别"]) print(df[["性别", "性别编码"]].drop_duplicates())print("\n🧊 One-Hot 编码 '性别':") df = pd.get_dummies(df, columns=["性别"]) print(df)# ================== 二、数值特征转换 ==================print("\n📐 标准化成绩(StandardScaler):") scaler_std = StandardScaler() df["成绩_标准化"] = scaler_std.fit_transform(df[["成绩"]])print("\n📏 归一化成绩(MinMaxScaler):") scaler_minmax = MinMaxScaler() df["成绩_归一化"] = scaler_minmax.fit_transform(df[["成绩"]])# ================== 三、派生特征 ==================print("\n✅ 添加是否及格字段(布尔 + 数值):") df["是否及格"] = df["成绩"] >= 60 df["是否及格_数值"] = df["是否及格"].astype(int)print("\n🎯 成绩等级分段:") df["成绩等级"] = pd.cut(df["成绩"], bins=[0, 60, 80, 100], labels=["不及格", "良", "优"])# ================== 四、时间特征处理 ==================print("\n🗓️ 添加考试时间字段:") df["考试时间"] = pd.to_datetime("2024-06-01") df["考试月"] = df["考试时间"].dt.month df["考试周"] = df["考试时间"].dt.isocalendar().week df["考试星期"] = df["考试时间"].dt.day_name()# ================== 五、保存结果 ==================os.makedirs("data/processed", exist_ok=True) output_path = "data/processed/students_featured.csv" df.to_csv(output_path, index=False)print(f"\n✅ 特征工程完成,已保存至:{output_path}")
运行结果:
✅ 原始数据预览:姓名 性别 成绩 是否及格 0 张三 男 88.0 True 1 李四 女 78.0 True 2 王五 男 59.0 False 3 田七 女 78.0 False🔢 LabelEncoder 编码 '性别':性别 性别编码 0 男 1 1 女 0🧊 One-Hot 编码 '性别':姓名 成绩 是否及格 性别编码 性别_女 性别_男 0 张三 88.0 True 1 False True 1 李四 78.0 True 0 True False 2 王五 59.0 False 1 False True 3 田七 78.0 False 0 True False📐 标准化成绩(StandardScaler):📏 归一化成绩(MinMaxScaler):✅ 添加是否及格字段(布尔 + 数值):🎯 成绩等级分段:🗓️ 添加考试时间字段:✅ 特征工程完成,已保存至:data/processed/students_featured.csv
students_featured.csv数据如图所示:
🧾 今日总结
特征类型 | 操作建议 |
---|---|
数值型 | 标准化 / 归一化 / 分段 |
类别型 | Label / OneHot 编码 |
时间型 | 拆分年月日、周几、节假日等 |
衍生型 | 等级、标签、数值映射 |
特征工程是数据科学的核心内容之一,好的特征往往胜过复杂模型。