机器学习基础~04.数据清洗

第 1 节 缺失值

摘要

缺失值的处理分为判断缺失值、展示缺失值、填补(删除)缺失值几步。

1.1 判断缺失值

判断数据中是否存在缺失值,以及缺失值的个数,方法如下:

1
2
3
4
5
6
7
df = pd.read_csv('data.csv',encoding='utf-8-sig',index_col=0)

#判断每列是否有缺失值
df.isnull().any()

#缺失值个数
df.isnull().sum()

1.2 展示缺失值

使用热力图展示数据中的缺失值,方法如下:

1
2
3
4
5
6
7
8
import pandas as pd
import seaborn as sns
import matplotlib.pyplot as plt

plt.figure(figsize=(8, 6))
sns.heatmap(df.isnull(), cmap='viridis', cbar=False)
plt.title('Missing Values Heatmap')
plt.show()

1.3 删除缺失值

如果缺失值较少,可以采用删除缺失值的方法处理,方法如下:

1
2
3
df2 = df.copy()
#删除df2中缺失值所在行
df2.dropna(axis = 0,inplace = True)

1.4 填补缺失值

缺失值较多时,可以考虑填补缺失值的方法处理,包括:

  • 插值法:通过插值方法填补缺失值,如均值插值、中位数插值、最近邻插值、多项式插值等。
  • 模型法:使用回归、决策树或神经网络等模型预测缺失值,但需要先对数据进行训练和测试,可能会导致模型的过拟合和不准确。
  • 多重填补法:使用多个模型进行填补,可以提高填补缺失值的准确性和可靠性。
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
# 均值插值
df2.apply(lambda x:x.fillna(x.mean(),inplace=True))

# 中位数插值
df2.apply(lambda x:x.fillna(x.median(),inplace=True))

# 均值插值
from sklearn.impute import SimpleImputer
imputer = SimpleImputer(strategy='mean')
X_imputed = imputer.fit_transform(X)

# 回归法
from sklearn.impute import IterativeImputer
imputer = IterativeImputer()
X_imputed = imputer.fit_transform(X)

# 最近邻插值
from sklearn.impute import KNNImputer
imputer = KNNImputer()
X_imputed = imputer.fit_transform(X)

第 2 节 异常值

常见的异常值检测方法包括基于统计学的方法、基于距离的方法、基于密度的方法和基于模型的方法。

处理异常值的方法包括删除、替换、调整或利用异常值建立新的模型等。

函数 介绍
sklearn.ensemble.IsolationForest() 使用隔离森林方法检测异常值。
sklearn.svm.OneClassSVM() 使用支持向量机方法进行单类异常值检测。
sklearn.covariance.EllipticEnvelope() 使用基于高斯分布的椭圆包络方法检测异常值。
sklearn.neighbors.LocalOutlierFactor() 使用局部离群因子方法检测异常值。
sklearn.covariance.RobustCovariance() 使用鲁棒协方差估计进行异常值检测。
sklearn.covariance.mahalanobis() 计算马哈拉诺比斯距离来检测异常值。

2.1 绘制决策边界

决策边界是判断一个值是否是异常值的边界条件,可以直观展示判断异常值的过程:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
import numpy as np
import matplotlib.pyplot as plt
from sklearn.svm import OneClassSVM

# 创建一个示例数据集
np.random.seed(42)
X = 0.3 * np.random.randn(100, 2)
X_train = np.r_[X + 2, X - 2]

# 创建 OneClassSVM 模型
clf = OneClassSVM(nu=0.1, kernel="rbf", gamma=0.1)
clf.fit(X_train)

# 创建一个网格来绘制决策边界
xx, yy = np.meshgrid(np.linspace(-5, 5, 500), np.linspace(-5, 5, 500))
Z = clf.decision_function(np.c_[xx.ravel(), yy.ravel()])
Z = Z.reshape(xx.shape)

# 绘制决策边界和支持向量
plt.figure(figsize=(10, 10))
plt.contourf(xx, yy, Z, levels=np.linspace(Z.min(), 0, 2), cmap=plt.cm.PuBu)
plt.contour(xx, yy, Z, levels=[0], linewidths=2, colors='darkred')
plt.scatter(X_train[:, 0], X_train[:, 1], s=10, color='black')
plt.xlim((-5, 5))
plt.ylim((-5, 5))
plt.title("OneClassSVM - Decision Boundary")
plt.show()

https://img.papergate.top:5000/i/2025/05/68286770eb35d.webp

2.2 填充异常值

将异常值填充为中位数的方法如下:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
# 3 sigma 异常值填充为中位数
def replace_outliers_with_median(column):
    # 计算均值和标准差
    mean = column.mean()
    std = column.std()
    # 计算下限和上限
    lower_limit = mean - 3 * std
    upper_limit = mean + 3 * std
    # 替换离群点为中位数
    return column.apply(lambda x: x if (lower_limit <= x <= upper_limit) else column.median())

# 使用 apply 方法处理每一列
df_cleaned = df.apply(replace_outliers_with_median)

第 3 节 重复值

展示并删除重复值的方法如下:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
import pandas as pd
data = pd.read_csv('example.csv')

# 展示重复数据
mask = data.duplicated(subset=['ID','Salary','Age'])
data[mask]

# 删除重复数据
new_data = data.drop_duplicates(subset=['ID','Salary','Age'],keep = 'first')
new_data