拉勾数据分析第八期

1. 数据分析思维与业务流程

1.1 数据分析概述

1.1.1 预测未来 - 数据分析在总统大选中的预测作用


传统抽样,随机抽人,但是可能抽样的人群大部分是某个特定群体的,导致结果不准,而定额抽样法可以避免,样本更分散

但是 1948 年的总统预测却错了,当时预测杜威会打败杜鲁门获胜,实际上却是杜鲁门获胜。因为杜威是共和党人,共和党人的选民大部分是高知和富裕的人,而调查人员又偏好去富裕、环境好的地方采样,所以导致预测失败。

于是,定额抽样法再次优化为分层多阶抽样




1.1.2-1.1.3 优化现状-数据分析对化妆品销售的优化作用…









加载数据

数据处理:将矩阵转置,要让列是不同的影响因素,行是不同月份。这样比较好处理


corr:获得特征和特征之间的线性关系(y=kx+b,y 和 x 之间的关系),一般值是-1~1,0 为不相关,1 为正相关(x↑y↑),-1 为负相关(x↑y↓)

我们只关心总销量和其他影响因素的关系

公司报表喜欢将结论放前面

1.1.4-1.1.5 总结规律-数据分析师在招聘市场上的需求分.…









从后端平台下载数据,存到 excel,通过 python 读入



使用工具进行汇总…



柱状图是 excel 生成的,通过 sql 导出 excel




1.1.6 数据分析师职业规划&课程体系



1.2 实战-某线下连锁水果店销售数

1.2.1 水果店营收背景

SKU可以理解为商品种类数量

1.2.2 问题确认与指标拆解

1.2.3 水果店利润问题解决流程



1.2.4 利用分组分析找到亏损店铺做营销优化

实操主要关注指定方案、目标评估、实验、分析实验效果等步骤,其中目标评估需要和领域专家合作





操作


1.2.5 分组分析实验验证与结论




这三组复制到右边,然后首列选择左对齐
计算日均毛利和平均利润的增幅(分析统计的方法、数据选择因人而异)
增长额度格子输入=号,然后鼠标会变成一个大加号,点击可以选择用于计算的格子里的数据
接下来输入-号,然后点击方案前的格子
回车后自动计算出结果,接下来点击格子右下角的小点,向下拖动就可以将该公式应用到下面的格子
接下来计算增幅:增长额度/方案前

将数据变为百分比
(常用)还可以右键点击设置单元格格式来变为百分比


计算毛利额:方案前日均毛利*(1 + 增幅)^3


数据可视化

先让表格好看点

选中一行后按住ctrl可以继续选择第二行

为了将刻度统一,我们双击其他两个小刻度的刻度轴,然后把刻度的最高值改为6000
对齐后,将右边两个的刻度去掉

然后可以右键柱子增加数据标签

增加趋势线
添加文本框,内容为增幅

1.2.6 运用对比分析、矩阵关联、超势分析解决水果…

2. MYSQL 数据分析实战

3. 互联网公司必备-BI 商业智能工具

3.1 Tableau 数据可视化

3.1.1 引言 BI 可视化明星——Tableau

01–问题先行










演示

为什么学 Tableau












Tableau 可视化成果展示


  • 其他 BI(fineBI、quickBI 等国产 BI)都是碰瓷 Tableau 和 PowerBi 的,不建议专门学

02–课程亮点&学完收获







03–课程大纲












3.1.2 任务一 出发去探索 Tableau 吧

01–Tableau 家族产品初探索





02–Tableau Desktop 工作区




双击表进入物理层

工作表



我 2021 版的破解需要在仪表盘打开工作表才能看到图

仪表板







故事


新建故事点

03–Tableau Desktop 文件管理

3.1 Tableau 工作簿 / 打包工作簿(.twb / .twbx)


3.2 Tableau 数据源(.tds / .tdsx)


3.3 Tableau 数据提取(.hyper)



总结


3.1.3 任务二 连接数据,基础且必须

01–认识 Tableau 数据–数据角色

度量和维度


离散和连续


蓝色字段和绿色字段


02–认识 Tableau 数据–字段类型

1.2.1 Tableau 中的数据类型图标

03–认识 Tableau 数据–字段类型转换

在 Tableau 中,我们可以在“数据源”页面或工作表“数据”窗格页面中更改字段的数据类型。

数据源页






工作表“数据”窗格


使用地图功能要科学上网
销售额拖动到颜色上,则根据销售额大小,显示不同颜色

04–认识 Tableau 数据–字段简单处理

1.4.1 数据解释器

csv是连接到文本文件

1.4.2 列拆分
  • 数据源页



  • 工作表“数据”窗格


1.4.3 转置



1.4.4 隐藏





1.4.5 重命名




05–支持导入的数据类型丰富多样

2.1 本地文件数据
  • 2.1.1 Excel 文件

  • 2.1.2 文本文件( csv / txt )




2.2 服务器数据




06–轻松实现数据融合–数据连接

3.1 数据连接

  • 3.1.1 连接方式


  • 3.1.2

    英雄榜



    双击进入物理层,然后才能连接
    将要连接的表拖入
    默认创建内连接
    建立左连接

07–轻松实现数据融合–数据合并[3]


3.2.1 数据合并方式
  • 手动合并



  • 通配符搜索

    双击 新建并集
    默认把所有表合并


    csv会把当前文件夹的都加载,而excel只会加载单个文件,所以excel只能通过通配符来建立并集

08–轻松实现数据融合–数据混合关系

4. 大数据查询利器 Hive

5. 数据分析必学编程语言-Python

6. 数据分析必备理论基础-统计学知识

1 统计学基本原理:描述统计、总体推断

任务一:描述统计

统计学的本质和目的


描述性统计大概了解数据表象的特征,再通过推断性统计检验表象特征哪些真哪些假

统计学基本概念:变量测量尺度

定距的数据,比如温度,为 0 是有意义的(没有绝对 0 点),而定比的数据,为 0 是没意义的;定比的数据可以乘除



统计学基本概念:平均值


调和平均用得很少

数据分布图(x轴0-1,y轴是数据的频率)波峰在左边则为右偏,这种情况可能使用调和平均




统计学基本概念:中位数和众数

均值和中值、众数衡量集中趋势,可以描述一个群体的共性




这里的x轴是分段数据,但是它通过取区间中点值转为了数值型变量

统计学基本概念:极差和标准差

离散趋势(应用更多,代表了数据包含的信息量)





任务二:总体推断

7. 数据分析项目实战-指标体系与 ABTest

8. 数据挖掘算法与实战

第八阶段模块一

1–任务一: KNN 算法

01–前言:机器学习理论基础





1.1 常用机器学习算法体系

  • 1.1.1 有监督学习
  • 1.1.2 无监督学习
  • 1.1.3 半监督学习
  • 1.1.4 强化学习
  • 1.1.5 输入/输出空间、特征空间
  • 1.1.6 过拟合与欠拟合


02–算法原理与实现步骤





03–算法优缺点及算法变种


04–python 实现

  • 导入相关包

    #全部行都能输出
    from IPython.core.interactiveshell import InteractiveShell
    InteractiveShell.ast_node_interactivity = "all"
    import numpy as np
    import pandas as pd
    import matplotlib.pyplot as plt
    # 解决坐标轴刻度负号乱码
    plt.rcParams['axes.unicode_minus'] = False
    # 解决中文乱码问题
    plt.rcParams['font.sans-serif'] = ['Simhei']
    plt.style.use('ggplot')
    # plt.figure(figsize=(2,3),dpi=720)
    
  • 构建已经分类好的原始数据集

    首先随机设置十个样本点表示十杯酒,这里取了部分样本。为了方便验证,这里使用 Python 的字典 dict 构建数据集,然后再将其转化成 DataFrame 格式。

    rowdata = {'颜色深度': [14.13,13.2,13.16,14.27,13.24,12.07,12.43,11.79,12.37,12.04],
               '酒精浓度': [5.64,4.28,5.68,4.80,4.22,2.76,3.94,3.1,2.12,2.6],
               '品种':  [0,0,0,0,0,1,1,1,1,1]}
    # 0 代表 “黑皮诺”,1 代表 “赤霞珠”
    wine_data = pd.DataFrame(rowdata)
    wine_data
    

    X = np.array(wine_data.iloc[:, 0:2])  # 我们把特征(酒的属性)放在X
    y = np.array(wine_data.iloc[:, -1])  # 把标签(酒的类别)放在Y
    # 探索数据,假如我们给出新数据[12.03,4.1] ,你能猜出这杯红酒是什么类别么?
    new_data = np.array([12.03, 4.1])
    plt.scatter(X[y == 1, 0], X[y == 1, 1], color='red', label='赤霞珠')  # 画出标签y为1的、关于“赤霞珠”的散点
    plt.scatter(X[y == 0, 0], X[y == 0, 1], color='purple', label='黑皮诺')  # 画出标签y为0的、关于“黑皮诺”的散点
    plt.scatter(new_data[0], new_data[1], color='yellow')  # 新数据点
    print(new_data)
    plt.xlabel('酒精浓度')
    plt.ylabel('颜色深度')
    plt.legend(loc='lower right')
    plt.savefig('葡萄酒样本.png')
    

  • 计算已知类别数据集中的点与当前点之间的距离

    我们使用欧式距离公式,计算新数据点 new_data 与现存的 X 数据集每一个点的距离:

    from math import sqrt
    distance = [sqrt(np.sum((x-new_data)**2)) for x in X ]
    distance
    

  • 将距离升序排列,然后选取距离最小的 k 个点

    sort_dist = np.argsort(distance)
    sort_dist
    

    array([6, 7, 1, 4, 5, 9, 2, 8, 3, 0], dtype=int64)

    6、7、4 为最近的 3 个“数据点”的索引值,那么这些索引值对应的原数据的标签是什么?

    k = 3
    topK = [y[i] for i in sort_dist[:k]]
    topK # [1,1,0]
    
  • 确定前 k 个点所在类别的计数

    pd.Series(topK).value_counts().index[0] # 1
    
  • 将上述过程封装成一个函数

    def KNN(new_data,dataSet,k):
    '''
    函数功能:KNN分类器
    参数说明:
    new_data: 需要预测分类的数据集
    dataSet: 已知分类标签的数据集
    k: k-近邻算法参数,选择距离最小的k个点
    return:
    result: 分类结果
    '''
    from math import sqrt
    from collections import Counter
    import numpy as np
    import pandas as pd
    result = []
    distance = [sqrt(np.sum((x-new_data)**2)) for x in
    np.array(dataSet.iloc[:,0:2])]
    sort_dist = np.argsort(distance)
    topK = [dataSet.iloc[:,-1][i] for i in sort_dist[:k]]
    result.append(pd.Series(topK).value_counts().index[0])
    return result
    
    # 测试函数的运行结果
    new_data=np.array([12.03,4.1])
    k = 3
    KNN(new_data,wine_data,k) # [1]
    

05–python 实现总结及可视化

# 全部行都能输出
from IPython.core.interactiveshell import InteractiveShell

InteractiveShell.ast_node_interactivity = "all"
import pandas as pd
import matplotlib.pyplot as plt
import numpy as np

# 解决坐标轴刻度负号乱码
plt.rcParams['axes.unicode_minus'] = False
# 解决中文乱码问题
plt.rcParams['font.sans-serif'] = ['Simhei']
plt.style.use('ggplot')
# plt.figure(figsize=(2,3),dpi=720)

rowdata = {'颜色深度': [14.13, 13.2, 13.16, 14.27, 13.24, 12.07, 12.43, 11.79, 12.37, 12.04],
           '酒精浓度': [5.64, 4.28, 5.68, 4.80, 4.22, 2.76, 3.94, 3.1, 2.12, 2.6],
           '品种': [0, 0, 0, 0, 0, 1, 1, 1, 1, 1]}
# 0 代表 “黑皮诺”,1 代表 “赤霞珠”
wine_data = pd.DataFrame(rowdata)
print(wine_data)

X = np.array(wine_data.iloc[:, 0:2])  # 我们把特征(酒的属性)放在X
y = np.array(wine_data.iloc[:, -1])  # 把标签(酒的类别)放在Y
# 探索数据,假如我们给出新数据[12.03,4.1] ,你能猜出这杯红酒是什么类别么?
new_data = np.array([12.03, 4.1])
plt.scatter(X[y == 1, 0], X[y == 1, 1], color='red', label='赤霞珠')  # 画出标签y为1的、关于“赤霞珠”的散点
plt.scatter(X[y == 0, 0], X[y == 0, 1], color='purple', label='黑皮诺')  # 画出标签y为0的、关于“黑皮诺”的散点
plt.scatter(new_data[0], new_data[1], color='yellow')  # 新数据点
print(new_data)
plt.xlabel('酒精浓度')
plt.ylabel('颜色深度')
plt.legend(loc='lower right')
plt.savefig('葡萄酒样本.png')
plt.show()

from math import sqrt

distance = [sqrt(np.sum((x - new_data) ** 2)) for x in X]
print(distance)

# 从近到远排序后的原数据点
sort_dist = np.argsort(distance)
print('sort_dist:\n', sort_dist)

k = 3
# 找出离新数据最近的3个点
topK = [y[i] for i in sort_dist[:k]]
print(topK)  # [1,1,0]

# Pandas Series 类似表格中的一个列(column),类似于一维数组,可以保存任何数据类型
# 找出其中数量最多的值
print(pd.Series(topK).value_counts().index[0])  # 1


def KNN(new_data, dataSet, k):
    '''
    函数功能:KNN分类器
    参数说明:
    new_data: 需要预测分类的数据集
    dataSet: 已知分类标签的数据集
    k: k-近邻算法参数,选择距离最小的k个点
    return:
    result: 分类结果
    '''
    from math import sqrt
    from collections import Counter
    import numpy as np
    import pandas as pd
    result = []
    distance = [sqrt(np.sum((x - new_data) ** 2)) for x in
                np.array(dataSet.iloc[:, 0:len(dataSet.columns) - 2])]
    sort_dist = np.argsort(distance)
    topK = [dataSet.iloc[:, -1][i] for i in sort_dist[:k]]
    result.append(pd.Series(topK).value_counts().index[0])
    return result


# 测试函数的运行结果
new_data = np.array([12.03, 4.1])
k = 3
print(KNN(new_data, wine_data, k))  # [1]

06–使用 sklearn 实现


  • 案例一:红酒

    from sklearn.neighbors import KNeighborsClassifier
    # 0 代表 “黑皮诺”,1 代表 “赤霞珠”
    clf = KNeighborsClassifier(n_neighbors = 3)
    clf = clf.fit(wine_data.iloc[:,0:2], wine_data.iloc[:,-1])
    result = clf.predict([[12.8,4.1]]) # 返回预测的标签
    result # array([0])
    
    # 对模型进行一个评估,接口score返回预测的准确率
    score = clf.score([[12.8,4.1]],[0])
    score # 1.0
    
    clf.predict_proba([[12.8,4.1]])  # array([[0.66666667, 0.33333333]])
    #输出数据[12.8,4.1]为标签0的概率(0.666...),以及标签为1的概率(0.333...)
    

    .py

    from sklearn.neighbors import KNeighborsClassifier
    import pandas as pd
    import numpy as np
    
    rowdata = {'颜色深度': [14.13, 13.2, 13.16, 14.27, 13.24, 12.07, 12.43, 11.79, 12.37, 12.04],
              '酒精浓度': [5.64, 4.28, 5.68, 4.80, 4.22, 2.76, 3.94, 3.1, 2.12, 2.6],
              '品种': [0, 0, 0, 0, 0, 1, 1, 1, 1, 1]}
    # 0 代表 “黑皮诺”,1 代表 “赤霞珠”
    wine_data = pd.DataFrame(rowdata)
    
    clf = KNeighborsClassifier(n_neighbors=3)  # n_neighbors默认5
    # 拟合(训练)
    clf = clf.fit(wine_data.iloc[:, 0:2], wine_data.iloc[:, -1])
    # 预测
    res = clf.predict([[12.8, 4.1]])
    print(res)  # [0]
    
    # 对模型进行一个评估,接口score返回预测的准确率
    score = clf.score([[12.8, 4.1]], [0])
    print(score)  # 1.0
    
    proba = clf.predict_proba([[12.8, 4.1]])
    print(proba)  # array([[0.66666667, 0.33333333]])
    # 输出数据[12.8,4.1]为标签0的概率(0.666...),以及标签为1的概率(0.333...)
    
    # 生成10个随机点
    # numpy.random.normal(loc=0.0, scale=1.0, size=None)
    # 从正态(高斯)分布中抽取随机样本。
    # loc: 分布的均值(中心)
    # scale: 分布的标准差(宽度)
    # size: 输出值的维度
    a = np.random.normal(11, 2, (10, 1))
    b = np.random.normal(5, 1, (10, 1))
    # print(a, b)
    # 拼接(列)
    new_data = np.concatenate([a, b], axis=1)
    print(new_data)
    
    # 预测
    print(clf.predict(new_data))
    # 设实际的红酒类型
    y_new = np.array([1, 0, 1, 0, 0, 1, 1, 0, 0, 1])
    
    score = clf.score(new_data, y_new)
    print(score)
    
    proba = clf.predict_proba(new_data)
    print(proba)  # 左列是标签为0的概率,右列是标签为1的概率
    
  • 案例二:乳腺癌

    from sklearn.neighbors import KNeighborsClassifier
    from sklearn.datasets import load_breast_cancer
    from sklearn.model_selection import train_test_split
    import pandas as pd
    import numpy as np
    # 读取数据集
    data = load_breast_cancer()
    # DateFrame格式显示
    X = data.data
    y = data.target
    name = ['平均半径','平均纹理','平均周长','平均面积',
            '平均光滑度','平均紧凑度','平均凹度',
            '平均凹点','平均对称','平均分形维数',
            '半径误差','纹理误差','周长误差','面积误差',
            '平滑度误差','紧凑度误差','凹度误差',
            '凹点误差','对称误差',
            '分形维数误差','最差半径','最差纹理',
            '最差的边界','最差的区域','最差的平滑度',
            '最差的紧凑性','最差的凹陷','最差的凹点',
            '最差的对称性','最差的分形维数','患病否']
    data=np.concatenate((X,y.reshape(-1,1)),axis=1)
    table=pd.DataFrame(data=data,columns=name)
    table.head()
    
    # 划分训练集和测试集 #30%数据作为训练集
    Xtrain,Xtest,Ytrain,Ytest = train_test_split(X,y,test_size=0.2,random_state=420)
    # 建立模型&评估模型
    clf = KNeighborsClassifier(n_neighbors=4)
    
    # 建立分类器
    clf = clf.fit(Xtrain,Ytrain)
    score = clf.score(Xtest,Ytest)
    score # 0.9210526315789473
    
    #查找点的K邻居。返回每个点的邻居的与之的距离和索引值。
    clf.kneighbors(Xtest[[20,30],:],return_distance=True)
    '''
    (array([[35.70015941, 42.02374599, 81.82147557, 83.06271326],
    [11.81126721, 14.5871725 , 17.4734004 , 18.94892695]]),
    array([[112, 221, 303, 263], [268, 162, 42, 134]], dtype=int64))
    '''
    
    from sklearn.neighbors import KNeighborsClassifier
    from sklearn.datasets import load_breast_cancer
    from sklearn.model_selection import train_test_split
    import pandas as pd
    import numpy as np
    
    # 读取数据集
    data = load_breast_cancer()
    # DateFrame格式显示
    X = data.data
    y = data.target
    name = ['平均半径', '平均纹理', '平均周长', '平均面积',
            '平均光滑度', '平均紧凑度', '平均凹度',
            '平均凹点', '平均对称', '平均分形维数',
            '半径误差', '纹理误差', '周长误差', '面积误差',
            '平滑度误差', '紧凑度误差', '凹度误差',
            '凹点误差', '对称误差',
            '分形维数误差', '最差半径', '最差纹理',
            '最差的边界', '最差的区域', '最差的平滑度',
            '最差的紧凑性', '最差的凹陷', '最差的凹点',
            '最差的对称性', '最差的分形维数', '患病否']
    # y.reshape(-1,1) -> -1自动推导,1则是1列,作为目标列
    # axis=1,按列拼接
    data = np.concatenate((X, y.reshape(-1, 1)), axis=1)
    table = pd.DataFrame(data=data, columns=name)
    print('head:\n', table.head())
    
    # 划分训练集和测试集 #30%数据作为训练集
    # random_state类似于随机种子
    Xtrain, Xtest, Ytrain, Ytest = train_test_split(X, y, test_size=0.2, random_state=420)
    # 建立模型&评估模型
    clf = KNeighborsClassifier(n_neighbors=4)
    
    # 建立分类器
    clf = clf.fit(Xtrain, Ytrain)
    score = clf.score(Xtest, Ytest)
    print('score:\n', score)  # 0.9210526315789473
    
    # 查找点的K邻居。返回 每个点的邻居 的 与之的距离和索引值。
    res = clf.kneighbors(Xtest[[20, 30], :], return_distance=True)
    print('res:\n', res)
    '''
    (array([[35.70015941, 42.02374599, 81.82147557, 83.06271326],
            [11.81126721, 14.5871725 , 17.4734004 , 18.94892695]]),
    array([[112, 221, 303, 263], [268, 162, 42, 134]], dtype=int64))
    '''
    

08–绘制学习曲线



  • 2.1.6.1 学习曲线

    那我们怎样选择一个最佳的 k 呢?在这里我们要使用机器学习中的神器:参数学习曲线。参数学习曲线是一条以不同的参数取值为横坐标,不同参数取值下的模型结果为纵坐标的曲线,我们往往选择模型表现最佳点的参数取值作为这个参数的取值。

    # 更换不同的n_neighbors参数的取值,观察结果的变化
    clf = KNeighborsClassifier(n_neighbors=7)
    clf = clf.fit(Xtrain,Ytrain)
    score = clf.score(Xtest,Ytest)
    score # 0.9385964912280702
    

    绘制学习曲线:

    import matplotlib.pyplot as plt
    
    score = [] # 得分列表
    krange = range(1, 20)
    for i in krange:
        # 使用不同的n_neighbors参数值
        clf = KNeighborsClassifier(n_neighbors=i)
        # 训练
        clf = clf.fit(Xtrain, Ytrain)
        # 记录得分
        score.append(clf.score(Xtest, Ytest))
    
    plt.plot(krange, score)
    plt.xticks(range(1, 20)) # x轴设置为1~20
    plt.show()
    

    究竟上图中 k 为多少的时候分数越高?

    score.index(max(score))+1 # 8
    

    但是这个时候会有个问题,如果随机划分的数据集变化的的话,得分最高的 k 值也会发生变化:

    Xtrain,Xtest,Ytrain,Ytest = train_test_split(X,y,test_size=0.2,random_state=421)
    score = []
    krange = range(1,20)
    for i in krange:
      clf = KNeighborsClassifier(n_neighbors=i)
      clf = clf.fit(Xtrain,Ytrain)
      score.append(clf.score(Xtest,Ytest))
    
    plt.plot(krange,score)
    plt.show()
    

09–交叉验证

  • 2.1.7.1 泛化能力

  • 2.1.7.2 K 折交叉验证

  • 2.1.7.3 带交叉验证的学习曲线

    from sklearn.model_selection import cross_val_score as CVS
    Xtrain,Xtest,Ytrain,Ytest = train_test_split(X,y,test_size=0.2,random_state=420)
    clf = KNeighborsClassifier(n_neighbors=8)
    cvresult = CVS(clf,Xtrain,Ytrain,cv=6) #训练集对折6次,一共6个预测率输出
    # array([0.92207792, 0.90789474, 0.97368421, 0.94736842, 0.93333333, 0.92 ])
    cvresult #每次交叉验证运行时估算器得分的数组
    
    # 均值:查看模型的平均效果
    cvresult.mean()
    # 方差:查看模型是否稳定
    cvresult.var()
    
    score = []
    var = []
    krange=range(1,20) # 设置不同的k值,从1到19都看看
    for i in krange:
      clf = KNeighborsClassifier(n_neighbors=i)
      cvresult = CVS(clf,Xtrain,Ytrain,cv=5)
      score.append(cvresult.mean()) # 每次交叉验证返回的得分数组,再求数组均值
      var.append(cvresult.var())
    
    plt.plot(krange,score,color='k')
    plt.plot(krange,np.array(score)+np.array(var)*2,c='red',linestyle='--')
    plt.plot(krange,np.array(score)-np.array(var)*2,c='red',linestyle='--')
    

11–归一化

  • 2.1.8.1 距离类模型归一化的要求

  • 2.1.8.2 先分数据集,再做归一化

  • 2.1.8.3 通过 python 实现

    data = [[-1,2],[-0.5,6],[0,10],[1,18]]
    data=pd.DataFrame(data)
    (data-np.min(data,axis=0))/(np.max(data,axis=0)-np.min(data,axis=0))
    
  • 2.1.8.4 通过 sklearn 实现

    from sklearn.preprocessing import MinMaxScaler as mms
    Xtrain,Xtest,Ytrain,Ytest=train_test_split(X,y,test_size=0.2,random_state=420)
    
    #归一化
    MMS_01=mms().fit(Xtrain) #求训练集最大/小值
    MMS_02=mms().fit(Xtest) #求测试集最大/小值
    
    #转换
    X_train=MMS_01.transform(Xtrain)
    X_test =MMS_02.transform(Xtest)
    
    score=[]
    var=[]
    
    for i in range(1,20):
      clf=KNeighborsClassifier(n_neighbors=i)
      cvresult=CVS(clf,X_train,Ytrain,cv=5) # 交叉验证的每次得分
      score.append(cvresult.mean())
      var.append(cvresult.var())
    
    plt.plot(krange,score,color="k")
    plt.plot(krange,np.array(score)+np.array(var)*2,c="red",linestyle="--")
    plt.plot(krange,np.array(score)-np.array(var)*2,c="red",linestyle="--")
    plt.show()
    
    score.index(max(score))+1 # 8
    


    clf=KNeighborsClassifier(n_neighbors=6,weights='distance').fit(X_train,Ytrain)
    score=clf.score(X_test,Ytest)
    score # 0.956140350877193
    

12–距离的惩罚

在样本很不均匀时可以使用,样本均匀时效果不是很明显

最近的k个点,就算最后几个点离得很远也在k个点里面,加入距离惩罚后,可以改善

for i in range(1, 20):
    clf = KNeighborsClassifier(n_neighbors=i, weights='distance')
    cvresult = CVS(clf, X_train, Ytrain, cv=5)  # 交叉验证的每次得分
    score.append(cvresult.mean())
    var.append(cvresult.var())

plt.plot(krange, score, color="k")
plt.plot(krange, np.array(score) + np.array(var) * 2, c="red", linestyle="--")
plt.plot(krange, np.array(score) - np.array(var) * 2, c="red", linestyle="--")
plt.show()

score.index(max(score))+1
print(score) # 6
clf=KNeighborsClassifier(n_neighbors=6,weights='distance').fit(X_train,Ytrain)
score=clf.score(X_test,Ytest)
score # 0.9473684210526315

2–任务二: 决策树

01–算法概述

  • 2.2.1 决策树模型

    • 2.2.1.1 决策树基本流程
    • 2.2.1.2 决策与条件概率分布


    • 2.2.1.3 学习算法

02–特征选择-信息熵

  • 香农熵的计算

    import numpy as np
    p=1/2
    -((p*np.log2(p))+(p*np.log2(p)))
    





  • 香农熵的代码实现

    row_data = {'是否陪伴': [0, 0, 0, 1, 1],
                '是否玩游戏': [1, 1, 0, 1, 1],
                '渣男': ['是', '是', '不是', '不是', '不是']}
    dataSet = pd.DataFrame(row_data)
    dataSet
    

    def calEnt(dataSet):
        n = dataSet.shape[0]  # 数据集总行数
        # [[不是, 3], [是, 2]]
        iset = dataSet.iloc[:, -1].value_counts()  # 标签的所有类别
        p = iset / n  # 每一类标签所占比
        ent = (-p * np.log2(p)).sum()  # 计算信息熵
        return ent
    
    # 计算全体数据的信息熵——根据标签列去进行计算
    # 0.9709505944546686
    calEnt(dataSet)
    


03–特征选择-信息增益




04–划分数据集

  • 数据集最佳切分函数
import numpy as np
import pandas as pd
row_data = {'是否陪伴': [0, 0, 0, 1, 1],
            '是否玩游戏': [1, 1, 0, 1, 1],
            '渣男': ['是', '是', '不是', '不是', '不是']}
dataSet = pd.DataFrame(row_data)
# 定义信息熵
def calEnt(dataSet):
    n = dataSet.shape[0]  # 数据集总行数
    iset = dataSet.iloc[:, -1].value_counts()  # 统计标签的所有类别
    p = iset / n  # 统计每一类标签所占比
    ent = (-p * np.log2(p)).sum()  # 计算信息熵
    return ent
# 选择最优的列进行切分
def bestSplit(dataSet):
    baseEnt = calEnt(dataSet)  # 计算原始熵
    bestGain = 0  # 初始化信息增益
    axis = -1  # 初始化最佳切分列,标签列
    for i in range(dataSet.shape[1] - 1):  # 对特征的每一列进行循环
        levels = dataSet.iloc[:, i].value_counts().index  # 提取出当前列的所有取值
        ents = 0  # 初始化子节点的信息熵
        for j in levels:  # 对当前列的每一个取值进行循环
            childSet = dataSet[dataSet.iloc[:, i] == j]  # 某一个子节点的dataframe
            ent = calEnt(childSet)  # 计算某一个子节点的信息熵
            ents += (childSet.shape[0] / dataSet.shape[0]) * ent  # 计算当前列的信息熵
        print('第{}列的信息熵为{}'.format(i, ents))
        infoGain = baseEnt - ents  # 计算当前列的信息增益
        print('第{}列的信息增益为{}\n'.format(i, infoGain))
        if (infoGain > bestGain):
            bestGain = infoGain  # 选择最大信息增益
            axis = i  # 最大信息增益所在列的索引
    print("第{}列为最优切分列".format(axis))
    return axis
print(bestSplit(dataSet))
  • 按照给定列切分数据集
def mySplit(dataSet, axis, value):
  """
  函数功能:按照给定的列划分数据集
  参数说明:
  dataSet:原始数据集
  axis:指定的列索引
  value:指定的属性值
  return:redataSet:按照指定列索引和属性值切分后的数据集
  """
  col = dataSet.columns[axis]
  redataSet = dataSet.loc[dataSet[col] == value, :].drop(col, axis=1)
  return redataSet
# 验证函数:以axis=0,value=1为例
print(mySplit(dataSet, 0, 1))

05–决策树生成(算法解析)

  • ID3 算法
row_data = {'是否陪伴': [0, 0, 0, 1, 1],
            '是否玩游戏': [1, 1, 0, 1, 1],
            '渣男': ['是', '是', '不是', '不是', '不是']}
dataSet = pd.DataFrame(row_data)
def createTree(dataSet):
    """
    函数功能:基于最大信息增益切分数据集,递归构建决策树
    参数说明:
    dataSet:原始数据集(最有一列是标签)
    return:myTree:字典形式的树
    """
    featlist = list(dataSet.columns)  # 提取出数据集所有的列
    # print(featlist) # ['是否陪伴', '是否玩游戏', '渣男']
    # 最后一列 -> [所有出现的取值:该取值的数量]
    classlist = dataSet.iloc[:, -1].value_counts()  # 获取最后一列类标签
    # 每个分支下的所有实例都具有相同的分类 || 程序遍历完所有划分数据集的属性
    # 判断最多标签数目是否等于数据集行数,或者数据集是否只有一列
    if classlist[0] == dataSet.shape[0] or dataSet.shape[1] == 1:
        return classlist.index[0]  # 如果是,返回类标签
    axis = bestSplit(dataSet)  # 确定出当前最佳切分列的索引
    bestfeat = featlist[axis]  # 获取该索引对应的特征
    myTree = {bestfeat: {}}  # 采用字典嵌套的方式存储树信息
    del featlist[axis]  # 删除当前特征
    valuelist = set(dataSet.iloc[:, axis])  # 提取最佳切分列所有属性值
    for value in valuelist:  # 对每一个属性值递归建树
        # mySplit([[1,1],[2,1],[0,0]],1,1) -> [1,2]
        # mySplit(数据集,第i列,value) 提取dataset中,第i列中,和value相等的值,组成新dataset
        myTree[bestfeat][value] = createTree(mySplit(dataSet, axis, value))
    return myTree

  #查看运行结果
  myTree = createTree(dataSet)
  # {'是否陪伴': {0: {'是否玩游戏': {0: '不是', 1: '是'}}, 1: '不是'}}
  print(myTree)

  • C4.5 算法



06–拟合度优化(CART 算法)

  • 剪枝

  • CART 算法



  • 测试集和验证集

07–使用 sklearn 生成决策树

  • 参数 CRITERION

  • 初步建模

    import pandas as pd
    import numpy as np
    import matplotlib.pyplot as plt
    # %matplotlib inline
    
    from sklearn import tree
    from sklearn.datasets import load_wine
    from sklearn.model_selection import train_test_split
    
    plt.rcParams['font.sans-serif'] = ['Simhei']
    plt.rcParams['axes.unicode_minus'] = False
    
  • 探索数据

    wine = load_wine()
    print('wine.data.shape:\n', wine.data.shape)
    print('wine.target:\n', wine.target)
    
    # 将data(特征)和target(结果),按列拼接
    wine_pd = pd.concat([pd.DataFrame(wine.data), pd.DataFrame(wine.target)], axis=1).head()
    # wine.feature_names.append("result")
    wine.feature_names = ['酒精', '苹果酸', '灰', '灰的碱性', '镁', '总酚',
                          '类黄酮', '非黄烷类酚类', '花青素', '颜色强度',
                          '色调', 'od280/od315 稀释葡萄酒', '脯氨酸', 'result']
    wine_pd.columns = wine.feature_names
    print('wine_pd:\n', wine_pd)
    print('wine_pd.info:\n',wine_pd.info())
    
    # 划分数据集
    # random_state: 随机种子
    Xtrain, Xtest, Ytrain, ytest = train_test_split(wine.data, wine.target, test_size=0.3, random_state=420)
    print('xtrain.shape:\n', Xtrain.shape)
    print('xtest.shape:\n', Xtest.shape)
    
  • 建立模型

    # 建立模型
    clf = tree.DecisionTreeClassifier(criterion="gini")  # 使用基尼系数计算不纯度(熵越高,不纯度越高,决策树要让不纯度降低)
    clf = clf.fit(Xtrain, Ytrain)
    # 0.9444444444444444
    print(clf.score(Xtest, ytest))  # 返回预测的准确度
    
  • 画出一棵树

    同时,我们可以利用 Graphviz 模块导出决策树模型,第一次使用 Graphviz 之前需要对其进行安装(官网下安装包,然后安装并配置环境变量), 若是使用从 pip 进行的 Python 包管理,则可直接在命令⾏界⾯中利用下述指令进行安装: pip install graphviz

    import matplotlib.pyplot as plt
    
    feature_name = ['酒精', '苹果酸', '灰', '灰的碱性', '镁', '总酚',
                    '类黄酮', '非黄烷类酚类', '花青素', '颜色强度',
                    '色调', 'od280/od315 稀释葡萄酒', '脯氨酸']
    import graphviz
    
    print(graphviz.__version__)
    
    dot_data = tree.export_graphviz(clf,
                                    out_file=None,
                                    feature_names=feature_name,
                                    class_names=["琴酒", "雪莉", "贝尔摩德"],
                                    filled=True,
                                    rounded=True)
    graph = graphviz.Source(dot_data, filename='决策树.pdf')
    graph
    

08–探索决策树属性(pdf 生成)

  • pdf 生成

    dot_data = tree.export_graphviz(clf,
                                    out_file=None,
                                    # 将该py文件设置为utf-8格式
                                    # 然后设置字体为仿宋,就可以解决pdf中文乱码
                                    fontname="FangSong",
                                    feature_names=feature_name,
                                    class_names=["琴酒", "雪莉", "贝尔摩德"],
                                    filled=True,
                                    rounded=True)
    graph = graphviz.Source(dot_data)
    print(graph)
    
    graph.render('wine')
    

    探索决策树属性

  • clf.feature_importances

    clf.feature_importances_
    [*zip(feature_name,clf.feature_importances_)]
    
  • clf.apply

  • clf.tree_.node_count

  • clf.tree_.feature

09–防止过拟合(剪枝参数)

  • random_state

  • splitter

  • 剪枝参数

    • max_depth

    • min_samples_leaf

    • min_samples_split

    • max_features

    • min_impurity_decrease

    • 确认最优的剪枝参数

      test = []
      # 如果多个参数都要调整,就需要多层for循环,怎么办? -> 网络搜索
      for i in range(10):
          clf = tree.DecisionTreeClassifier(max_depth=i + 1,  # 最大深度
                                            criterion="entropy",
                                            random_state=30,
                                            # min_samples_leaf=5, # 子节点包含样本最小个数(父节点)
                                            # min_samples_split=20 ,
                                            splitter="random")
          clf = clf.fit(Xtrain, Ytrain)
          score = clf.score(Xtest, ytest)  # 记录下不同 max_depth 下模型在测试集分数
          test.append(score)
      
      plt.plot(range(1, 11), test, color="red", label="学习曲线")
      plt.ylabel("socre")
      plt.xlabel("max_depth")
      plt.legend()
      plt.show()
      


10–分类模型评估指标(class_weight)

  • class_weight
import numpy as np
import matplotlib.pyplot as plt
from sklearn.tree import DecisionTreeClassifier
from sklearn.model_selection import train_test_split
from sklearn.datasets import make_blobs  # 聚类产生数据集的方法

class_1 = 1000  # 类别1,1000个
class_2 = 100  # 类别2,100个
centers = [[0, 0], [2.0, 2.0]]  # 两个类别的中心点
clusters_std = [2.5, 0.5]  # 两个类别的方差

X, y = make_blobs(n_samples=[class_1, class_2],
                  centers=centers,
                  cluster_std=clusters_std,
                  random_state=420,
                  shuffle=False)
plt.scatter(X[:, 0], X[:, 1], c=y, cmap='rainbow', s=10)
plt.show()

# 划分数据集
Xtrain, Xtest, Ytrain, Ytest = train_test_split(X, y, test_size=0.2, random_state=420)

# 不设定class_weight
clf_1 = DecisionTreeClassifier()
clf_1.fit(Xtrain, Ytrain)

# 设定class_weight
clf_2 = DecisionTreeClassifier(class_weight='balanced')
clf_2.fit(Xtrain, Ytrain)

# 0.8954545454545455
print('clf1.score:\n', clf_1.score(Xtest, Ytest))
# 0.9045454545454545
print('clf2.score:\n', clf_2.score(Xtest, Ytest))

11–分类模型评估指标(混淆矩阵)









# PART2 混淆矩阵
from sklearn import metrics

# 样本平衡前
predict = metrics.confusion_matrix(Ytest, clf_1.predict(Xtest))
print('predict:\n', predict)
# 样本平衡后
predict = metrics.confusion_matrix(Ytest, clf_2.predict(Xtest))
print('predict:\n', predict)

# 精准率 -> 精确度是” 将多数类判错后所需付出成本的衡量’’,越高越好
# 精确度越低,意味着 01 比重很大,则代表你的模型对多数类 0 误判率越高,误伤了过多的多数类。
pScore = metrics.precision_score(Ytest, clf_1.predict(Xtest))
print('pScore:\n', pScore)  # 0.6363636363636364
pScore = metrics.precision_score(Ytest, clf_2.predict(Xtest))
print('pScore:\n', pScore)  # 0.6538461538461539

# 召回率 -> 召回率越高,代表我们尽量捕捉出了越多的少数类
rScore = metrics.recall_score(Ytest, clf_1.predict(Xtest))
print('rScore:\n', rScore)  # 0.4827586206896552
rScore = metrics.recall_score(Ytest, clf_2.predict(Xtest))
print('rScore:\n', rScore)  # 0.5862068965517241

# F值 -> 取值0~1,越高越好
# 为了同时兼顾精确度和召回率,用两者的调和平均数作为考量两者平衡的综合性指标,称之为F1 measure
f1Score = metrics.f1_score(Ytest, clf_1.predict(Xtest))
print('f1Score:\n', f1Score)  # 0.56
f1Score = metrics.f1_score(Ytest, clf_2.predict(Xtest))
print('f1Score:\n', f1Score)  # 0.6296296296296295

总结


3–任务三: 线性回归

01–基础原理(python 实现)











import numpy as np
import pandas as pd
import matplotlib.pyplot as plt

# 解决报错
'''
MatplotlibDeprecationWarning: Support for FigureCanvases without a required_interactive_framework
attribute was deprecated in Matplotlib 3.6 and will be removed two minor releases later.
'''
plt.switch_backend('TkAgg')
# plt.switch_backend('WebAgg')
# plt.switch_backend('QtAgg')

# 随机种子
np.random.seed(420)

# 生成横坐标
x = np.random.rand(50) * 10  # 50个点 -> 取值范围[0,10]
print('x:\n', x[:10])

# y = 2x-5
y = 2 * x - 5
# 添加扰动项
y += np.random.randn(50)  # 生成50个正态分布下的随机数
print('y:\n', y[:10])

plt.plot(x, y, 'o')
plt.show()

from sklearn.linear_model import LinearRegression

# 实例化
model = LinearRegression(fit_intercept=True)

# 扩展维度,sklearn不接受1维的数据
# Reshape your data either using array.reshape(-1, 1)
# if your data has a single feature or array.reshape(1, -1) if it contains a single sample.
x = x.reshape(-1, 1)

# 训练模型
model.fit(x, y)
# coef_: 斜率
print('coef:\n', model.coef_)  # [1.93715154]
# intercept_: 截距(y=kx+b中的b)
print('intercept_:\n', model.intercept_)  # -4.8841609114156785

# 绘制拟合好的直线

# 生成绘制直线的横坐标
xfit = np.linspace(0, 10, 100)  # 从0到10, 生成100个
print('xfit:\n', xfit[:10])
xfit = xfit.reshape(-1, 1)

# 预测
yfit = model.predict(xfit)
print('yfit:\n', yfit[:10])

# 画出点的直线
plt.plot(xfit,yfit)
# 画出原来训练集的点
plt.plot(x,y,'o')
plt.show()

多元线性回归 Python 实现

  • 利用矩阵乘法编写回归算法
    多元线性回归的执行函数编写并不复杂,主要涉及大量的矩阵运算,需要借助 Numpy 中的矩阵数据格式来完成。首先执行标准化导入

    import numpy as np
    import pandas as pd
    import matplotlib.pyplot as plt
    

    回顾可能用到的矩阵运算相关知识:

    • 矩阵创建

      a = np.array([[1, 2], [3, 4]])
      m = np.mat(a)  # NumPy中创建矩阵需要使⽤mat函数,该函数需要输⼊⼆维数组
      print('matrix:\n', m)
      
    • 矩阵运算
      当然,定义矩阵对象主要是为了能够执行矩阵运算,Numpy 中有个 linalg 库专门给矩阵对象提供计算方法,下面简答单回归常用矩阵运算

      # 矩阵转置
      print('m.T:\n', m.T)
      # 矩阵乘法
      print('m * m:\n', m * m)
      # 计算矩阵行列式
      print('np.linalg.det(m):\n', np.linalg.det(m))
      # 求逆矩阵
      print('m.I:\n', m.I)
      

      然后编写线性回归函数,同理,我们假设输入数据集为 DataFrame,且最后一列为标签值。

      # 线性回归函数
      def standRegres(dataSet):
          xMat = np.mat(dataSet.iloc[:, :-1].values)  # 提取特征
          yMat = np.mat(dataSet.iloc[:, -1].values).T  # 提取标签
          xTx = xMat.T * xMat
          if np.linalg.det(xTx) == 0:
              print('This matrix is singular,cannot do inverse')  # 行列式为0,则该矩阵为奇异矩阵,无法求解逆矩阵
              return
      
          ws = xTx.I * (xMat.T * yMat)
          return ws
      

      这里需要提前判断 xTx 是否是满秩矩阵。若不满秩,则无法对其进行求逆矩阵的操作。定义完函数后,即可测试运行效果,此处我们建立线性随机数进行多元线性回归方程拟合。这里需要注意的是,当使用矩阵分解来求解多元线性回归时,必须添加一列全为 1 的列,用于表征线性方程截距

      rng = np.random.RandomState(1)  # 设置随机种子
      x = 5 * rng.rand(100)  # 100个[0,5)的随机数
      y = 2 * x - 5 + rng.randn(100)  # 真实规律的标签取值
      X = pd.DataFrame(x)
      Y = pd.DataFrame(y)
      ex = pd.DataFrame(np.ones([100, 1]))  # 添加一列权威1的列,表示截距
      data = pd.concat([ex, X, Y], axis=1)
      

      数据满足基本的建模要求,然后执行函数运算:

      ws = standRegres(data)
      print('ws', ws)
      

      返回结果即为各列特征权重,其中数据集第一列值均为 1,因此返回结果的第一个分量表示截距。然后可用可视化图形展示模型拟合效果

      yhat = data.iloc[:,:-1].values*ws # 预测标签值
      plt.plot(data.iloc[:,1],data.iloc[:,2],'o') #原始数据点
      plt.plot(data.iloc[:,1],yhat) # 拟合直线
      

  • 回顾算法评估指标



y = data.iloc[:, -1].values
yhat = yhat.flatten()
SSE = np.power(yhat - y, 2).sum()
print('SSE:\n', SSE)

def sseCal(dataSet, regres):
  n = dataSet.shape[0]
  y = dataSet.iloc[:, -1].values
  ws = regres(dataSet)
  yhat = dataSet.iloc[:, :-1].values * ws
  yhat = yhat.flatten()
  SSE = np.power(yhat - y, 2).sum()
  return SSE


SSE = sseCal(data, standRegres)
print('SSE:\n', SSE) 
 
sse = sseCal(data, standRegres)
y = data.iloc[:, -1].values
sst = np.power(y - y.mean(), 2).sum()
print(1 - sse / sst)


def rSquare(dataSet, regres):
    sse = sseCal(dataSet, regres)
    y = dataSet.iloc[:, -1].values
    sst = np.power(y - y.mean(), 2).sum()
    return 1 - sse / sst


res = rSquare(data, standRegres)
print('rSquare:\n', res)

02–房价预测(sklearn 实现)

一般线性回归通过看 MSE(平均残差)和 R^2(判定系数)来判断拟合程度

from sklearn.linear_model import LinearRegression
from sklearn.model_selection import train_test_split, cross_val_score
from sklearn.datasets import fetch_california_housing  # 加利福尼亚房价数据集
import pandas as pd

# 下载数据
housevalue = fetch_california_housing()

# 特征解释
# MedInc:该街区住户的收入中位数
# HouseAge:该街区房屋使用年代的中位数
# AveRooms:该街区平均的房间数目
# AveBedrms:该街区平均的卧室数目
# Population:街区人口
# AveOccup:平均入住率
# Latitude:街区的纬度
# Longitude:街区的经度
print('feature_names:\n', housevalue.feature_names)

# 将数据转成DataFrame
X = pd.DataFrame(housevalue.data, columns=housevalue.feature_names)
print('x:\n', X[:5])

y = housevalue.target
print('y:\n', y[:5])

# 拆分数据集
Xtrain, Xtest, Ytrain, Ytest = train_test_split(X, y, test_size=0.3, random_state=420)

# 线性回归建模
model = LinearRegression()
# 拟合(训练)
model.fit(Xtrain, Ytrain)

# 模型评估
# MSE均方误差 -> 越小越好
from sklearn.metrics import mean_squared_error

# 对训练集做预测
y_pred = model.predict(Xtrain)

# 真实值和预测值对比
mse = mean_squared_error(Ytrain, y_pred)
# 0.52185226625331
print('mse:\n', mse)

# 对测试集做预测
y_test_pred = model.predict(Xtest)

# 真实值和预测值对比
mse = mean_squared_error(Ytest, y_test_pred)
# 0.5309012639324568
print('mse:\n', mse)

03–模型评估(sklearn 实现)

# 交叉验证,使用MSE指标
# neg_mean_squared_error -> 负的均方误差
cvs = cross_val_score(model, Xtrain, Ytrain, cv=10, scoring='neg_mean_squared_error')
print('cross_val_score(MSE):\n', cvs)
print('cross_val_score(MSE).mean():\n', cvs.mean())  # -0.5251459182173356

# MAE绝对均值误差(和MSE差不多,选一个用就行)
from sklearn.metrics import mean_absolute_error

mae = mean_absolute_error(Ytrain, y_pred)
# 0.5309427617356033
print('mae:\n', mae)

# 交叉验证,使用MAE指标
# neg_mean_absolute_error -> 负的绝对均方误差
cvs = cross_val_score(model, Xtrain, Ytrain, cv=10, scoring='neg_mean_absolute_error')
print('cross_val_score(MAE):\n', cvs)
print('cross_val_score(MAE).mean():\n', cvs.mean())  # -0.531393157638884

# R^2 -> 方差,衡量数据集包含多少信息量 -> 越接近1拟合效果越好
from sklearn.metrics import r2_score

r2Score = r2_score(Ytrain, y_pred)
print('r2Score:\n', r2Score)  # 0.6067440341875014

r2Score = r2_score(Ytest, y_test_pred)
print('r2Score:\n', r2Score)  # 0.6043668160178819

# 默认score就是用r2
score = model.score(Xtrain, Ytrain)
print('score:\n', score)  # 0.6067440341875014
score = model.score(Xtest, Ytest)
print('score:\n', score)  # 0.6043668160178819

# 交叉验证(R2)
cvs = cross_val_score(model, Xtrain, Ytrain, cv=10, scoring='r2')
print('cross_val_score(R2):\n', cvs)
print('cross_val_score(R2).mean():\n', cvs.mean())  # 0.6039238235546336

# 查看模型系数(训练计算出的w)
print('coef_:\n', model.coef_)
# 截距b
print('intercept_:\n', model.intercept_)  # -36.256893229203854

zipXCoef = list(zip(X.columns, model.coef_))
print('zipXCoef:\n', zipXCoef)

04–拟合图像(sklearn 实现)

# 数据集标准化(归一化)后再训练
from sklearn.preprocessing import StandardScaler

std = StandardScaler()
# 训练集标准化
X_train_std = std.fit_transform(Xtrain)

print('X_train_std:\n', X_train_std[:5])

model2 = LinearRegression()
model2.fit(X_train_std, Ytrain)
score = model2.score(X_train_std, Ytrain)
print('score:\n', score)  # 0.6067440341875014

# 绘制拟合图像
# 因为是无序的,所以点是乱的
plt.scatter(range(len(Ytest)), Ytest, s=2)
plt.show()
# 排序后
plt.scatter(range(len(Ytest)), sorted(Ytest), s=2)
plt.show()

# 预测值和真实值如何匹配
print('Ytest:\n', Ytest[:5])
print('y_test_pred:\n', y_test_pred[:5])
# 将测试值排序得到索引序列
Ytest_ids = np.argsort(Ytest)
print('Ytest_ids:\n', Ytest_ids[:5])
# 可以用id访问
print('Ytest:\n', Ytest[2477])  # 0.14999
# 预测值和真实值关联
print(y_test_pred[np.argsort(Ytest)][:5])

# 排序好的数据进行绘图
plt.scatter(range(len(Ytest)), sorted(Ytest), s=2, label='True')
plt.scatter(range(len(Ytest)), y_test_pred[np.argsort(Ytest)], s=2, c='r', label='True', alpha=0.3)
plt.show()

05–多重共线性(sklearn 实现)








import matplotlib.pyplot as plt

plt.switch_backend('TkAgg')
from sklearn.linear_model import LinearRegression
from sklearn.datasets import fetch_california_housing  # 加利福尼亚房价数据集
import pandas as pd

# 下载数据
housevalue = fetch_california_housing()

# 特征解释
# MedInc:该街区住户的收入中位数
# HouseAge:该街区房屋使用年代的中位数
# AveRooms:该街区平均的房间数目
# AveBedrms:该街区平均的卧室数目
# Population:街区人口
# AveOccup:平均入住率
# Latitude:街区的纬度
# Longitude:街区的经度
print('feature_names:\n', housevalue.feature_names)

# 将数据转成DataFrame
X = pd.DataFrame(housevalue.data, columns=housevalue.feature_names)
print('x:\n', X[:5])

X.columns = [
    '该街区住户的收入中位数', '该街区房屋使用年代的中位数', '该街区平均的房间数目',
    '该街区平均的卧室数目', '街区人口', '平均入住率', '街区的纬度', '街区的经度'
]
print('x:\n', X[:5])

y = housevalue.target
print('y:\n', y[:5])

import sklearn
from sklearn.preprocessing import PolynomialFeatures

print(sklearn.__version__)  # 1.2.2

# degree:度数,决定多项式的次数
poly = PolynomialFeatures(degree=2)
poly.fit(X, y)
p_features = poly.get_feature_names_out(X.columns)
# print('get_feature_names:\n', poly.get_feature_names(X.columns))  # 可能是旧版或新版的api?
print('get_feature_names_out:\n', p_features)  # 通过多项式构造列

X_ = poly.transform(X)  # 多项式变化后
# print('X:\n', X_[:5])

model = LinearRegression()
model.fit(X_, y)  # 用转换后的数据进行训练
print('coef:\n', model.coef_)
print('zip:\n', [*zip(p_features, model.coef_)])

coeff = pd.DataFrame([p_features, model.coef_.tolist()]).T
print('coeff:\n', coeff)

# 变换前的模型的拟合效果
poly = PolynomialFeatures(degree=2)
poly.fit(X, y)
X_ = poly.transform(X)

model = LinearRegression()
model.fit(X, y)
# 0.606232685199805
print('score:\n', model.score(X, y))

model_poly = LinearRegression()
model.fit(X_, y)
# 0.6832976293317492
print('score:\n', model.score(X_, y))
  • 岭回归和 lasso









import numpy as np
import pandas as pd


# 线性回归函数
def standRegres(dataSet):
    xMat = np.mat(dataSet.iloc[:, :-1].values)  # 提取特征
    yMat = np.mat(dataSet.iloc[:, -1].values).T  # 提取标签
    xTx = xMat.T * xMat
    if np.linalg.det(xTx) == 0:
        print('This matrix is singular,cannot do inverse')  # 行列式为0,则该矩阵为奇异矩阵,无法求解逆矩阵
        return

    ws = xTx.I * (xMat.T * yMat)
    return ws


def sseCal(dataSet, regres):
    n = dataSet.shape[0]
    y = dataSet.iloc[:, -1].values
    ws = regres(dataSet)
    yhat = dataSet.iloc[:, :-1].values * ws
    yhat = yhat.flatten()
    SSE = np.power(yhat - y, 2).sum()

    return SSE


def rSquare(dataSet, regres):
    sse = sseCal(dataSet, regres)
    y = dataSet.iloc[:, -1].values
    sst = np.power(y - y.mean(), 2).sum()
    return 1 - sse / sst


def ridgeRegres(dataSet, lam=0.2):
    xMat = np.mat(dataSet.iloc[:, :-1].values)
    yMat = np.mat(dataSet.iloc[:, -1].values).T
    xTx = xMat.T * xMat
    denom = xTx + np.eye(xMat.shape[1]) * lam
    ws = denom.I * (xMat.T * yMat)
    return ws


aba = pd.read_csv('abalone.csv', header=None)
print('aba.head():\n', aba.head())

aba.iloc[:, 0] = 1
print('aba.head():\n', aba.head())

rws = ridgeRegres(aba)
print('rws:\n', rws)

standRegres(aba)

rSquare(aba, ridgeRegres)
rSquare(aba, standRegres)

from sklearn.linear_model import Ridge

ridge = Ridge(alpha=0.2)
ridge.fit(aba.iloc[:, :-1], aba.iloc[:, -1])

print('ridge.coef_:\n', ridge.coef_)  # 查看系数
print('ridge.intercept_:\n', ridge.intercept_)  # 查看截距

from sklearn.linear_model import RidgeCV

Ridge_ = RidgeCV(alphas=np.arange(1, 1001, 100),
                 scoring="r2",
                 store_cv_values=True  # ,cv=5
                 )
Ridge_.fit(aba.iloc[:, :-1], aba.iloc[:, -1])
# ⽆关交叉验证的岭回归结果
Ridge_.score(aba.iloc[:, :-1], aba.iloc[:, -1])
# 调⽤所有交叉验证的结果
print('Ridge_.cv_values_.shape:\n', Ridge_.cv_values_.shape)
# 进⾏平均后可以查看每个正则化系数取值下的交叉验证结果
Ridge_.cv_values_.mean(axis=0)
# 查看被选择出来的最佳正则化系数
print('Ridge_.alpha_:\n', Ridge_.alpha_)




4–任务四: 逻辑回归

01–基础原理




02–sklearn 实现





  • 逻辑回归的 Scikit-Learn 实现



# 导入数据(乳腺癌)
import numpy as np
import pandas as pd
from sklearn.datasets import load_breast_cancer
import matplotlib.pyplot as plt

X = load_breast_cancer().data
Y = load_breast_cancer().target

x_pd = pd.DataFrame(X)  # 可以考虑去量纲(标准化)
print('x:\n', x_pd[:3])

# 建模
from sklearn.linear_model import LogisticRegression as LR  # 逻辑回归
from sklearn.model_selection import train_test_split

# LR(
#     penalty='l2', # l2正则化---岭回归   l1正则化---lasso  默认l2
#     *,
#     dual=False,
#     tol=0.0001,
#     C=1.0,    # C越小表示惩罚力度越大,C越大惩罚力度越小
#     fit_intercept=True,
#     intercept_scaling=1,
#     class_weight=None,
#     random_state=None,
#     solver='lbfgs', # 梯度下降的方式
#     max_iter=100, # 梯度下降会有迭代次数
#     multi_class='auto',
#     verbose=0,
#     warm_start=False,
#     n_jobs=None,
#     l1_ratio=None,
# )

# liblinear -> 坐标下降法
model_l1 = LR(penalty='l1', solver='liblinear', C=0.5, max_iter=1000)
model_l1.fit(X, Y)
print('score:\n', model_l1.score(X, Y))  # 0.9578207381370826

model_l2 = LR(penalty='l2', solver='liblinear', C=0.5, max_iter=1000)
model_l2.fit(X, Y)
print('score:\n', model_l2.score(X, Y))  # 0.9560632688927944

# 剩下10个 -> l1正则化可以对特征进行筛选(重要的参数),防止过拟合
# 模型太复杂会把噪声学习进去(过拟合),当然,太简单会欠拟合
print('model_l1.coef_', model_l1.coef_)
print('model_l2.coef_', model_l2.coef_)

# 对每一行进行预测,每行预测结果加起来都为1
pred = model_l2.predict_proba(X)  # 0 1
print('predict_proba\n', pred)
print('predict_proba.sum:\n', pred.sum(axis=1)[:5])

03–绘制学习曲线 2

# 绘制学习曲线
Xtrain, Xtest, Ytrain, Ytest = train_test_split(X, Y, test_size=0.3, random_state=420)
# 查看C在L1和L2下训练集和测试集的表现
l1 = []
l2 = []

l1test = []
l2test = []

# 在0.05到1之间均匀地取20个数
for i in np.linspace(0.05, 1, 19):
    # 实例化模型
    lrl1 = LR(penalty='l1', solver='liblinear', C=i, max_iter=1000)
    lrl1.fit(Xtrain, Ytrain)

    lrl2 = LR(penalty='l2', solver='liblinear', C=i, max_iter=1000)
    lrl2.fit(Xtrain, Ytrain)

    # 记录训练集分数
    l1.append(lrl1.score(Xtrain, Ytrain))
    l2.append(lrl2.score(Xtrain, Ytrain))

    # 记录测试分数
    l1test.append(lrl1.score(Xtest, Ytest))
    l2test.append(lrl2.score(Xtest, Ytest))

# 画图
plt.switch_backend('TkAgg')
graph = [l1, l2, l1test, l2test]
color = ['green', 'black', 'lightgreen', 'gray']
label = ['L1', 'L2', 'L1test', 'L2test']

plt.figure(figsize=(6, 6))
for i in range(len(graph)):
    plt.plot(np.linspace(0.05, 1, 19), graph[i], color[i], label=label[i])
plt.legend(loc=4)  # 图例位置在哪?4表示右下角
plt.show()


04–利用网格搜索确定最优参数

  • 算法优化参数:solver
  • 梯度下降:重要参数 max_iter

  • 分类方式选参数




# 网格搜索-确认最优参数
from sklearn.model_selection import GridSearchCV  # 网络搜索

'''
在机器学习领域中,不同评价指标(即特征向量中的不同特征就是所述的不同评价指标)往往具有不同的量纲和量纲单位,
这样的情况会影响到数据分析的结果,为了消除指标之间的量纲影响,需要进行数据标准化处理,以解决数据指标之间的可比性。
'''
from sklearn.preprocessing import StandardScaler  # 标准化

data = pd.DataFrame(X, columns=load_breast_cancer().feature_names)
print('data:\n', data.head())
data['label'] = Y

# 划分数据集
Xtrain, Xtest, Ytrain, Ytest = train_test_split(X, Y, test_size=0.3, random_state=420)

# 对训练集和测试集做标准化--去量纲
Xstd = StandardScaler().fit(Xtrain)
Xtrain_std = Xstd.transform(Xtrain)
Xtest_std = Xstd.transform(Xtest)
# print('Xtrain_std:\n', Xtrain_std[:3])

# 在l2范式下,判断C和solver最优值
p = {
    'C': list(np.linspace(0.05, 1, 19)),
    'solver': ['liblinear', 'sag', 'newton-cg', 'lbfgs']
}

model = LR(penalty='l2', max_iter=10000)
'''
cv: 交叉验证参数,默认None,使用三折交叉验证。指定fold数量,默认为3,也可以是yield训练/测试数据的生成器。
'''
GS = GridSearchCV(model, p, cv=5)
GS.fit(Xtrain, Ytrain)
# 0.9673417721518988
print('GS.best_score_:\n', GS.best_score_)
# {'C': 0.3138888888888889, 'solver': 'newton-cg'}
print('GS.best_params_:\n', GS.best_params_)

# 注意: 除了liblinear以外的三种需要导数计算的solver不能使用l1正则化
# 将最优参数用于实例化模型,查看训练集和测试集下的分数
model = LR(penalty='l2', max_iter=10000, C=GS.best_params_['C'], solver=GS.best_params_['solver'])
model.fit(Xtrain, Ytrain)
# 0.9673366834170855
print('train score:\n', model.score(Xtrain, Ytrain))
# 0.9239766081871345
print('test score:\n', model.score(Xtest, Ytest))

第八阶段模块二

k-means

01–基础原理-拉勾教育

  • 无监督算法


  • k-means





python 实现

附件 1














import numpy as np
import pandas as pd
import matplotlib as mpl
import matplotlib.pyplot as plt

plt.switch_backend('TkAgg')

# %matplotlib inline

# 导入数据集
iris = pd.read_csv('iris.txt', header=None)
print('iris:\n', iris[:3])
# print(len(iris.columns))
# iris = iris.iloc[:, :len(iris.columns) - 1]
# print('iris:\n', iris[:3])


# 计算距离
def distEclud(arrA, arrB):
    # d = a-b
    d = arrA - arrB
    # sum(d^2)
    dist = np.sum(np.power(d, 2), axis=1)
    return dist


# 自动生成随机质心
def randCent(dataSet, k):
    n = dataSet.shape[1]
    # 取每一列的最大最小值
    data_max = dataSet.iloc[:,:n-1].max()
    data_min = dataSet.iloc[:,:n-1].min()
    # 均匀分布抽样
    # numpy.random.uniform(low,high,size)
    # 从一个均匀分布[low,high)中随机采样,注意定义域是左闭右开
    # size: 输出样本数目,为int或元组(tuple)类型,
    # 例如,size=(m,n,k), 则输出 m * n * k 个样本,缺省时输出1个值。
    data_cent = np.random.uniform(data_min, data_max, (k, n-1))
    return data_cent  # 质心


# 随机生成3个质心
iris_cent = randCent(iris, 3)

### ERROR
def kMeans(dataSet, k, distMeas=distEclud, createCent=randCent):  # iris为150*5
    m, n = dataSet.shape  # m是行数(数据量),n是列数iris为150*5
    # 下面生成的centroids,即第一个容器,后面用来存储最新更新的质心
    centroids = createCent(dataSet, k)  # centroids为3*4,用三个长度为4的一维数组记载3个质心
    # 第一次centroids是随机生成的
    # 这段生成的result_set,即第二个容器
    # result_set结构: [数据集, 该行到最近质心的距离, 本次迭代中最近质心编号,上次迭代中最近质心编号]
    clusterAssment = np.zeros((m, 3))  # clusterAssment为150*3的数组
    clusterAssment[:, 0] = np.inf  # np.inf为无穷大
    clusterAssment[:, 1: 3] = -1  # 此时clusterAssment为150*3
    result_set = pd.concat([dataSet, pd.DataFrame(clusterAssment)],
                           axis=1, ignore_index=True)  # result_set为150*8

    clusterChanged = True
    while clusterChanged:
        clusterChanged = False

        for i in range(m):  # 遍历result_set中每一行,一共m行
            # 小心,下面的n为5,而resulit_set的列数已经变成8
            dist = distMeas(dataSet.iloc[i, :n-1].values , centroids)  # 第i行与三个质心的距离,dist为3*1
            result_set.iloc[i, n] = dist.min()  # result_set[i,n]记录该行与3个质心的最小距离
            result_set.iloc[i, n + 1] = np.where(dist == dist.min())[0]  # result_set[i,n]记录最近质心的索引
            clusterChanged = not (result_set.iloc[:, -1] == result_set.iloc[:, -2]).all()
            # 只要result_set最后两列不完全相等,意味着本次for循环结束时,m行所有的新质心与上次while循环留下的不完全一样
        # 后果:clusterChanged为True,while继续循环

        # clusterChanged为True,则需要运行下面的if语句代码块,重置第一个容器centroids和第二个容器result_set
        if clusterChanged:
            cent_df = result_set.groupby(n + 1).mean()  # 按照列索引为n+1(质心索引)(第6列)进行分组求均值
            # 即:按照最新的簇分类,计算最新3个质心的位置
            centroids = cent_df.iloc[:, :n - 1].values  # 重置centroids,用最新质心位置,替换上次的。3*4
            result_set.iloc[:, -1] = result_set.iloc[:, -2]  # result_set最后一列,本次的簇分类编码,替换掉上次的
    return centroids, result_set


iris_cent, iris_result = kMeans(iris, 3)
print(iris_result.head())

sklearn 实现







from sklearn.datasets import make_blobs
import numpy as np
import pandas as pd
import matplotlib as mpl
import matplotlib.pyplot as plt

plt.switch_backend('TkAgg')

# 自己创建数据集
X, y = make_blobs(n_samples=500, n_features=2, centers=4, random_state=1)
plt.scatter(X[:, 0], X[:, 1], marker='o')  # 点的形状 ,s=8 #点的大小

# 查看分布
color = ["red", "pink", "orange", "gray"]
for i in range(4):
    plt.scatter(X[y == i, 0], X[y == i, 1],
                marker='o',  # 点的形状
                s=8,  # 点的大小
                c=color[i])
plt.show()

from sklearn.cluster import KMeans

cluster = KMeans(n_clusters=3, random_state=0)
cluster.fit(X)
y_pred = cluster.labels_
print('y_pred:\n', y_pred)  # 该属性使用得比较多

fit_pre = KMeans(n_clusters=3, random_state=0).fit_predict(X)
print((cluster.predict(X) == fit_pre).sum())
print((fit_pre == cluster.labels_).sum())

# 当我们数据量非常大的时候,为了提高模型学习效率,我们可以使用部分数据来帮助我们确认质心
# 剩下的数据的聚类结果,使用 predict 来调用
cluster_smallsub = KMeans(n_clusters=3, random_state=0).fit(X[:200])
sample_pred = cluster_smallsub.predict(X)
# 但这样的结果,肯定与直接 fit 全部数据会不一致。
# 有时候,当我们不要求那么精确,或者我们的数据量实在太大,那我们可以使用这样的方法
print(y_pred == sample_pred)

# 查看质心
centroid = cluster.cluster_centers_
print('centroid:\n', centroid)
print('centroid.shape:\n', centroid.shape)

# 查看总距离平方和
inertia = cluster.inertia_
# 1903.5607664611764
print('inertia:\n', inertia)

n_clusters = 4
cluster_ = KMeans(n_clusters=n_clusters, random_state=0).fit(X)
inertia = cluster_.inertia_
# 908.3855684760615
print('inertia:\n', inertia)

n_clusters = 5
cluster_ = KMeans(n_clusters=n_clusters, random_state=0).fit(X)
inertia_ = cluster_.inertia_
# 811.0841324482415
print('inertia:\n', inertia_)

n_clusters = 6
cluster_ = KMeans(n_clusters=n_clusters, random_state=0).fit(X)
inertia_ = cluster_.inertia_
# 733.1538350083081
print('inertia:\n', inertia_)

评估指标: 轮廓系数

















from sklearn.datasets import make_blobs
import numpy as np
import pandas as pd
import matplotlib as mpl
import matplotlib.pyplot as plt

plt.switch_backend('TkAgg')

# 自己创建数据集
X, y = make_blobs(n_samples=500, n_features=2, centers=4, random_state=1)
plt.scatter(X[:, 0], X[:, 1], marker='o')  # 点的形状 ,s=8 #点的大小

# 查看分布
color = ["red", "pink", "orange", "gray"]
for i in range(4):
    plt.scatter(X[y == i, 0], X[y == i, 1],
                marker='o',  # 点的形状
                s=8,  # 点的大小
                c=color[i])
plt.show()

from sklearn.cluster import KMeans

cluster = KMeans(n_clusters=3, random_state=0)
cluster.fit(X)
y_pred = cluster.labels_
print('y_pred:\n', y_pred)  # 该属性使用得比较多

fit_pre = KMeans(n_clusters=3, random_state=0).fit_predict(X)
print((cluster.predict(X) == fit_pre).sum())
print((fit_pre == cluster.labels_).sum())

# 当我们数据量非常大的时候,为了提高模型学习效率,我们可以使用部分数据来帮助我们确认质心
# 剩下的数据的聚类结果,使用 predict 来调用
cluster_smallsub = KMeans(n_clusters=3, random_state=0).fit(X[:200])
sample_pred = cluster_smallsub.predict(X)
# 但这样的结果,肯定与直接 fit 全部数据会不一致。
# 有时候,当我们不要求那么精确,或者我们的数据量实在太大,那我们可以使用这样的方法
print(y_pred == sample_pred)

# 查看质心
centroid = cluster.cluster_centers_
print('centroid:\n', centroid)
print('centroid.shape:\n', centroid.shape)

# 查看总距离平方和
inertia = cluster.inertia_
# 1903.5607664611764
print('inertia:\n', inertia)

n_clusters = 4
cluster_ = KMeans(n_clusters=n_clusters, random_state=0).fit(X)
inertia = cluster_.inertia_
# 908.3855684760615
print('inertia:\n', inertia)

n_clusters = 5
cluster_ = KMeans(n_clusters=n_clusters, random_state=0).fit(X)
inertia_ = cluster_.inertia_
# 811.0841324482415
print('inertia:\n', inertia_)

n_clusters = 6
cluster_ = KMeans(n_clusters=n_clusters, random_state=0).fit(X)
inertia_ = cluster_.inertia_
# 733.1538350083081
print('inertia:\n', inertia_)

# 评估指标: 轮廓系数
from sklearn.metrics import silhouette_score, silhouette_samples

# 计算所有样本的轮廓系数的均值
score = silhouette_score(X, y_pred)
# 0.5882004012129721
print('score:\n', score)
# 每个样本的轮廓系数
samples = silhouette_samples(X, y_pred)
print('samples:\n', samples[:5])

score = []

# 将K值从2到20进行实验
for i in range(2, 20):
    cluster = KMeans(n_clusters=i, random_state=0)
    cluster.fit(X)
    score.append(silhouette_score(X, cluster.labels_))

plt.plot(range(2, 20), score)
# 最高点的x=?画虚线
plt.axvline(pd.DataFrame(score).idxmax()[0] + 2, ls=':')
plt.show()

# 绘制轮廓系数分布图和聚类后的数据分布图来选择最佳n_clusters
from sklearn.cluster import KMeans
from sklearn.metrics import silhouette_samples, silhouette_score
import matplotlib.pyplot as plt
import matplotlib.cm as cm
import numpy as np

for i in range(2, 10, 2):  # 6个质心的聚合情况,分别画在6张图
    fig, (ax1, ax2) = plt.subplots(1, 2)  # 每张图有两幅子图
    fig.set_size_inches(18, 7)  # 设置大图尺寸
    # 给第一幅子图大小做限定
    ax1.set_xlim([-0.1, 1])
    ax1.set_ylim([0, X.shape[0] + (n_clusters + 1) * 10])

    # 生成模型、簇标签、轮廓系数均值,样本轮廓系数
    clusterer = KMeans(n_clusters=i, random_state=10).fit(X)  # 生产KMeans模型
    cluster_labels = clusterer.labels_  # 记录聚合结果的所有簇标签
    silhouette_avg = silhouette_score(X, cluster_labels)  # 全体样本的轮廓系数
    sample_silhouette_values = silhouette_samples(X, cluster_labels)  # 记录每个样本的轮廓系数
    print("簇数 =", i,
          "\n 轮廓系数均值:", silhouette_avg)

    y_lower = 10  # 为后面画图设定一个y轴最低范围

    for j in range(i):
        ith_cluster_silhouette_values = sample_silhouette_values[cluster_labels == j]  # 筛选留下簇j类样本的轮廓系数
        ith_cluster_silhouette_values.sort()  # 对上面的数组结果排序
        size_cluster_j = ith_cluster_silhouette_values.shape[0]  # size_cluster_i记录第i簇样本个数

        # 画图
        y_upper = y_lower + size_cluster_j  # 第j簇在y轴的范围上限
        color = cm.nipy_spectral(float(j) / i)  # 第j 簇设定颜色

        ax1.fill_betweenx(np.arange(y_lower, y_upper)  # 图形直角在y轴上
                          , ith_cluster_silhouette_values  # 簇j全部样本的轮廓系数,高度映射在x轴
                          , facecolor=color
                          , alpha=0.5)

        ax1.text(-0.05  # 添加簇的编号
                 , y_lower + 0.5 * size_cluster_j
                 , str(j));

        y_lower = y_upper + 10  # 下一簇的图显示的y轴坐标起点往上挪10个单位

    ax1.set_title("不同簇的轮廓图")
    ax1.set_xlabel("轮廓系数值")
    ax1.set_ylabel("簇类标签")
    ax1.axvline(x=silhouette_avg, color="red", linestyle="--")  # 全样本的轮廓系数
    ax1.set_yticks([])
    ax1.set_xticks([-0.1, 0, 0.2, 0.4, 0.6, 0.8, 1])

    # 接下来画出子图2的散点图
    colors = cm.nipy_spectral(cluster_labels.astype(float) / i)
    ax2.scatter(X[:, 0], X[:, 1], marker='o', s=8, c=colors)

    centers = clusterer.cluster_centers_  # 返回不同簇的质心坐标
    ax2.scatter(centers[:, 0], centers[:, 1], marker='x', c="red", s=200)

    ax2.set_title("簇群数据可视化")
    ax2.set_xlabel("第一特征的特征空间")
    ax2.set_ylabel("第二特征的特征空间")

    plt.suptitle(("样本数据的KMeans轮廓分析--簇数为:%d" % i),
                 fontsize=14, fontweight='bold')
    plt.show()

第八阶段模块三

1–任务一: 金融保险用户分类综合项目

01–业务背景












02–项目分析流程(1)









04–数据清洗-处理异常字段[2]

9. 一线互联网数据分析综合项目实战

10. 就业指导 + 简历指导


 上一篇
数学建模导论:基于Python语言(2022年秋季学期) 数学建模导论:基于Python语言(2022年秋季学期)
1. 函数极值与规划模型1.1 线性代数知识补充与线性规划引入 线性可行域:边界由直线组成 线性规划的目的是在围出的形状中寻找一个点,使得目标函数(3x+2y=0)的值最大 线性规划的应用 中学的线性规划
2023-08-14
下一篇 
nuxt3 教程 nuxt3 教程
什么是 Nuxt 根据 Vue 官网的说法 而 Nuxt 是由 Vue 官方团队开发的 SSR 框架 创建项目npx nuxi init todo 项目结构 创建完需要手动安装依赖 cd todo npm i # 启动
2023-08-11
  目录