本文目录导读:

Python中清洗原始数据是一个非常常见的任务,通常使用pandas库来完成,以下是一些最常见的清洗场景和对应的Python代码示例:
导入必要的库
import pandas as pd import numpy as np import matplotlib.pyplot as plt import seaborn as sns %matplotlib inline # 如果在Jupyter Notebook中
加载原始数据
# 从CSV文件加载
df = pd.read_csv('raw_data.csv')
# 查看数据的基本信息
print("数据形状:", df.shape)
print("\n前5行数据:")
df.head()
print("\n数据类型和缺失值:")
df.info()
print("\n描述性统计:")
df.describe(include='all')
处理缺失值
# 查看每列的缺失值数量 print(df.isnull().sum()) # 删除含有缺失值的行 df_cleaned = df.dropna() # 删除特定列有缺失值的行 df_cleaned = df.dropna(subset=['重要列名']) # 用特定值填充缺失值 df['列名'] = df['列名'].fillna(0) # 填充0 df['列名'] = df['列名'].fillna(df['列名'].mean()) # 填充均值 df['列名'] = df['列名'].fillna(df['列名'].median()) # 填充中位数 df['列名'] = df['列名'].fillna(method='ffill') # 用前一个值填充 df['列名'] = df['列名'].fillna(method='bfill') # 用后一个值填充 # 对于分类数据,用众数填充 df['分类列'] = df['分类列'].fillna(df['分类列'].mode()[0])
处理重复值
# 检查重复行
print(f"重复行数量: {df.duplicated().sum()}")
# 查看重复行
df[df.duplicated()]
# 删除重复行
df_cleaned = df.drop_duplicates()
# 删除指定列的重复行
df_cleaned = df.drop_duplicates(subset=['列1', '列2'])
# 保留最后出现的重复行
df_cleaned = df.drop_duplicates(keep='last')
处理异常值
# 方法1:使用Z-score检测异常值 from scipy import stats z_scores = np.abs(stats.zscore(df['数值列'])) df_cleaned = df[(z_scores < 3)] # 保留Z-score小于3的数据 # 方法2:使用IQR(四分位距)检测异常值 Q1 = df['数值列'].quantile(0.25) Q3 = df['数值列'].quantile(0.75) IQR = Q3 - Q1 lower_bound = Q1 - 1.5 * IQR upper_bound = Q3 + 1.5 * IQR df_cleaned = df[(df['数值列'] >= lower_bound) & (df['数值列'] <= upper_bound)] # 方法3:用上下限值替换异常值(winsorize处理) df['数值列'] = np.where(df['数值列'] < lower_bound, lower_bound, df['数值列']) df['数值列'] = np.where(df['数值列'] > upper_bound, upper_bound, df['数值列'])
数据类型转换
# 转换数据类型
df['日期列'] = pd.to_datetime(df['日期列']) # 转日期类型
df['数值列'] = pd.to_numeric(df['数值列'], errors='coerce') # 转数值类型,无效值转为NaN
df['字符串列'] = df['字符串列'].astype(str) # 转字符串类型
df['分类列'] = df['分类列'].astype('category') # 转分类类型
# 处理数值列中的特殊字符
df['价格列'] = df['价格列'].str.replace('$', '').str.replace(',', '').astype(float)
文本数据清洗
# 去除空格
df['文本列'] = df['文本列'].str.strip() # 去除前后空格
df['文本列'] = df['文本列'].str.replace(' ', '') # 去除所有空格
# 统一大小写
df['文本列'] = df['文本列'].str.lower() # 转小写
df['文本列'] = df['文本列'].str.upper() # 转大写
# 替换特殊字符
df['文本列'] = df['文本列'].str.replace('[^a-zA-Z0-9]', '', regex=True) # 只保留字母和数字
# 去除特定模式
df['文本列'] = df['文本列'].str.replace('\d+', '', regex=True) # 去除数字
完整的清洗函数示例
def clean_data(df):
"""
数据清洗函数
"""
# 创建副本
df_cleaned = df.copy()
# 1. 删除完全重复的行
df_cleaned = df_cleaned.drop_duplicates()
# 2. 处理缺失值
# 删除缺失值超过50%的列
df_cleaned = df_cleaned.dropna(thresh=len(df_cleaned)*0.5, axis=1)
# 数值列用中位数填充
numeric_cols = df_cleaned.select_dtypes(include=[np.number]).columns
for col in numeric_cols:
df_cleaned[col].fillna(df_cleaned[col].median(), inplace=True)
# 分类列用众数填充
categorical_cols = df_cleaned.select_dtypes(include=['object']).columns
for col in categorical_cols:
df_cleaned[col].fillna(df_cleaned[col].mode()[0], inplace=True)
# 3. 去除异常值(使用IQR方法)
for col in numeric_cols:
Q1 = df_cleaned[col].quantile(0.25)
Q3 = df_cleaned[col].quantile(0.75)
IQR = Q3 - Q1
lower_bound = Q1 - 1.5 * IQR
upper_bound = Q3 + 1.5 * IQR
df_cleaned[col] = df_cleaned[col].clip(lower_bound, upper_bound)
# 4. 重置索引
df_cleaned.reset_index(drop=True, inplace=True)
return df_cleaned
# 使用清洗函数
df_cleaned = clean_data(df)
print(f"\n清洗前数据量: {len(df)}")
print(f"清洗后数据量: {len(df_cleaned)}")
print(f"清洗掉的数据量: {len(df) - len(df_cleaned)}")
保存清洗后的数据
# 保存为CSV
df_cleaned.to_csv('cleaned_data.csv', index=False)
# 保存为Excel
df_cleaned.to_excel('cleaned_data.xlsx', index=False)
可视化检查数据分布
# 查看数值列的分布(洗前 vs 洗后)
fig, axes = plt.subplots(1, 2, figsize=(12, 4))
# 清洗前
axes[0].hist(df['数值列'], bins=30, edgecolor='black')
axes[0].set_title('清洗前')
# 清洗后
axes[1].hist(df_cleaned['数值列'], bins=30, edgecolor='black')
axes[1].set_title('清洗后')
plt.show()
这个完整的案例涵盖了数据清洗的各个方面,根据你的实际数据和需求,可以选择使用其中的某些部分,关键是要先了解数据的特点(通过df.info()和df.describe()),然后针对性地进行清洗。