数据分析相关面试题汇总

目录

Pandas

Pandas作用?

如何读取 csv、excel?如何指定编码、索引?

拿到一个 DataFrame,你第一步会看什么?

如何按条件筛选行?如何选取列?

如何查看重复行、删除重复?

如何把字符串转时间?转整数?

按专业分组,统计分数的均值、最大值、人数

多表合并用什么?和 SQL 的 JOIN 对应什么?

用 Pandas 做 Excel 透视表

根据分数新增等级列(优秀 / 良好 / 及格)

如何提取年、月、日?如何按月求和?

如何识别并剔除异常值?

行转列、列转行(melt /pivot)

apply/map/applymap 区别

为什么会出现SettingWithCopyWarning这个警告?怎么解决?

如何实现 SQL 的 group by having?

导出 Excel / CSV

NumPy

NumPy作用?

NumPy 数组(ndarray)和 Python 列表 list 的区别?

创建数组的常用方式有哪些?

查看数组属性

数组索引与切片

什么是广播(broadcasting)?为什么重要?

数据归一化 / 标准化

用 NumPy 实现 3σ 异常值筛选

数组形状修改

np.where 用法

空值(NaN)相关问题

为什么要设置 dtype?

随机数生成

Matplotlib + Seaborn

Matplotlib 是什么?Seaborn 是什么?关系?

数据分析常用哪些图表?分别用于什么场景?

Matplotlib 两张图:figure /axes 是什么?

Matplotlib-绘制最简单的折线图

Matplotlib-画柱状图

Matplotlib-画直方图(看分布)

Matplotlib-画散点图(看相关性)

Matplotlib-画子图(多图并排)

Matplotlib-如何保存图片?

Matplotlib-中文乱码怎么解决?

Seaborn-绘制柱状图(带误差棒 / 分组)

Seaborn-箱线图(识别异常值)

Matplotlib vs Seaborn 区别?

箱线图、直方图、散点图分别用来干什么?

什么时候用热力图?

如何让图表更专业、更适合汇报?

做数据分析时可视化流程是什么?

SciPy

SciPy 是什么,在数据分析里用来干什么?

什么是 p 值?

常见统计检验怎么选?

导入scipy

正态性检验,如何检验一组数据是否符合正态分布?

独立样本 t 检验

配对样本 t 检验

单样本 t 检验

方差分析 ANOVA(多组比较)

卡方检验(分类变量关联性)

皮尔逊相关系数(线性相关)

斯皮尔曼等级相关(非参数,不要求正态)

秩和检验(非参数替代 t 检验)

t 检验和方差分析的区别?

什么时候用非参数检验?

相关系数 ≠ 因果关系?

p 值很小代表什么?

数据分析完整统计检验流程?

Statsmodels

Statsmodels 是什么?和 Sklearn 有什么区别?

线性回归用来干什么?

最小二乘线性回归代码

如何看回归结果 summary?

逻辑回归(分类问题)

线性回归有哪些基本假设?

多重共线性怎么判断、怎么处理?

异常值 / 强影响点怎么检测?

Statsmodels 时间序列能干什么?

ADF 平稳性检验

什么时候用 Statsmodels,什么时候用 Sklearn?

回归系数(coef)代表什么?

p < 0.05 代表什么?

R² 是什么意思?太低怎么办?

用 Statsmodels 做过什么业务分析?

Scikit-learn(sklearn)

Scikit-learn 是什么,在数据分析里用来干什么?

机器学习四大类

模型构建标准流程

分类特征编码:OneHot、LabelEncoder

数值特征归一化 / 标准化

缺失值处理 SimpleImputer

数据集划分

线性回归(预测连续值,如分数)

逻辑回归(二分类,如是否升学、是否就业)

决策树 / 随机森林(最常用、最强业务解释性)

K-Means 聚类(用户分层、生源分层)

PCA 降维

分类模型指标有哪些?

回归模型指标有哪些?

聚类评估有哪些?

过拟合是什么?怎么解决?

欠拟合是什么?怎么解决?

什么是交叉验证?

为什么要用交叉验证?

网格搜索 GridSearchCV

特征重要性怎么看?

分类模型评估指标

标准化和归一化区别?

类别特征用什么编码?

用 sklearn 做过什么实际分析?

类别不平衡(比如很少人违约、很少人辍学)怎么办?

逻辑回归 / 决策树 / 随机森林怎么选?

K-Means

K-Means 是什么?

K-Means 的执行过程?

K 怎么确定?

K-Means 优缺点?

K-Means 为什么要标准化 / 归一化?

K-Means 遇到异常值怎么办?

用 K-Means 做过什么?


Pandas

Pandas作用?

主要用 Pandas 做数据读取、清洗、分组聚合、多表关联和特征工程,是日常最核心的库。

如何读取 csv、excel?如何指定编码、索引?

注释:编码常用 utf-8 / gbk,中文乱码常用 encoding='gbk' 或 encoding='gb2312'。

读取 CSV

import pandas as pd

df = pd.read_csv("data.csv", encoding="utf-8")

读取 Excel

import pandas as pd

df = pd.read_excel("data.xlsx", sheet_name="Sheet1")

读取时指定索引列

import pandas as pd

df = pd.read_csv("data.csv", index_col="id")

拿到一个 DataFrame,你第一步会看什么?

先看结构、类型、空值、重复、异常值。

前5行,看数据结构

df.head()

字段类型、是否有空值、占用内存

df.info()

数值列统计(均值、分位数、最大最小)

df.describe()

行数, 列数

df.shape

每列空值数量(最重要)

df.isnull().sum()

如何按条件筛选行?如何选取列?

1. 条件筛选(最常用)

df[df["age"] > 18]

2. 多条件 & 且 | 或

& | 两边必须加括号,否则报错。

df[(df["score"] >= 60) & (df["province"] == "河南")]

3. loc:按标签(行名+列名)

df.loc[df["score"] > 90, ["name", "score"]]

4. iloc:按位置(第0行到第5行,前2列)

df.iloc[0:5, 0:2]

如何查看、处理缺失值?

  • 数值列:均值 / 中位数 / 分位数
  • 分类列:众数
  • 空值很少:直接删
  • 空值有规律:前向填充 ffill / 后向填充 bfill

查看空值

df.isnull().sum()

删除含空值的行

df = df.dropna()

填充 0

df = df.fillna(0)

连续数值用均值填充

df["score"] = df["score"].fillna(df["score"].mean())

分类字段用众数填充

df["province"] = df["province"].fillna(df["province"].mode()[0])

如何查看重复行、删除重复?

查看重复行数

df.duplicated().sum()

删除全部重复行

df = df.drop_duplicates()

按某一列去重(如按id去重,保留第一条)

df = df.drop_duplicates(subset=["id"], keep="first")

如何把字符串转时间?转整数?

转时间类型(非常常用)

df["date"] = pd.to_datetime(df["date"])

转整型

df["age"] = df["age"].astype(int)

查看类型

df.dtypes

按专业分组,统计分数的均值、最大值、人数

单指标

df.groupby("major")["score"].mean()

多分组 + 多聚合函数

reset_index() 非常常用,否则分组字段是索引,不方便后续处理。

df.groupby(["college", "major"])["score"].agg(
    mean_score="mean",
    max_score="max",
    count="count"
).reset_index()  # 把索引变回列

多表合并用什么?和 SQL 的 JOIN 对应什么?

  • 按共同字段关联 → merge
  • 上下堆叠数据 → concat
  • 按行号 / 索引合并 → join

1. merge:按列关联(对应 SQL JOIN)

df3 = pd.merge(df1, df2, on="id", how="left")  # left join

2. concat:上下拼接(追加数据)

 df_all = pd.concat([df1, df2], axis=0)

3. join:按索引合并

 df1.join(df2)

用 Pandas 做 Excel 透视表

pd.pivot_table(
    data=df,
    index="college",      # 行
    columns="major",     # 列
    values="score",      # 值
    aggfunc="mean"       # 聚合方式
)

根据分数新增等级列(优秀 / 良好 / 及格)

方法1:np.where(简单二分类)

import numpy as np

df["is_pass"] = np.where(df["score"] >= 60, 1, 0)

方法2:apply(多分类)

df["level"] = df["score"].apply(lambda x:
    "优秀" if x >= 90 else
    "良好" if x >= 70 else
    "及格" if x >= 60 else "不及格"
)

方法3:pd.cut(分桶,最规范)

df["level"] = pd.cut(
    df["score"],
    bins=[0, 60, 70, 90, 100],
    labels=["不及格", "及格", "良好", "优秀"]
)

如何提取年、月、日?如何按月求和?

df["date"] = pd.to_datetime(df["date"])

df["year"] = df["date"].dt.year
df["month"] = df["date"].dt.month
df["day"] = df["date"].dt.day

按月重采样统计

df.resample("M", on="date")["amount"].sum()

如何识别并剔除异常值?

超出 ±3σ 视为异常,是数据分析标准做法。

mean = df["score"].mean()
std = df["score"].std()

upper = mean + 3 * std
lower = mean - 3 * std

df = df[(df["score"] >= lower) & (df["score"] <= upper)]

行转列、列转行(melt /pivot)

宽表 → 长表

df_long = df.melt(id_vars="id", var_name="type", value_name="value")

长表 → 宽表

df_wide = df_long.pivot(index="id", columns="type", values="value")

apply/map/applymap 区别

  • map:只用于 Series,元素映射
  • apply:可用于 Series / DataFrame,支持复杂函数
  • applymap:对 DataFrame 每个单元格操作(现已逐渐被 map 替代)

为什么会出现SettingWithCopyWarning这个警告?怎么解决?

对切片 DataFrame 直接修改,Pandas 不确定你改原表还是副本。

解决:加上 .copy() 即可。

df = df[df["score"]>60].copy()

如何实现 SQL 的 group by having?

例子:筛选平均分 > 60 的专业

df.groupby("major").filter(lambda x: x["score"].mean() > 60)

导出 Excel / CSV

df.to_csv("out.csv", index=False, encoding="utf-8-sig")
df.to_excel("out.xlsx", index=False, sheet_name="结果")

NumPy

NumPy作用?

用 NumPy 做数值计算、异常值判断、数据归一化,配合 Pandas 做向量化操作。

NumPy 数组(ndarray)和 Python 列表 list 的区别?

  1. 数组元素类型必须统一,列表可以混放任意类型。
  2. 数组支持矢量化运算,不用循环,速度极快。
  3. 数组支持多维结构(矩阵),更适合数值计算。
  4. 数组占用内存更小,底层连续存储。
  5. 提供大量数学 / 统计函数,适合数据分析、建模。

创建数组的常用方式有哪些?

import numpy as np

从列表创建

arr = np.array([1,2,3,4])

全0/全1数组

arr = np.zeros((3,4))
arr = np.ones((2,2))

固定值

arr = np.full((2,3), 5)

等差序列

arr = np.arange(0, 10, 2)    # 0,2,4,6,8
arr = np.linspace(0,10,5)    # 均分5个点

单位矩阵

arr = np.eye(3)

查看数组属性

arr = np.array([[1,2],[3,4]])

形状 (行数,列数)

arr.shape

维度数

arr.ndim

总元素个数

arr.size

数据类型

arr.dtype

转置

arr.T

数组索引与切片

arr = np.array([[1,2,3],
                [4,5,6],
                [7,8,9]])

取某行

arr[0]

取某行某列

arr[0, 1]

切片:所有行,前2列

arr[:, :2]

布尔索引 arr[arr > 5]

arr[arr > 5]

什么是广播(broadcasting)?为什么重要?

  • 不同形状的数组在运算时,NumPy 会自动扩展维度对齐,不需要手动循环。
  • 优点:代码简洁、速度极快、内存高效。
  • 是 Pandas、Matplotlib、机器学习库高效的基础。

示例:

a = np.array([[1,2],[3,4]])
b = np.array([10, 20])
# b 自动广播成 [[10,20],[10,20]]
print(a + b)

常用数学 / 统计函数

arr = np.array([1,2,3,4,5])

求和

np.sum(arr)

均值

np.mean(arr)

标准差

np.std(arr)

方差

np.var(arr)

最大值

np.max(arr)

最小值

np.min(arr)

中位数

np.median(arr)

最大值下标

np.argmax(arr)

最小值下标

np.argmin(arr)

累计求和

np.cumsum(arr)

数据归一化 / 标准化

题目:把数组缩放到 [0,1] 之间

arr = np.array([1,2,3,4,5])
arr_min = arr.min()
arr_max = arr.max()

# 最小-最大归一化
arr_norm = (arr - arr_min) / (arr_max - arr_min)

题目:Z-score 标准化(均值 0,方差 1)

arr_std = (arr - np.mean(arr)) / np.std(arr)

用 NumPy 实现 3σ 异常值筛选

arr = np.array([1,2,3,4,100])

mean = arr.mean()
std = arr.std()

upper = mean + 3 * std
lower = mean - 3 * std

# 保留正常范围内数据
arr_clean = arr[(arr >= lower) & (arr <= upper)]

数组形状修改

arr = np.arange(12)

改为3行4列

arr.reshape(3,4)

展平成一维

arr.flatten()

转置

arr.reshape(3,4).T

拼接与分割

a = np.array([[1,2],[3,4]])
b = np.array([[5,6],[7,8]])

垂直拼接(上下)

np.vstack([a, b])

水平拼接(左右)

np.hstack([a, b])

均等分割

np.vsplit(a, 2)
np.hsplit(a, 2)

np.where 用法

arr = np.array([1,2,3,4,5])

满足条件返回x,否则y

new_arr = np.where(arr > 3, 100, 0)

只返回满足条件的下标

idx = np.where(arr > 3)

去重、唯一值

arr = np.array([1,2,2,3,3,3])

去重

np.unique(arr)

去重 + 计数

vals, counts = np.unique(arr, return_counts=True)

空值(NaN)相关问题

arr = np.array([1, 2, np.nan, 4])

判断是否 NaN

np.isnan(arr)

注意:np.nan == np.nan 是 False,正确删除 NaN

arr[~np.isnan(arr)]

算时自动跳过 NaN

np.nanmean(arr)
np.nansum(arr)
np.nanstd(arr)

为什么要设置 dtype?

  • 控制内存占用(int8/int32/float64)
  • 避免溢出、计算错误
  • 提升运算速度
arr = np.array([1,2,3], dtype=np.float32)

随机数生成

0~1 均匀分布

np.random.rand(3,3)

标准正态分布

np.random.randn(3,3)

整数随机

np.random.randint(0,10, size=(2,2))

打乱顺序

np.random.shuffle(arr)

设置随机种子,保证可复现

np.random.seed(42)

Matplotlib + Seaborn

Matplotlib 是什么?Seaborn 是什么?关系?

  • Matplotlib:Python 最基础的绘图库,可以画几乎所有静态图表,自由度极高。
  • Seaborn:基于 Matplotlib 封装的统计可视化库,语法更简洁、图更美观,专门用于数据分析。
  • 关系:Seaborn 底层是 Matplotlib,可以互相配合使用。

数据分析常用哪些图表?分别用于什么场景?

  • 折线图:看趋势、时间变化
  • 柱状图 / 条形图:类别对比
  • 直方图 / 核密度图:看数据分布
  • 箱线图:看异常值、分位数、分布范围
  • 散点图:看变量相关性
  • 热力图:看相关系数矩阵
  • 饼图:看占比

Matplotlib 两张图:figure /axes 是什么?

  • figure:画布,整张图的容器
  • axes:子图,真正画图的区域
  • 现在推荐用 OO 风格fig, ax = plt.subplots()

Matplotlib-绘制最简单的折线图

import matplotlib.pyplot as plt
import numpy as np

x = [1,2,3,4,5]
y = [2,4,6,8,10]

# 创建画布
fig, ax = plt.subplots(figsize=(8,4))
# 画折线
ax.plot(x, y, color='red', linewidth=2, marker='o', label='y=2x')
# 标题、标签
ax.set_title('折线图示例', fontsize=14)
ax.set_xlabel('X轴')
ax.set_ylabel('Y轴')
# 图例
ax.legend()
# 网格
ax.grid(True, alpha=0.3)
plt.show()

Matplotlib-画柱状图

x = ['A','B','C','D']
y = [10,25,18,32]

fig, ax = plt.subplots()
ax.bar(x, y, color='steelblue')
ax.set_title('柱状图')
plt.show()

Matplotlib-画直方图(看分布)

data = np.random.randn(1000)
fig, ax = plt.subplots()
ax.hist(data, bins=30, alpha=0.7)
ax.set_title('数据分布')
plt.show()

Matplotlib-画散点图(看相关性)

x = np.random.randn(100)
y = x * 2 + np.random.randn(100)

fig, ax = plt.subplots()
ax.scatter(x, y, s=20, alpha=0.6)
ax.set_title('散点图')
plt.show()

Matplotlib-画子图(多图并排)

fig, (ax1, ax2) = plt.subplots(1,2, figsize=(10,4))
ax1.plot([1,2,3],[4,5,6])
ax2.bar(['a','b'],[10,20])
plt.tight_layout()  # 自动调整间距
plt.show()

Matplotlib-如何保存图片?

  • dpi=300 高清
  • bbox_inches='tight' 防止标题被截断
plt.savefig('test.png', dpi=300, bbox_inches='tight')

Matplotlib-中文乱码怎么解决?

plt.rcParams['font.sans-serif'] = ['SimHei']  # 黑体
plt.rcParams['axes.unicode_minus'] = False     # 负号正常显示

Seaborn-绘制柱状图(带误差棒 / 分组)

import seaborn as sns
import pandas as pd

df = pd.DataFrame({
    'major':['工','工','理','理'],
    'score':[80,85,75,78]
})

sns.barplot(data=df, x='major', y='score', palette='viridis')
plt.title('各专业平均分')
plt.show()

Seaborn-箱线图(识别异常值)

# 单变量箱线图
sns.boxplot(y=df['score'])

# 分组箱线图
sns.boxplot(data=df, x='major', y='score')
plt.show()

Seaborn-热力图(相关系数矩阵)

用途:看变量之间相关性,常用于生源、分数、深造率分析。

# 构造相关矩阵
corr = df.corr()
# 画热力图
sns.heatmap(corr, annot=True, cmap='coolwarm', fmt='.2f')
plt.title('相关性热力图')
plt.show()

Seaborn-散点图 + 拟合线(看线性关系)

sns.regplot(data=df, x='score', y='advance_rate')
plt.title('分数与深造率关系')
plt.show()

Seaborn-核密度图 / 分布对比

sns.kdeplot(df['score'], fill=True)
plt.title('分数分布')
plt.show()

Seaborn-分面图 FacetGrid(按类别分别画图)

g = sns.FacetGrid(df, col='major')
g.map(plt.hist, 'score')
plt.show()

Matplotlib vs Seaborn 区别?

  • Matplotlib:底层、灵活、代码多、适合自定义
  • Seaborn:高层、简洁、美观、适合统计分析、快速出图
  • 数据分析日常:Seaborn 快速画图 + Matplotlib 微调细节

箱线图、直方图、散点图分别用来干什么?

  • 箱线图:异常值 + 分位数 + 分组对比
  • 直方图:数据分布(是否正态、偏态)
  • 散点图:两个变量相关性、趋势

什么时候用热力图?

  • 展示相关系数矩阵
  • 展示交叉表、频次表
  • 常用于多维度指标相关性分析(如生源分数、毕业率、深造率)

如何让图表更专业、更适合汇报?

plt.rcParams['font.sans-serif'] = ['SimHei']
plt.figure(figsize=(10,5))
sns.barplot(...)
plt.title('...', fontsize=14)
plt.xlabel(...)
plt.ylabel(...)
plt.tight_layout()
plt.savefig('xxx.png', dpi=300)

做数据分析时可视化流程是什么?

  1. 先看数据整体:直方图 / 核密度图看分布
  2. 看异常值:箱线图
  3. 看对比:柱状图 / 条形图
  4. 看趋势:折线图
  5. 看相关性:散点图 + 热力图
  6. 最后用 Matplotlib 统一调整字体、标题、尺寸,导出高清图用于报告。

SciPy

SciPy 是什么,在数据分析里用来干什么?

SciPy 是基于 NumPy 的科学计算库,最常用在统计检验

数据分析中主要用于:A/B 测试、差异显著性检验、相关性分析

常见场景:

  • 不同专业深造率是否有显著差异
  • 不同生源分数是否存在真实差别
  • 政策 / 干预前后效果是否显著
  • 两个变量是否相关

什么是 p 值?

p 值是假设检验成立的概率

常用显著性水平 α = 0.05

  • p < 0.05:差异显著,拒绝原假设
  • p > 0.05:差异不显著,不能认为有真实差别

常见统计检验怎么选?

  • 两组连续数据比较 → t 检验
  • 多组连续数据比较 → 方差分析 ANOVA
  • 两个分类变量关系 → 卡方检验
  • 两个连续变量相关性 → 皮尔逊 / 斯皮尔曼相关
  • 非正态分布数据 → 秩和检验(Mann-Whitney U)

导入scipy

from scipy import stats
import numpy as np

正态性检验,如何检验一组数据是否符合正态分布?

t 检验前提是数据正态,否则要用秩和检验。

# 生成测试数据
data = np.random.normal(0, 1, 1000)

# Shapiro-Wilk 检验(小样本)
stat, p = stats.shapiro(data)

# Kolmogorov-Smirnov 检验
stat, p = stats.kstest(data, 'norm', args=(np.mean(data), np.std(data)))

print(f'p值={p:.3f}')
# p>0.05 → 符合正态
# p<0.05 → 非正态

独立样本 t 检验

比较 A/B 两组均值是否有显著差异

group1 = np.array([80,82,85,87,81])
group2 = np.array([75,77,72,76,74])

# 独立样本 t 检验
stat, p = stats.ttest_ind(group1, group2)

print(f't统计量={stat:.3f}, p值={p:.3f}')

# 判断
if p < 0.05:
    print("差异显著")
else:
    print("差异不显著")

配对样本 t 检验

同一批学生干预前 vs 干预后成绩是否显著提高

用途:政策效果、教学干预、活动效果评估。

before = [70,72,75,68,73]
after  = [76,78,82,74,79]

stat, p = stats.ttest_rel(before, after)

单样本 t 检验

样本均值是否显著不等于某个理论值

例如:本校平均分是否显著高于全省平均分

data = [82,81,85,83,80]
pop_mean = 75  # 全省均值

stat, p = stats.ttest_1samp(data, pop_mean)

方差分析 ANOVA(多组比较)

3 个及以上专业的分数是否存在显著差异

g1 = [80,82,85]
g2 = [75,77,79]
g3 = [70,72,71]

stat, p = stats.f_oneway(g1, g2, g3)

# p<0.05 → 至少一组有差异

卡方检验(分类变量关联性)

高频场景

  • 性别 vs 升学
  • 生源地 vs 毕业情况
  • 专业 vs 就业类型

输入是列联表(交叉表)

# 列联表:行=性别,列=是否深造
table = [[50, 100],
         [30, 120]]

chi2, p, dof, expected = stats.chi2_contingency(table)

# p<0.05 → 两个分类变量显著相关

皮尔逊相关系数(线性相关)

  • corr 接近 1 → 强正相关
  • corr 接近 -1 → 强负相关
  • p<0.05 → 相关显著
x = [1,2,3,4,5]
y = [2,4,5,7,8]

corr, p = stats.pearsonr(x, y)

斯皮尔曼等级相关(非参数,不要求正态)

数据不符合正态时用斯皮尔曼。

corr, p = stats.spearmanr(x, y)

秩和检验(非参数替代 t 检验)

数据非正态时,不能用 t 检验,用 Mann-Whitney U

stat, p = stats.mannwhitneyu(group1, group2)

t 检验和方差分析的区别?

  • t 检验:两组比较
  • ANOVA:三组及以上

什么时候用非参数检验?

  • 样本量小
  • 数据明显不符合正态分布
  • 存在极端异常值

相关系数 ≠ 因果关系?

相关只能说明一起变化,不能判断谁影响谁,也可能是第三方因素导致。

p 值很小代表什么?

代表两组差异极不可能是随机误差造成的,可以认为存在真实差异。

数据分析完整统计检验流程?

  1. 看数据分布 → 正态检验
  2. 正态 → t 检验 / ANOVA
  3. 非正态 → 秩和检验
  4. 分类变量 → 卡方检验
  5. 看相关性 → 皮尔逊 / 斯皮尔曼
  6. 看 p 值判断是否显著

Statsmodels

Statsmodels 是什么?和 Sklearn 有什么区别?

Statsmodels 是 Python 用于统计建模、统计推断的库,侧重假设检验、p 值、置信区间、R²、残差分析等统计结果。

Sklearn 侧重预测、机器学习,不重视统计指标。

数据分析常用场景:

  • 线性回归 / 逻辑回归
  • 时间序列(ARIMA)
  • 方差分析
  • 拟合后看影响因素是否显著

总结

  • 解释因素影响、看显著性 → Statsmodels
  • 预测结果、准确率 → Sklearn

线性回归用来干什么?

分析哪些变量对目标有显著影响

量化影响大小(回归系数)

控制其他变量后,看某个因素的净影响

常用于:

  • 分数 / 深造率受哪些因素影响
  • 生源、性别、专业对毕业的影响
  • 政策效果评估

最小二乘线性回归代码

import statsmodels.api as sm
import pandas as pd
import numpy as np

# 构造数据
df = pd.DataFrame({
    'score':      [80,85,77,79,82,83],  # 因变量 Y
    'study_hour': [5,  7,  4,  5, 6, 5], # 自变量 X1
    'age':        [19,20,19,18,20,19]    # X2
})

# 1. 自变量 X 必须加常数项(截距)
X = df[['study_hour', 'age']]
X = sm.add_constant(X)  # 必须加!
y = df['score']

# 2. 拟合模型
model = sm.OLS(y, X).fit()

# 3. 输出完整统计结果
print(model.summary())

注释

  • add_constant 不加会没有截距,结果错误
  • .summary() 是面试亮点:能看懂统计报表

如何看回归结果 summary?

1. R-squared(R²)

模型解释力,越接近 1 越好。

2. coef(系数)

变量每增加 1,y 变化多少。正 = 正向影响,负 = 负向影响。

3. P>|t|(p 值)

  • p < 0.05:变量显著
  • p > 0.05:不显著,可剔除

4. std err / t

系数的统计显著性。

5. 残差诊断(JB、Prob (JB))

看残差是否正态,模型是否合理。

总结

先看 R² 判断解释力度,再看每个变量的 coef 方向与大小,最后看 p 值判断是否显著,同时观察残差是否满足正态假设。

逻辑回归(分类问题)

用于二分类问题:是否毕业、是否深造、是否就业、是否报到等。

# 因变量是 0/1
y = np.array([1,1,0,1,0,1])

# 建模
model = sm.Logit(y, X).fit()
print(model.summary())

输出看

  • coef:影响方向
  • P>|z|:是否显著
  • 预测概率:model.predict(X)

线性回归有哪些基本假设?

  1. 线性:X 与 Y 线性关系
  2. 独立:样本相互独立
  3. 正态:残差近似正态分布
  4. 同方差:残差方差恒定
  5. 无多重共线性:自变量之间不高度相关

多重共线性怎么判断、怎么处理?

判断

  • 看系数符号反常、p 值不显著
  • 计算VIF(方差膨胀因子)
from statsmodels.stats.outliers_influence import variance_inflation_factor

vif = [variance_inflation_factor(X.values, i) for i in range(X.shape[1])]

判断标准

  • VIF > 10:严重共线性
  • VIF > 5:轻度共线性

处理

  • 删除其中一个变量
  • 合并变量
  • 正则化(ridge/lasso)

异常值 / 强影响点怎么检测?

# Cook 距离
infl = model.get_influence()
cook = infl.cooks_distance[0]

Cook 距离大 → 强影响点,需要检查。

Statsmodels 时间序列能干什么?

  • ARIMA / SARIMA 预测
  • 平稳性检验(ADF)
  • 白噪声检验
  • 趋势、季节性分析

ADF 平稳性检验

from statsmodels.tsa.stattools import adfuller

stat, p, _, _, _, _ = adfuller(ts)
# p < 0.05 → 序列平稳

什么时候用 Statsmodels,什么时候用 Sklearn?

  • 统计推断、看显著性、解释影响因素、写分析报告 → Statsmodels
  • 预测、分类、模型准确率 → Sklearn

回归系数(coef)代表什么?

控制其他变量不变的情况下,该变量每增加 1,因变量平均变化多少。

p < 0.05 代表什么?

该变量对 Y 有显著影响,不是随机误差造成的。

R² 是什么意思?太低怎么办?

R² 表示模型能解释 Y 的方差比例。

太低说明:

  • 缺失重要变量
  • 关系不是线性
  • 噪声太大

用 Statsmodels 做过什么业务分析?

用 Statsmodels 做过影响因素分析,比如分析生源分数、学习时长、专业等变量对深造率 / 毕业率的影响,通过回归系数和 p 值判断哪些因素显著,最终给出可解释的分析结论,而不只是预测

Scikit-learn(sklearn)

Scikit-learn 是什么,在数据分析里用来干什么?

Python 里最通用的机器学习库,封装了几乎所有经典算法。

数据分析里主要用于:

  • 分类 / 预测(是否升学、是否报到、是否流失)
  • 特征重要性分析
  • 聚类(用户分群、生源分群)
  • 数据预处理(归一化、编码、降维)

和 Statsmodels 区别:

  • sklearn:重预测、重准确率
  • Statsmodels:重统计推断、重显著性、重解释

机器学习四大类

  • 分类:预测类别(0/1,是否深造)
  • 回归:预测连续值(分数、收入、升学概率)
  • 聚类:无标签分组(用户分层、生源分层)
  • 降维:PCA 等,简化特征、可视化

模型构建标准流程

  1. 数据读取与探索
  2.  特征工程(缺失值、编码、归一化)
  3. 划分训练集/测试集 train_test_split
  4. 模型初始化
  5. 训练 model.fit(X_train, y_train)
  6. 预测 model.predict(X_test)
  7. 评估指标(准确率、MAE、AUC 等)
  8. 模型优化与特征重要性

分类特征编码:OneHot、LabelEncoder

性别、专业等离散特征 → OneHotEncoder

有序类别(低/中/高)→ LabelEncoder

from sklearn.preprocessing import OneHotEncoder, LabelEncoder

数值特征归一化 / 标准化

标准化(均值0方差1)→ 大多数模型首选

归一化(0~1)→ 神经网络、距离模型

from sklearn.preprocessing import StandardScaler, MinMaxScaler

scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)

缺失值处理 SimpleImputer

均值/中位数/众数填充

from sklearn.impute import SimpleImputer

imputer = SimpleImputer(strategy='median')

数据集划分

from sklearn.model_selection import train_test_split

X_train, X_test, y_train, y_test = train_test_split(
    X, y, test_size=0.2, random_state=42
)

线性回归(预测连续值,如分数)

from sklearn.linear_model import LinearRegression

model = LinearRegression()
model.fit(X_train, y_train)
pred = model.predict(X_test)

逻辑回归(二分类,如是否升学、是否就业)

from sklearn.linear_model import LogisticRegression

model = LogisticRegression()
model.fit(X_train, y_train)
pred = model.predict(X_test)
pred_prob = model.predict_proba(X_test)[:,1]

决策树 / 随机森林(最常用、最强业务解释性)

  • 能输出特征重要性 feature_importances_
  • 不需要强特征标准化
  • 擅长非线性关系
from sklearn.ensemble import RandomForestClassifier

rf = RandomForestClassifier(n_estimators=100)
rf.fit(X_train, y_train)

K-Means 聚类(用户分层、生源分层)

用途:

  • 把学生分成:高分稳定型、潜力型、待关注型
  • 做精细化运营 / 培养策略
from sklearn.cluster import KMeans

km = KMeans(n_clusters=3, random_state=42)
labels = km.fit_predict(X_scaled)

PCA 降维

from sklearn.decomposition import PCA

pca = PCA(n_components=2)
X_pca = pca.fit_transform(X_scaled)

分类模型指标有哪些?

  • 准确率 Accuracy:总体预测对的比例
  • 精确率 Precision:预测为 1 的里面真的是 1
  • 召回率 Recall:真实 1 里被预测出来的比例
  • F1:精确率与召回率平衡
  • AUC / ROC:二分类最常用、最靠谱
from sklearn.metrics import accuracy_score, precision_score, recall_score, roc_auc_score

回归模型指标有哪些?

  • MAE 平均绝对误差
  • MSE/RMSE 均方误差 / 平方根误差
  • 解释程度(越接近 1 越好)
from sklearn.metrics import mean_absolute_error, r2_score

聚类评估有哪些?

  • 轮廓系数
  • Calinski-Harabasz 指数

过拟合是什么?怎么解决?

模型在训练集上表现特别好,但在测试集 / 新数据上表现很差。

原因:模型把噪声、偶然规律也学会了,没有学到真正通用的模式。

表现:

  • 训练集准确率 / 误差很优秀
  • 测试集准确率骤降、误差飙升
  • 模型太复杂,泛化能力差

解决方案:

1. 增加数据

  • 数据越多,噪声影响越小,模型越容易学到真实规律。

2. 降低模型复杂度

  • 线性模型:减少特征
  • 决策树:减小深度、减少叶子节点
  • 少用复杂模型(如深度树、复杂神经网络)

3. 正则化(最常用)

  • L1 正则:让部分特征系数变为 0,自动做特征选择
  • L2 正则:压缩系数大小,防止极端权重
  • 逻辑回归、线性回归常用:LogisticRegression(C=0.1) C 越小,正则越强

4. 剪枝(树模型专用)

  • 限制树深度 max_depth
  • 限制叶子节点最小样本数 min_samples_leaf
  • 提前停止生长

5. 特征选择 / 降维

  • 删除无关、冗余、噪声特征
  • 使用 PCA、方差筛选、相关性筛选

6. 早停 Early Stopping

  • 训练时监控验证集误差,不再提升就停止,防止过度学习。

7. 集成模型(简单有效)

  • 随机森林、XGBoost 自带抗过拟合能力,比单棵树稳得多。

总结

过拟合就是模型在训练集表现很好,但泛化能力差,在新数据上表现差。

解决方法主要有:增加数据、降低模型复杂度、使用正则化、特征选择、剪枝,以及用随机森林这类集成模型

欠拟合是什么?怎么解决?

模型在训练集上表现就很差,测试集也很差

原因:模型太简单、学习能力不足,连数据里的基本规律都没学会

表现:

  • 训练集误差大、准确率低
  • 测试集同样差
  • 模型偏差(Bias)过高

解决方案:

1. 增加更有用的特征

  • 手工构造特征(组合特征、交叉特征、时间特征等)
  • 引入更多维度信息

2. 提高模型复杂度

  • 换成更复杂的模型:线性 → 树模型 / 集成模型
  • 加深树深度、增加叶子节点

3. 减少正则化

  • 减小正则化强度
  • 线性模型调大 C
  • 树模型减少剪枝

4. 去掉不必要的降维、特征筛选

  • 别把有用信息过滤掉了

5. 训练更充分

  • 增加迭代次数
  • 调整学习率
欠拟合 Underfitting 过拟合 Overfitting
训练集效果 很好
测试集效果 很差
模型复杂度 太简单 太复杂
核心问题 高偏差,没学会规律 高方差,学了噪声
解决思路 加特征、加复杂度 降复杂度、正则、剪枝、加数据

总结

欠拟合是模型太简单,在训练集上都学不好,偏差过高。

解决方法主要是:增加有效特征、提高模型复杂度、减少正则化

而过拟合是模型太复杂,学了噪声,泛化差,需要降复杂度、正则化、剪枝、增加数据等方式解决。

什么是交叉验证?

交叉验证(Cross Validation)就是:把数据集分成多份,轮流用其中一部分当验证集,多次训练评估,最后取平均结果,让模型评估更可靠。

为什么要用交叉验证?

  • 只分一次 train/test,结果容易碰巧好 / 碰巧差,不稳定。
  • 交叉验证能避免运气成分,更真实地反映模型泛化能力。
  • 防止你因为单次划分运气好,高估或低估模型效果。

最常用的:K 折交叉验证(K-Fold)

流程(以 5 折 为例):

  1. 把数据平均分成 5 份
  2. 第 1 次:用 1,2,3,4 份训练,第 5 份验证
  3. 第 2 次:用 1,2,3,5 份训练,第 4 份验证
  4. …… 依次轮换
  5. 最后得到 5 个分数,取平均值 作为最终评估结果
from sklearn.model_selection import cross_val_score

# cv=5 就是 5 折交叉验证
scores = cross_val_score(model, X, y, cv=5)

# 平均分数
print(scores.mean())

总结

交叉验证是把数据集分成若干份,轮流作为验证集来多次评估模型,最后取平均结果。目的是让模型评估更稳定、可靠,避免单次划分带来的偶然性,更准确地反映模型的泛化能力。

扩展

  • K 一般取多少?常用 5 折 或 10 折
  • 什么时候用留一法(LOOCV)?数据特别少的时候
  • 交叉验证的作用?
    1. 评估模型效果
    2. 调参(网格搜索)
    3. 对比不同模型

网格搜索 GridSearchCV

GridSearchCV = 穷举所有参数组合 + 交叉验证(CV)自动选出最好的参数。

  • 模型里有很多超参数:比如随机森林的 max_depthn_estimators逻辑回归的 C(正则强度)
  • 人工一个个试太慢、不准
  • GridSearchCV 自动遍历所有参数组合,用交叉验证打分,选出最优一组

基本流程

  1. 定义一个参数网格(字典):要试哪些值都列出来
  2. 遍历每一种参数组合
  3. 每组参数都做 K 折交叉验证
  4. 记录平均分数
  5. 最终输出:最优参数 + 最优分数
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import GridSearchCV

# 模型
rf = RandomForestClassifier()

# 定义要搜索的参数网格
param_grid = {
    'max_depth': [3, 5, 7],       # 树深度
    'n_estimators': [50, 100, 200] # 树数量
}

# 网格搜索 + 5折交叉验证
grid = GridSearchCV(
    estimator=rf,
    param_grid=param_grid,
    cv=5,          # 5折交叉验证
    scoring='roc_auc'
)

grid.fit(X_train, y_train)

# 结果
print("最优参数:", grid.best_params_)
print("最优分数:", grid.best_score_)

# 用最优模型预测
best_model = grid.best_estimator_
  • 优点:结果客观、自动、可靠
  • 缺点:参数多的时候非常慢(暴力穷举)
  • 更快的替代RandomizedSearchCV(随机搜索,不遍历全部)

总结

GridSearchCV 是一种自动调参方法,它会穷举我们指定的所有参数组合,并通过交叉验证评估每组参数的效果,最终自动选出泛化能力最好的参数组合,让模型效果更稳定、避免人工调参的主观性。

特征重要性怎么看?

特征重要性 = 这个特征对模型预测贡献有多大,值越大,说明这个特征越关键。

1. 树模型(最常用)

  • 随机森林 Random Forest
  • 决策树
  • GBDT / XGBoost / LightGBM

2. 线性模型

  • 线性回归
  • 逻辑回归(看系数绝对值大小,但要先标准化)

3. 不推荐

KNN、SVM、神经网络 → 很难直接看重要性

树模型代码

from sklearn.ensemble import RandomForestRegressor

model = RandomForestRegressor()
model.fit(X_train, y_train)

# 查看特征重要性
importances = model.feature_importances_

# 转成DataFrame方便看
import pandas as pd
fi = pd.DataFrame({
    'feature': X_train.columns,
    'importance': importances
}).sort_values('importance', ascending=False)

print(fi)

原理

  • 树在分裂时,用这个特征减少了多少误差(基尼系数 / 方差)
  • 减少越多 → 越重要

线性模型代码

  • 必须先标准化,否则量纲不同不能比
  • 系数绝对值越大 → 越重要
  • 正负代表影响方向
from sklearn.linear_model import LinearRegression

model = LinearRegression()
model.fit(X_train_scaled, y_train)  # 必须先标准化!

coef = pd.DataFrame({
    'feature': X_train.columns,
    'coef': model.coef_
}).sort_values('coef', key=abs, ascending=False)

总结

树模型(如随机森林)可以直接通过 feature_importances_ 查看特征重要性,值越大表示该特征对预测贡献越大。线性模型需要先做标准化,再看系数的绝对值大小。在分析中常用它来识别关键影响因素。

注意

  • 特征重要性高 ≠ 因果关系,只是相关性
  • 多重共线性会让重要性失真
  • 树模型容易偏好高基数特征(如 ID、类别多的特征)
  • 数据分析里最常用:随机森林看特征重要性,用来做因素分析

分类模型评估指标

4 个基础指标

  • TP(真正例):真 1,预测 1
  • FN(假反例):真 1,预测 0
  • FP(假正例):真 0,预测 1
  • TN(真反例):真 0,预测 0

5 大核心指标

1. 准确率 Accuracy

公式:(TP + TN) / 全部

  • 所有样本里预测对的比例
  • 缺点:类别不平衡时完全没用(比如 99% 是 0,瞎猜都能 99% 准确率)

2. 精确率 Precision(查准率)

预测为 1 的里面,有多少是真 1

  • TP / (TP + FP)
  • 场景:宁可少抓,不能抓错例如:垃圾邮件识别、推荐系统

3. 召回率 Recall(查全率)

真实为 1 的里面,有多少被找出来

  • TP / (TP + FN)
  • 场景:宁可错抓,不能漏掉例如:金融欺诈、疾病检测、风险识别

4. F1 分数

精确率与召回率的调和平均

  • 2 * (Precision * Recall) / (Precision + Recall)
  • 两者都要兼顾时用

5. AUC(最常用、最重要)

  • 衡量模型整体区分能力
  • 范围 0.5 ~ 1
    • 0.5 = 瞎猜
    • 0.7~0.8 = 可用
    • 0.8~0.9 = 很好
    • 0.9+ = 极强
  • 优点:不受类别不平衡影响
  • 数据分析面试必说 AUC

总结

分类模型常用的评估指标有:准确率、精确率、召回率、F1 和 AUC。准确率在不平衡数据下不可靠,所以我一般优先看 AUC。业务需要少误判时看精确率,需要不漏掉目标时看召回率,两者兼顾用 F1。

标准化和归一化区别?

归一化 MinMaxScaler 标准化 StandardScaler
范围 0~1 均值 0,方差 1
受异常值影响 很大 较小
数据分布要求 近似正态更稳
适用场景 固定范围、距离模型 大多数机器学习模型
  • StandardScaler:均值 0 方差 1 → 通用
  • MinMaxScaler:0~1 → 距离类模型(KNN、KMeans、神经网络)

用 归一化 的场景:

  • KNN、K-Means、SVM 等距离 - based 模型
  • 神经网络
  • 需要把值限定在 0~1 之间

用 标准化 的场景:

  • 线性回归、逻辑回归
  • 随机森林、树模型也可以用(不强制)
  • 数据存在异常值时更稳
  • 日常建模默认优先用标准化

树模型不需要标准化?树模型按大小排序分裂,和数值绝对大小无关。

总结

归一化是把数据缩放到 0~1,标准化是把数据变成 均值 0 方差 1。归一化受异常值影响大,适合距离类模型;标准化更稳健,日常建模一般优先用标准化

类别特征用什么编码?

一、无序分类特征(性别、专业、城市、省份)

1. One-Hot 编码(独热编码)

最常用、默认首选

  • 一列变多列,只有 0/1
  • 不引入大小关系
  • 类别不多时用

适用:性别、专业、省份、学历等

二、有序分类特征(低 / 中 / 高、小 / 大、差 / 良 / 优)

2. 标签编码 / 有序编码 LabelEncoder / OrdinalEncoder

  • 按顺序映射成 0,1,2…
  • 保留大小关系

适用:成绩等级、风险等级、教育阶段

三、高基数类别(用户 ID、手机号、学校编号、超多省份)

3. 频率编码(计数编码)

用出现次数代替类别

4. 目标编码(均值编码)

用该类别对应的目标均值编码(比如:某专业深造率 = 编码)

适用:类别特别多、one-hot 会爆炸的场景

四、树模型 vs 线性模型怎么选?

树模型(随机森林、XGBoost)

  • 可以直接用标签编码
  • 也可以用 目标编码
  • 一般不用 one-hot(会影响效果)

线性模型 / 逻辑回归 / KNN / 神经网络

  • 必须用 One-Hot
  • 不能直接用标签编码(会引入虚假大小关系)

总结

类别不多的无序特征用 One-Hot 编码;有序特征用 标签编码或有序编码;类别特别多的高基数特征用 频率编码或目标编码;线性模型必须用 One-Hot,树模型可以直接用标签编码或目标编码。

用 sklearn 做过什么实际分析?

用 sklearn 做过学生升学概率预测模型,用随机森林看特征重要性,识别出影响深造的关键因素,并用聚类做学生分层,辅助制定针对性培养策略。

类别不平衡(比如很少人违约、很少人辍学)怎么办?

1. 更换评估指标(最简单、第一步必做)

  • 不用 Accuracy 准确率(会骗人)
  • 改用:
    • AUC
    • F1 分数
    • Recall 召回率

2. 调整样本(最常用)

(1)过采样 Oversampling

  • 少数类重复采样、生成样本
  • 优点:用足少量信息
  • 缺点:容易过拟合

(2)欠采样 Undersampling

  • 多数类随机删掉一些
  • 优点:快、简单
  • 缺点:丢信息

(3)SMOTE 算法

  • 在少数类样本之间插值生成新样本
  • 比简单过采样更不容易过拟合
  • 最常用、最推荐

3. 类别权重 Class Weight

直接在模型里给少数类更高的权重,惩罚错分。

代码示例:

# 逻辑回归
LogisticRegression(class_weight='balanced')

# 随机森林
RandomForestClassifier(class_weight='balanced')

不用改数据,效果往往很好。

4. 阈值移动 Threshold Moving

模型默认阈值 0.5,我们调低阈值(如 0.2、0.3),让模型更容易预测为少数类,提高召回率

5. 集成方法

  • 对多数类多次欠采样
  • 训练多个模型
  • 最后投票不容易过拟合,效果稳定。

总结

类别不平衡时,首先不使用准确率,改用 AUC、F1、召回率。然后可以用SMOTE 过采样欠采样平衡数据。最简单有效的是直接设置 class_weight='balanced' 调整类别权重。也可以通过降低阈值提高少数类的识别率。

逻辑回归 / 决策树 / 随机森林怎么选?

  • 逻辑回归:线性模型,可解释性极强,速度快
  • 决策树:非线性,可解释,但容易过拟合
  • 随机森林:多棵树集成,效果最好、最稳,泛化能力强

1. 逻辑回归 Logistic Regression

  • 类型:线性模型
  • 优点
    • 速度极快
    • 可解释性最强(能看系数、显著性、概率)
    • 不容易过拟合
    • 输出是概率,方便业务理解
  • 缺点
    • 只能学线性关系
    • 无法处理复杂交互
  • 适合场景
    • 需要清晰解释因素影响(如:哪些因素影响升学 / 违约)
    • 数据量很大、要求快
    • 线上简单预测

2. 决策树 Decision Tree

  • 类型:非线性、规则模型
  • 优点
    • 可解释(能画树、能读规则)
    • 不用标准化
    • 能处理非线性、特征交互
  • 缺点
    • 非常容易过拟合
    • 不稳定,数据一变树就大变
  • 适合场景
    • 小数据、需要白盒规则
    • 做初步探索分析
    • 一般不直接用于最终建模

3. 随机森林 Random Forest

  • 类型:集成模型(多棵决策树投票)
  • 优点
    • 效果通常最好
    • 抗过拟合、稳定性强
    • 能处理非线性、异常值、多重共线性
    • 能输出特征重要性(数据分析神器)
  • 缺点
    • 比逻辑回归慢一点
    • 可解释性比逻辑回归差(黑盒)
  • 适合场景
    • 通用首选模型
    • 效果优先、不知道用啥时就用它
    • 找关键影响因素(特征重要性)
    • 分类 / 回归都强

怎么选?

1. 优先选 逻辑回归

  • 需要强可解释性
  • 要报告系数、显著性、影响方向
  • 数据大、要求速度

2. 优先选 随机森林

  • 追求预测效果
  • 存在非线性、特征交互
  • 想看特征重要性
  • 不知道用啥模型时的默认首选

3. 一般不单独用决策树

  • 容易过拟合、不稳定
  • 要用也用剪枝,或直接升级成随机森林

总结

逻辑回归线性、可解释性最强,适合需要清晰说明因素影响的场景;决策树能处理非线性,但容易过拟合;随机森林是集成模型,效果最稳定、泛化能力最强,还能输出特征重要性,是我做数据分析时的通用首选模型

K-Means

K-Means 是什么?

K-means 属于 Scikit-learn,是无监督聚类算法,把相似的样本自动分成 K 个簇。不需要标签 y,只需要特征 X。

from sklearn.cluster import KMeans

K-Means 的执行过程?

  1. 随机选 K 个点作为初始质心
  2. 每个样本计算到质心距离,归到最近的簇
  3. 重新计算每个簇的新质心(均值)
  4. 重复 2、3,直到质心不再变化

归类 → 求中心 → 再归类

K 怎么确定?

  • 手肘法(Elbow Method)看簇内误差平方和 SSE 下降趋势,拐弯点就是 K
  • 轮廓系数(Silhouette Score)越大聚类效果越好
  • 结合业务:比如分 3 类:高价值 / 中等 / 普通

K-Means 优缺点?

优点

  • 简单、快、好用
  • 大数据集也能跑
  • 客户分群、用户分层神器

缺点

  • 需要手动指定 K
  • 异常值极敏感
  • 量纲敏感(必须标准化)
  • 只能发现凸、球形簇,不规则形状不行
  • 初始质心影响结果(要设 random_state)

K-Means 为什么要标准化 / 归一化?

因为 K-Means 基于距离(欧氏距离)。如果特征量纲不一样(比如年龄 0-100,收入 0-100 万),收入会直接主导距离,结果失真。

必须用 StandardScaler 或 MinMaxScaler。

K-Means 遇到异常值怎么办?

  • 先删异常值
  • 或用 K-Medians(更稳,但 sklearn 没有)
  • 或用 DBSCAN 密度聚类替代

用 K-Means 做过什么?

做用户 / 学生分层,比如根据成绩、活跃度、消费等特征聚类,分成高潜力、普通、待关注群体,用于精细化运营和策略分析。

Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐