机器学习中理解数据的关键:从EDA到数据清洗的完整流程

机器学习中理解数据的关键:从EDA到数据清洗的完整流程 拿到数据集后直接训练模型这是不少机器学习初学者最容易踩的坑。训练完成后一看指标不理想开始怀疑算法选错、参数没调好折腾半天才发现问题往往出在最开始就被忽视的环节——数据本身。特征里大量缺失值没有处理异常值把模型带偏类别特征没有编码数值特征之间高度共线。这些问题几乎都源于对数据理解不足。在 100 天机器学习计划的第 19 天核心主题就是“理解你的数据”。我们会按一条完整的探索性数据分析EDA流程讲解如何用 Python 工具快速掌握数据集的整体结构、分布规律、缺失情况、相关性和异常值搞清楚数据到底长什么样再决定下一步如何清洗和建模。适合刚入门机器学习的读者也适合想把数据理解环节做扎实的开发同学。1. 理解你的数据机器学习项目的第一步1.1 为什么数据理解比建模更值得重视很多人以为机器学习的核心是算法和模型于是把大量时间花在调参、选模型上。但在真实项目中一个模型能不能用往往在数据阶段就已经决定了。垃圾进、垃圾出如果输入的数据本身有问题后续模型再先进也无济于事。数据理解的作用主要体现在几个方面识别数据质量问题比如缺失、重复、异常值、错误编码。判断特征类型确定哪些是数值特征、哪些是类别特征方便后续做编码和缩放。发现分布规律比如目标变量是否均衡、连续特征是否偏态。找出特征之间的关系避免引入高度相关的冗余特征。为特征工程提供依据比如是否需要分箱、取对数、构造交叉特征。所以“理解你的数据”不是走过场而是为了给建模打下一个可靠的基础。1.2 EDA 是什么包含哪些内容理解数据的过程在机器学习里通常被称为探索性数据分析Exploratory Data Analysis简称 EDA。EDA 的核心目标不是验证某个假设而是用尽可能直观的方式发现数据中的规律、异常和问题。一份完整的 EDA 通常包括以下内容数据概览行数、列数、字段类型、样例数据。描述性统计均值、中位数、标准差、最大值、最小值、分位数。缺失值分析哪些字段有缺失缺失比例是多少。重复值检测是否存在完全重复的行。目标变量分析分类问题看类别分布回归问题看数值分布。特征分布分析直方图、箱线图、偏度与峰度。相关性分析数值特征之间的线性相关程度。异常值检测通过 IQR、Z-Score 等方法识别离群点。这些内容不需要一次全部做完但每拿到一个新数据集都应该尽快跑一遍形成对数据的基本判断。1.3 本文使用的工具链本文使用 Python 生态中非常成熟的数据分析工具。具体包括Pandas用于数据加载、筛选、聚合、缺失值统计等结构化操作。NumPy提供数值计算支持尤其是方差、标准差、数组运算。Matplotlib基础绘图库用于绘制直方图、折线图、散点图。Seaborn基于 Matplotlib 的高级绘图库适合画统计图表比如热力图、箱线图、计数图。如果你是第一次接触这些工具不用担心。本文将结合 Titanic泰坦尼克号数据集把每一步代码和输出都展示出来。你只需要按照文章顺序运行代码就能看到完整的分析结果。2. 环境准备与数据集说明2.1 Python 环境安装与激活在开始之前建议先创建一个独立的 Python 虚拟环境避免不同项目之间的依赖冲突。以 Miniconda 或 Anaconda 为例打开终端执行以下命令。conda create -n ml100 python3.10 -y conda activate ml100如果你没有安装 Anaconda可以安装 Python 3.10 以上版本然后直接使用 venv 创建虚拟环境。创建好环境后安装本文所需的库。pip install pandas numpy matplotlib seaborn scikit-learn如果安装速度较慢可以临时使用国内镜像源例如清华源。pip install pandas numpy matplotlib seaborn scikit-learn -i https://pypi.tuna.tsinghua.edu.cn/simple2.2 导入依赖库在 Jupyter Notebook 或 Python 脚本中首先导入需要使用的库。为了让图表正常显示中文需要额外配置 Matplotlib 的字体参数。import pandas as pd import numpy as np import matplotlib.pyplot as plt import seaborn as sns # 设置中文显示 plt.rcParams[font.sans-serif] [SimHei] # Windows 系统使用黑体 plt.rcParams[axes.unicode_minus] False # 解决坐标轴负号显示问题 # 在 Jupyter 中显示图表 %matplotlib inline如果你在 Linux 服务器上运行可能没有 SimHei 字体。这时可以使用系统自带的中文字体或者在代码中改为plt.rcParams[font.sans-serif] [WenQuanYi Zen Hei, Noto Sans CJK SC]还有一种更简单的办法不显示中文把图表的标题、标签都写成英文。对于数据分析脚本来说这样反而能避免字体问题。2.3 示例数据集TitanicTitanic 数据集是机器学习入门最经典的数据集之一。它记录了泰坦尼克号上乘客的船舱等级、年龄、性别、票价、是否生存等信息。我们通过分析这份数据可以回答很多有趣的问题比如“女性乘客的存活率是否更高”“头等舱乘客是否更容易获救”。为了方便运行本文直接使用 Seaborn 内置的 Titanic 数据集。它的列名和 Kaggle 上的原始版本略有差异但信息量基本一致。df sns.load_dataset(titanic) print(df.head())如果 Seaborn 提示网络问题无法下载内置数据集也可以从 GitHub 加载 Kaggle 版本的 CSV 文件。url https://raw.githubusercontent.com/datasciencedojo/datasets/master/titanic.csv df pd.read_csv(url)两种方式选一种即可。下面所有代码都围绕df这个 DataFrame 展开。运行print(df.head())后你会看到一张表格。每一行代表一位乘客每一列代表一个特征。常见列的含义如下survived是否生存0 表示死亡1 表示生存。pclass船舱等级1 等舱、2 等舱、3 等舱。sex性别。age年龄。sibsp同行的兄弟姐妹或配偶数量。parch同行的父母或子女数量。fare票价。embarked登船港口。class船舱等级的文字描述。who乘客身份man、woman、child。deck甲板编号。embark_town登船港口名称。alive是否生存的文字描述。alone是否独自一人。有了这些基础信息就可以开始正式的数据理解了。3. 数据加载与概览3.1 读取 CSV 文件Pandas 读取 CSV 文件的接口是pd.read_csv()。它支持本地路径也支持 URL。读取完成后数据会保存在一个 DataFrame 对象中。df sns.load_dataset(titanic)如果使用 Kaggle 原始 CSV读取方式如下df pd.read_csv(titanic.csv)这里的df是 DataFrame你可以把它理解成一张 Excel 表格有行有列。Pandas 为这种表格结构提供了非常丰富的操作方法。3.2 查看数据结构拿到 DataFrame 之后第一步是看它的整体规模。使用shape属性可以查看行数和列数。print(数据集形状:, df.shape) print(行数:, df.shape[0]) print(列数:, df.shape[1])Titanic 数据集在 Seaborn 内置版本中通常有 891 行、15 列。接下来查看每一列的名称和数据类型。print(列名列表:) print(df.columns.tolist())查看所有列的数据类型print(数据类型:) print(df.dtypes)通过这些输出你可以快速知道哪些列是数值类型哪些是对象类型。例如 age 是 float64fare 是 float64sex 是 objectembarked 是 object。3.3 快速预览数据可以用head()查看前几行数据tail()查看最后几行sample()随机抽取几行。print(前 5 行数据:) print(df.head()) print(\n最后 5 行数据:) print(df.tail()) print(\n随机抽取 5 行数据:) print(df.sample(5, random_state42))sample()中的random_state参数用于固定随机种子。加上它之后每次抽样的结果都一样方便复现分析结果。预览数据能让你直观感受每一列的内容。比如观察 age 列你可能已经发现有些位置显示NaN这就是缺失值的开始。4. 描述性统计与数据类型分析4.1 info() 查看数据概况info()是 Pandas 中非常实用的方法。它会一次性输出 DataFrame 的行数、列名、非空值数量、数据类型和内存占用。df.info()输出结果类似class pandas.core.frame.DataFrame RangeIndex: 891 entries, 0 to 890 Data columns (total 15 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 survived 891 non-null int64 1 pclass 891 non-null int64 2 sex 891 non-null object 3 age 714 non-null float64 4 sibsp 891 non-null int64 5 parch 891 non-null int64 6 fare 891 non-null float64 7 embarked 889 non-null object 8 class 891 non-null category ...从info()的输出中我们可以立刻看到age 列只有 714 个非空值说明该列存在缺失。embarked 列只有 889 个非空值也存在少量缺失。deck 列缺失比较严重如果继续做建模通常需要特殊处理或删除。info()是理解数据质量的第一步也是后续缺失值分析的入口。4.2 describe() 查看统计摘要describe()方法可以输出数值列的统计摘要包括计数、均值、标准差、最小值、四分之一分位数、中位数、四分之三分位数和最大值。print(df.describe())输出结果中每一行是一个统计指标每一列是一个数值特征。以 age 列为例你会看到count非空样本数。注意这里不是 891而是 714因为 age 有缺失值。mean年龄均值。std标准差。min最小年龄。25%四分之一分位数。50%中位数。75%四分之三分位数。max最大年龄。如果你还想对类别特征做类似的统计可以加上includeO参数这里的 O 指的是 object 类型列。print(df.describe(includeO))这样会输出类别列的计数、唯一值数量、出现次数最多的取值等。比如 sex 列有两个唯一值embarked 列有三个唯一值。4.3 数值特征与类别特征在机器学习中数值特征和类别特征的处理方式完全不同。数值特征如 age、fare可以进行加减乘除适合计算均值、标准差后续可以做标准化或归一化。类别特征如 sex、embarked本身是离散的取值需要转换成数值编码才能输入模型。我们可以用select_dtypes()将数值列和类别列分开。numeric_cols df.select_dtypes(include[np.number]).columns.tolist() print(数值特征:, numeric_cols) category_cols df.select_dtypes(include[object, category]).columns.tolist() print(类别特征:, category_cols)这一步很重要。后续做相关性分析时我们只会选择数值列做编码时我们只会处理类别列。先把特征类型搞清楚能避免很多不必要的错误。5. 缺失值与重复值分析5.1 统计缺失值缺失值是数据理解中最常见的问题之一。统计缺失值可以用isnull()结合sum()。missing_count df.isnull().sum() print(每列缺失值数量:) print(missing_count) missing_ratio df.isnull().mean() * 100 print(\n每列缺失值比例:) print(missing_ratio)isnull()会把每个单元格标记为 True 或 FalseTrue 表示空值。sum()统计每列中 True 的个数mean()则计算缺失比例。将缺失数量和缺失比例整理成一张表会更清晰。missing_info pd.DataFrame({ 缺失数量: missing_count, 缺失比例: missing_ratio }) print(missing_info[missing_info[缺失数量] 0])这类报告可以直接复制到项目文档中作为数据质量分析的一部分。5.2 缺失值可视化除了数值统计我们还可以用热力图直观查看缺失值的位置。Seaborn 的heatmap()配合isnull()可以做到这一点。plt.figure(figsize(12, 6)) sns.heatmap(df.isnull(), cbarFalse, cmapviridis) plt.title(数据缺失值热力图) plt.show()图中深色代表有数据的位置亮色代表缺失的位置。通过热力图你可以快速看到哪些列缺失严重以及缺失是否集中在某些行上。对于 deck 这种缺失比例很高的列最简单的处理方式是删除整列。对于 age 这种缺失比例适中的列可以考虑用中位数或均值填充。5.3 重复值检测重复值是指两行数据完全一致。在真实业务数据中重复值可能是因为数据采集重叠或导入错误导致的。检测重复值使用duplicated()。duplicated_count df.duplicated().sum() print(重复行数量:, duplicated_count)如果重复行不多可以选择直接删除。删除使用drop_duplicates()。df_clean df.drop_duplicates() print(去重后的行数:, df_clean.shape[0])需要注意的是在 Titanic 这种按乘客记录的数据中完全重复的行通常不是因为同一位乘客被记录两次而可能是数据合并时的错误。不管原因如何重复值都会影响模型训练时对样本权重的判断应该及时处理。5.4 缺失值处理策略缺失值的处理方式取决于缺失比例和业务含义没有统一答案。常见的策略如下删除缺失列当某列缺失比例过高比如超过 50%且业务价值较低时直接删除。删除缺失行当缺失行数很少且其他特征完整度较高时可以删除这些行。填充缺失值数值特征常用均值、中位数或众数填充类别特征常用众数填充。模型预测填充用其他特征训练一个简单模型预测缺失值。标记缺失新增一列记录该行是否缺失保留缺失信息。在 Titanic 例子中age 的缺失值通常用中位数填充因为年龄可能存在偏态分布中位数比均值更稳健。median_age df[age].median() df[age_filled] df[age].fillna(median_age) print(df[age_filled].describe())这里我们把填充后的结果保存在新列age_filled中避免破坏原始数据。这是一个非常好的习惯——处理数据时尽量保留原始列新增处理后的列方便对比和回溯。6. 目标变量与特征分布分析6.1 目标变量分布在监督学习中目标变量是我们的预测对象。Titanic 数据集的预测目标是 survived它是一个二分类变量。分析目标变量的分布可以判断类别是否均衡。sns.countplot(xsurvived, datadf) plt.title(Survived 分布) plt.show()输出结果中0 和 1 两个柱子的高度代表死亡和生存的人数。如果两者比例接近 1:1说明数据相对均衡如果一方明显偏多说明存在类别不平衡问题后续可能需要使用过采样、欠采样或调整分类阈值等策略。也可以用value_counts()查看具体数量。print(df[survived].value_counts())如果使用normalizeTrue参数可以直接看到比例。print(df[survived].value_counts(normalizeTrue))在 Titanic 数据集中死亡人数略多于生存人数但还不至于严重失衡因此即使不做特殊处理直接训练逻辑回归等模型也是可行的。6.2 数值特征分布数值特征的分布情况可以通过直方图观察。直方图会把数据按区间分组然后统计每个区间内样本的数量。df[[age, fare]].hist(bins30, figsize(12, 4)) plt.show()从 age 的直方图可以看出旅客年龄主要集中在 20 到 40 岁之间。而 fare 的分布则呈现明显的右偏形态少数乘客的票价特别高大多数乘客的票价集中在较低区间。这种长尾分布对很多机器学习模型不太友好。后续可以考虑对 fare 取对数压缩数值范围减少极端值的影响。箱线图也是观察分布的重要工具。它可以展示数据的最小值、下四分位数、中位数、上四分位数和最大值并且能直接标记异常值。plt.figure(figsize(8, 4)) sns.boxplot(yage, datadf) plt.title(Age 箱线图) plt.show()通过箱线图你可以看到 age 的分布范围以及位于上下边界之外的点这些点往往就是潜在的异常值。6.3 类别特征分布类别特征可以通过计数图查看不同取值的样本数量。我们选择几个有意义的列一次性绘制出来。fig, axes plt.subplots(1, 3, figsize(16, 4)) sns.countplot(xsex, datadf, axaxes[0]) axes[0].set_title(Sex 分布) sns.countplot(xpclass, datadf, axaxes[1]) axes[1].set_title(Pclass 分布) sns.countplot(xembark_town, datadf, axaxes[2]) axes[2].set_title(Embark Town 分布) plt.tight_layout() plt.show()从这些图中可以看出男性乘客多于女性乘客三等舱乘客数量最多登船港口以 Southampton 为主。这些信息虽然简单但可以帮助你理解数据来源和样本构成。如果发现某个类别特征的类别数量过多比如超过几十个后续建模时就要考虑是否做频次编码、目标编码或者是否直接丢弃该列。比如 name 和 ticket 这类高基数列通常不会直接作为模型特征。7. 相关性分析与特征关系探索7.1 数值特征相关性矩阵相关性描述的是两个变量之间的线性相关程度取值在 -1 到 1 之间。大于 0 表示正相关小于 0 表示负相关0 表示没有线性相关。在建模前我们通常希望特征之间不要存在过高的相关性否则会产生多重共线性影响模型稳定性。使用 Pandas 的corr()方法可以计算数值特征之间的相关系数矩阵。numeric_df df[[survived, pclass, age, sibsp, parch, fare]] corr numeric_df.corr() print(corr)输出结果是一张矩阵表。每个单元格的值表示两个特征之间的皮尔逊相关系数。7.2 热力图可视化相关系数矩阵直接看数字可能不够直观用热力图可以更快发现规律。plt.figure(figsize(10, 8)) sns.heatmap(corr, annotTrue, cmapcoolwarm, fmt.2f, linewidths0.5) plt.title(数值特征相关性矩阵) plt.show()annotTrue表示在热力图上显示具体数值cmapcoolwarm设置颜色映射红色代表正相关蓝色代表负相关。从 Titanic 的热力图中我们可以发现pclass 与 survived 之间存在负相关说明船舱等级越低生存率越低。fare 与 survived 之间存在正相关说明票价越高生存率越高。sibsp 与 parch 之间的相关性较低说明这两个家庭相关特征相对独立。这些信息对后续特征筛选非常有帮助。如果两个特征的相关系数超过 0.8通常建议只保留其中一个。7.3 特征与目标的关系相关性矩阵只能反映数值特征之间的线性关系。我们还可以直接从业务角度分析特征和目标变量之间的关系。例如分析不同船舱等级的生存率。sns.barplot(xpclass, ysurvived, datadf) plt.title(不同船舱等级的生存率) plt.show()柱状图显示一等舱乘客的生存率明显高于三等舱乘客。再看性别对生存率的影响。sns.barplot(xsex, ysurvived, datadf) plt.title(不同性别的生存率) plt.show()女性乘客的生存率远远高于男性乘客。这符合泰坦尼克号“妇女和儿童优先”的疏散原则。这些分析表面看起来很简单但正是建模前最有力的依据。你可以带着这些发现去构建特征比如把“是否女性”“是否一等舱”等信息转化为更有预测力的特征。8. 异常值检测与处理8.1 什么是异常值异常值是指与其他样本明显不同的数据点。在 Titanic 数据集中fare 列可能存在极高票价它们虽然真实但在模型中可能产生较大影响让模型过于关注这些少数样本。处理异常值之前需要先想清楚一个问题这是一个真实业务中的特殊值还是数据录入错误如果是真实值可能需要特殊编码或进行稳健的变换如果是错误值则应该修正或删除。8.2 IQR 方法识别异常值IQRInterquartile Range四分位距是常用的异常值识别方法。它的原理是先计算数据的下四分位数 Q1 和上四分位数 Q3IQR Q3 - Q1。认为小于 Q1 - 1.5 * IQR 或大于 Q3 1.5 * IQR 的点为异常值。下面封装一个函数方便后续对多个特征重复使用。def detect_outliers_iqr(data, column): Q1 data[column].quantile(0.25) Q3 data[column].quantile(0.75) IQR Q3 - Q1 lower_bound Q1 - 1.5 * IQR upper_bound Q3 1.5 * IQR outliers data[(data[column] lower_bound) | (data[column] upper_bound)] return outliers, lower_bound, upper_bound outliers_age, lower_age, upper_age detect_outliers_iqr(df, age) print(fAge 异常值数量: {len(outliers_age)}) print(fAge 正常范围: [{lower_age:.2f}, {upper_age:.2f}])得到的下边界可能为负数。对于年龄来说负数没有实际意义所以还要结合业务判断。IQR 方法的优点是简单、不依赖数据分布假设缺点是只考虑了分位数无法充分反映数据内部的复杂结构。8.3 Z-Score 方法识别异常值Z-Score 方法通过计算每个样本距离均值有多少个标准差来判断异常。通常认为 Z-Score 的绝对值大于 3 的点是异常值。from scipy import stats z_scores np.abs(stats.zscore(df[fare])) outliers_z df[fare][z_scores 3] print(fFare 异常值数量: {len(outliers_z)}) print(outliers_z)该结果可能显示 fare 中存在多个高票价样本比如 512 美元、520 美元等。这些极端值在现实中可能存在但在模型中会对损失函数产生较大影响。需要对它们做处理时可以考虑保留但取对数变换。用盖帽法winsorize把超过 99% 分位数的值压缩到 99% 分位数。删除明显录入错误的数据点。8.4 异常值处理策略异常值处理并没有绝对标准。不同的模型对异常值的敏感度不同线性回归、逻辑回归、KNN 等模型对异常值敏感。决策树、随机森林、XGBoost 等树模型相对稳健。如果后续要使用对异常值敏感的模型可以考虑删除和修正异常值。如果使用树模型并且异常值本身是真实业务记录可以保留让模型自己学习规律。更推荐的做法是在训练集上做异常值处理并且把处理逻辑封装成函数在验证集和测试集上使用同一套处理规则避免数据泄露。9. 常见问题与排查思路在实际操作中新手经常会遇到一些固定报错和结果异常。下面整理了一份常见问题排查表。问题现象常见原因解决思路df.head()输出正常但df.isnull().sum()结果全为 0缺失值被存储为空字符串或特殊字符使用df.replace(, np.nan)将空字符串替换为 NaNpd.read_csv()报编码错误文件编码与默认 UTF-8 不一致指定编码参数如encodinggbk或encodingutf-8-sig图表中文显示为方块系统中没有对应中文字体配置plt.rcParams[font.sans-serif]或改用英文图表标签df.describe()没有展示类别列describe 默认只统计数值列添加参数includeO或includeallage 填充后均值出现偏移用均值填充了大量缺失值导致中心偏移改用中位数填充或在填充后检查均值和方差变化两个特征相关系数很高存在共线或重复表达的信息删除其中一个或使用 PCA 降维模型效果与 EDA 结论矛盾EDA 只在训练集上做了分析没有考虑验证集将 EDA 流程封装为函数统一应用到所有数据集这些问题的共同点是没有先确认数据结构就直接进入建模或可视化导致后续方向跑偏。建议在写任何机器学习代码之前先把info()、describe()、isnull().sum()三个方法固定跑一遍。10. 最佳实践与工程建议10.1 数据理解的流程规范在团队协作或正式项目中数据理解不能只写在 Notebook 里还应该形成可复用的报告和脚本。推荐按照以下顺序组织流程读取数据后立即生成一份数据字典记录每个字段的含义、类型和业务意义。将缺失值统计、重复值统计、数值列统计摘要输出为 CSV 文件方便共享。对重要特征绘制分布图、箱线图和相关性热力图并把图片保存到指定目录。把 EDA 结论用 Markdown 记录下来包括发现的问题、做出的处理决策和处理理由。这样做的好处是当团队成员或未来的你重新打开项目时不需要重新从零探索数据直接查看报告就能快速进入状态。10.2 数据质量与安全边界理解数据的过程中经常会涉及数据备份、数据清洗、数据脱敏等操作。这里需要特别注意几个原则不要直接修改原始数据文件。所有操作尽量在 DataFrame 的副本上进行或者保留原始 CSV 的备份。对数据进行清洗前先做备份。如果使用了drop_duplicates()、dropna()等操作确认无误后再覆盖保存。如果数据包含用户身份证号、手机号等敏感信息在分析和输出报告时需要进行脱敏处理。在生产环境中删除数据和覆盖文件都需要额外谨慎最好有权限审批和操作审计。这些原则不仅适用于机器学习的探索阶段也是数据工程和数据治理的基本要求。尤其当你处理的是公司内部数据时合规性比模型效果更重要。10.3 效率提升技巧数据理解阶段虽然偏重探索但也可以用工程化手段提升效率。一是把常用的 EDA 操作封装成函数。比如前面写的异常值检测函数就可以放在一个独立的eda_utils.py文件中多个 Notebook 共用。二是使用pandas-profiling现在叫 ydata-profiling一键生成 EDA 报告。示例如下pip install ydata-profilingfrom ydata_profiling import ProfileReport profile ProfileReport(df, titleTitanic EDA Report) profile.to_file(titanic_eda_report.html)这样会生成一个交互式 HTML 报告包含数据概览、缺失值、相关性、分布图等模块。虽然自动化报告不能完全替代手动分析但可以帮你节省大量时间快速定位需要深入研究的特征。三是记录每一次数据清洗操作的参数和依据。很多数据问题在分析时看起来是独立的但后续建模或上线时会被重新放大。如果没有记录排错会非常困难。11. 总结与后续学习今天这篇文章完成了机器学习计划中“理解你的数据”这一关键环节。从环境准备、数据加载、结构概览、描述性统计到缺失值分析、分布分析、相关性分析和异常值检测我们完整走了一遍探索性数据分析的流程。使用的工具主要是 Pandas、Matplotlib 和 Seaborn示例数据是经典的 Titanic 数据集。在实际项目中花在数据理解上的时间从来不会白费。把数据结构和质量搞清楚后续的特征工程、模型训练甚至调参都会顺利很多。建议你用自己的数据集把上面的代码完整跑一遍观察每个输出尝试修改填充阈值动手处理缺失和异常然后记录分析结论。理解数据的能力是在一次次实操中积累出来的。下一阶段可以继续学习数据清洗、特征工程、数据编码和特征缩放等内容。你已经知道了数据里有什么问题接下来就是想办法解决这些问题为模型训练准备出干净、可靠的数据。如果本文对你有帮助可以先收藏备用方便以后做数据分析时快速查阅。