学习scikit-learn

scikit-learn

网址:http://scikit-learn.org/stable/datasets/index.html#datasets

一、特征工程

特征工程或特征提取或特征发现是利用领域知识从原始数据(特性、属性、属性)的过程。其动机是利用这些额外的特征来提高机器学习过程的结果的质量,而不是只提供原始数据给机器学习过程。

数据和特征决定了机器学习的上限,而模型和算法只是逼近这个上限而已

特征工程包含

  • 特征抽取
  • 特征预处理
  • 特征降维

2.1 特征提取

将任意数据(如文本或图像)转换为可用于机器学习的数字特征

API :sklearn.feature_extraction

字典特征提取DictVectorizer

​ 对类别特征进行数值化、离散化

sklearn.feature_extraction.DictVectorizer(sparse=True,…)

  • DictVectorizer.fit_transform(X) X:字典或者包含字典的迭代器返回值:返回sparse矩阵
  • DictVectorizer.inverse_transform(X) X:array数组或者sparse矩阵 返回值:转换之前数据格式
  • DictVectorizer.get_feature_names() 返回类别名称

tips:参数sparse表示是否为稀疏矩阵、(特征离散化)

#字典特征抽取
def dict_demo():
    data = [{'city': '北京', 'temperature': 100}, {'city': '上海', 'temperature': 60}, {'city': '深圳', 'temperature': 30}]
    # 1、实例化一个转换器类
    transfer = DictVectorizer(sparse=False)
    # 2、调用fit_transform
    datanew=transfer.fit_transform(data)
    print("datanew 为: \n",datanew)
    print("特征名字:\n",transfer.get_feature_names_out())
    return None

结果采用的是”one-hot“编码

datanew 为: 
 [[  0.   1.   0. 100.]
 [  1.   0.   0.  60.]
 [  0.   0.   1.  30.]]
特征名字:
 ['city=上海' 'city=北京' 'city=深圳' 'temperature']
文本特征提取countvetorizer、TfidfVectorizer

​ 对文本特征进行数值化

sklearn.feature_extraction.text.CountVectorizer(stop_words=[]) 返回词频矩阵

常用方法

  • .fit_transform(X) X:文本或者包含文本字符串的可迭代对象 返回值:返回sparse矩阵
  • .inverse_transform(X) X:array数组或者sparse矩阵 返回值:转换之前数据格
  • .get_feature_names() 返回值:单词列表
def count_demo():  # 对文本进行特征抽取
    data = ["oh crazy i like like python", "omg i dislike python"]
    transfer = CountVectorizer()
    datanew = transfer.fit_transform(data)
    print("特征名字:\n", transfer.get_feature_names_out())
    print("datanew 为:\n",datanew.toarray()) #toarrary为显示二维数组的方法,原先默认是稀疏数组
    return None

结果

特征名字:
 ['crazy' 'dislike' 'like' 'oh' 'omg' 'python']
datanew 为:
 [[1 0 2 1 0 1]
 [0 1 0 0 1 1]]

sklearn.feature_extraction.text.TfidfVectorizer

若文本为中文采用jieba分词处理

**jieba.cut()**返回词语组成的生成器

#对中文进行特征抽取
def text_chinese_tfidf_demo():
    data = ["在我过去四十余年的生涯中,冬民情味尝得最深刻的要算十年前初移居的时侯了,",
            "十年以来,白马湖已成了一个小村落,当我移居的时侯,还是一片荒野,",
            "此外两三里内没有人烟。一家人于阴历十一月下甸从热闹的杭州移居于这荒凉的山野,宛如投身于极带中。"]
    # 将原始数据转换成分好词的形式
    text_list = []
    for sent in data:
        text_list.append(cut_word(sent))
    print(text_list)

    # 1、实例化一个转换器类
    transfer = TfidfVectorizer(stop_words=['一个', '时候', '不要'])
    # 2、调用fit_transform
    data = transfer.fit_transform(text_list)
    print("文本特征抽取的结果:\n", data.toarray())
['在 我 过去 四十余年 的 生涯 中 , 冬 民情 味尝得 最 深刻 的 要 算 十年 前初 移居 的 时侯 了 ,', '十年 以来 , 白马湖 已成 了 一个 小 村落 , 当 我 移居 的 时侯 , 还是 一片 荒野 ,', '此外 两三里 内 没有 人烟 。 一家人 于 阴历 十一月 下甸 从 热闹 的 杭州 移居 于 这 荒凉 的 山野 , 宛如 投身于 极带 中 。']
[[0.         0.         0.         0.         0.         0.
  0.         0.34288371 0.         0.2607719  0.34288371 0.34288371
  0.         0.         0.         0.         0.2607719  0.
  0.         0.         0.         0.34288371 0.         0.34288371
  0.         0.34288371 0.         0.20251264 0.         0.
  0.34288371 0.         0.        ]
 [0.32434681 0.         0.32434681 0.         0.         0.
  0.32434681 0.         0.         0.24667411 0.         0.
  0.         0.         0.32434681 0.         0.24667411 0.32434681
  0.         0.         0.         0.         0.         0.
  0.         0.         0.32434681 0.19156445 0.         0.32434681
  0.         0.32434681 0.        ]
 [0.         0.25524803 0.         0.25524803 0.25524803 0.25524803
  0.         0.         0.25524803 0.         0.         0.
  0.25524803 0.25524803 0.         0.25524803 0.         0.
  0.25524803 0.25524803 0.25524803 0.         0.25524803 0.
  0.25524803 0.         0.         0.1507536  0.25524803 0.
  0.         0.         0.25524803]]
Tf-idf文本特征提取
  • 主要思想:如果某个词或短语在一篇文章中出现的概率高,并且在其他文章中很少出现,则认为此词或者短语具有很好的类别区分能力,适合用来分类。
  • 作用:用以评估一字词对于一个文件集或一个语料库中的其中一份文件的重要程度。

词频(term frequency,tf)指的是某一个给定的词语在该文件中出现的频率

逆向文档频率(inverse document frequency,idf)是一个词语普遍重要性的度量。某一特定词语的idf,可以由总文件数目除以包含该词语之文件的数目,再将得到的商取以10为底的对数得到

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-s0TOvKa8-1678960641237)(…/picture/tfidf%E5%85%AC%E5%BC%8F.png)]

图像特征提取

2.2 特征预处理

官方解释:provides several common utility functions and transformer classes to change raw feature vectors into a representation that is more suitable for the downstream estimators. 通过一些转换函数将特征数据转换成更加适合算法模型的特征数据过程

归一化 MinMaxScaler

把所有数据都转化成[0,1]或者[-1,1]之间的数,其目的是为了取消各维数据之间的数量级差别,避免因为输入输出数据数量级差别大而造成网络预测误差过大。

​ [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RmAnfZCv-1678960641239)(D:\Desktop\java学习笔记\img\20210522174628234.png)]

def MinMaxScaler(x,Max,Min):
    x = (x - Min) / (Max - Min);
    return x

sklearn.preprocessing.MinMaxScaler (feature_range=(0,1)… )

  • MinMaxScalar.fit_transform(X) X:numpy array格式的数据[n_samples,n_features]
  • 返回值:转换后的形状相同的array
#归一化演示
def minmax_demo():
    data = pd.read_csv("dating.txt")
    print(data)
    transfer = MinMaxScaler(feature_range=(0, 1))  #(0,1)表示归一化的范围
    data = transfer.fit_transform(data[['milage', 'Liters', 'Consumtime']])
    print("最小值最大值归一化处理的结果:\n", data)
    return None

结果:

   milage     Liters  Consumtime  target
0   40920   8.326976    0.953952       3
1   14488   7.153469    1.673904       2
2   26052   1.441871    0.805124       1
3   75136  13.147394    0.428964       1
4   38344   1.669788    0.134296       1
最小值最大值归一化处理的结果:
 [[0.43582641 0.58819286 0.53237967]
 [0.         0.48794044 1.        ]
 [0.19067405 0.         0.43571351]
 [1.         1.         0.19139157]
 [0.3933518  0.01947089 0.        ]]

tips:容易收到最大值最小值异常的影响,若异常值是最大或者最小值,会导致结果非常不理想,鲁棒性较差,只适合传统精确小数据场景

标准化 StandardScaler

将对应数据的分布规约在均值为0,标准差为1的分布上,近似高斯分布

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-U6AS68zX-1678960641241)(…/picture/gif.latex)]

其中μ为原始数据的均值,σ为原始数据的标准差,是当前用的最多的标准化公式

def StandardScaler(x,mu,sigma):
    x = (x - mu) / sigma;
    return x

sklearn.preprocessing.StandardScaler( )

  • 处理之后每列来说所有数据都聚集在均值0附近标准差差为1
  • StandardScaler.fit_transform(X) X:numpy array格式的数据[n_samples,n_features]
  • 返回值:转换后的形状相同的array
    #标准化
def standard_demo():
    data = pd.read_csv("dating.txt")
    print(data)
    transfer = StandardScaler()
    data = transfer.fit_transform(data[['milage', 'Liters', 'Consumtime']])
    print("标准化的结果:\n", data,"\n")
    print("每一列特征的平均值:", transfer.mean_,"\n")
    print("每一列特征的方差:", transfer.var_,"\n")
    return None

结果:

   milage     Liters  Consumtime  target
0   40920   8.326976    0.953952       3
1   14488   7.153469    1.673904       2
2   26052   1.441871    0.805124       1
3   75136  13.147394    0.428964       1
4   38344   1.669788    0.134296       1
标准化的结果:
 [[ 0.0947602   0.44990013  0.29573441]
 [-1.20166916  0.18312874  1.67200507]
 [-0.63448132 -1.11527928  0.01123265]
 [ 1.77297701  1.54571769 -0.70784025]
 [-0.03158673 -1.06346729 -1.27113187]] 
每一列特征的平均值: [3.8988000e+04 6.3478996e+00 7.9924800e-01] 
每一列特征的方差: [4.15683072e+08 1.93505309e+01 2.73652475e-01] 

tips:适合现代嘈杂大数据场景

2.3 降维

降维是指在某些限定条件下,降低随机变量(特征)个数,得到一组“不相关”主变量的过程

特征选择

数据中包含冗余或无关变量(或称特征、属性、指标等),旨在从原有特征中找出主要特征

方法 sklearn.feature_selection

Filter(过滤式)

主要探究特征本身特点、特征与特征和目标值之间关联

sklearn.feature_selection.VarianceThreshold(threshold = 0.0)

  • Variance.fit_transform(X) X:numpy array格式的数据[n_samples,n_features]
  • 返回值:训练集差异低于threshold的特征将被删除。默认值是保留所有非零方差特征,即删除所有样本中具有相同值的特征。
	#过滤方差特征
def filter_demo():
    data = pd.read_csv("factor_returns.csv")
  #  print("结果:\n", data, "\n")
    transfer =VarianceThreshold(threshold=20)
    datanew = transfer.fit_transform(data.iloc[:,1:-2]) #[:,1:-2],逗号左边表行全要,逗号右边表要1列到-2列
  #  print("结果:\n", datanew, datanew.shape,"\n")
原始数据:
             index  pe_ratio  pb_ratio  ...  total_expense        date    return
0     000001.XSHE    5.9572    1.1818  ...   1.088254e+10  2012-01-31  0.027657
1     000002.XSHE    7.0289    1.5880  ...   2.378348e+10  2012-01-31  0.082352
2     000008.XSHE -262.7461    7.0003  ...   1.203008e+07  2012-01-31  0.099789
3     000060.XSHE   16.4760    3.7146  ...   7.935543e+09  2012-01-31  0.121595
4     000069.XSHE   12.5878    2.5616  ...   7.091398e+09  2012-01-31 -0.002681
...           ...       ...       ...  ...            ...         ...       ...
2313  601888.XSHG   25.0848    4.2323  ...   1.041419e+10  2012-11-30  0.060727
2314  601901.XSHG   59.4849    1.6392  ...   1.089783e+09  2012-11-30  0.179148
2315  601933.XSHG   39.5523    4.0052  ...   1.749295e+10  2012-11-30  0.137134
2316  601958.XSHG   52.5408    2.4646  ...   6.009007e+09  2012-11-30  0.149167
2317  601989.XSHG   14.2203    1.4103  ...   4.132842e+10  2012-11-30  0.183629
[2318 rows x 12 columns] 

过滤后结果:
 [[ 5.95720000e+00  8.52525509e+10  8.00800000e-01 ...  1.21144486e+12
   2.07014010e+10  1.08825400e+10]
 [ 7.02890000e+00  8.41133582e+10  1.64630000e+00 ...  3.00252062e+11
   2.93083692e+10  2.37834769e+10]
 [-2.62746100e+02  5.17045520e+08 -5.67800000e-01 ...  7.70517753e+08
   1.16798290e+07  1.20300800e+07]
 ...
 [ 3.95523000e+01  1.70243430e+10  3.34400000e+00 ...  2.42081699e+10
   1.78908166e+10  1.74929478e+10]
 [ 5.25408000e+01  3.28790988e+10  2.74440000e+00 ...  3.88380258e+10
   6.46539204e+09  6.00900728e+09]
 [ 1.42203000e+01  5.91108572e+10  2.03830000e+00 ...  2.02066110e+11
   4.50987171e+10  4.13284212e+10]] (2318, 7) 
相关系数

皮尔逊相关系数(Pearson Correlation Coefficient),反映变量之间相关关系密切程度的统计指标

相关系数的值介于–1与+1之间,即–1≤ r ≤+1。其性质如下:

  • 当r>0时,表示两变量正相关,r<0时,两变量为负相关
  • 当|r|=1时,表示两变量为完全相关,当r=0时,表示两变量间无相关关系
  • 当0<|r|<1时,表示两变量存在一定程度的相关。且|r|越接近1,两变量间线性关系越密切;|r|越接近于0,表示两变量的线性相关越弱
  • 一般可按三级划分:|r|<0.4为低度相关;0.4≤|r|<0.7为显著性相关;0.7≤|r|<1为高度线性相关

from scipy.stats import pearsonr

  • 两两特征之间进行相关性计算

  • x : (N,) array_like

  • y : (N,) array_like Returns: (Pearson’s correlation coefficient, p-value)

   #相关系数
    r = pearsonr(data["revenue"],data["total_expense"])
    print("相关系数:\n", r, "\n")
    #通过画图表示
    plt.figure(figsize=(20, 8), dpi=100)
    plt.scatter(data['revenue'], data['total_expense'])
    plt.show()
    return None
相关系数:
 PearsonRResult(statistic=0.9958450413136115, pvalue=0.0) 
 #指标revenue与指标total_expense之间的相关性大小为0.995845

也可以通过画图的形式展现

import matplotlib.pyplot as plt
plt.figure(figsize=(20, 8), dpi=100)
plt.scatter(data['revenue'], data['total_expense'])
plt.show()

Embedded (嵌入式):算法自动选择特征(特征与目标值之间的关联)

  • 决策树:信息熵、信息增益
  • 正则化:L1、L2
  • 深度学习:卷积等

主成分分析

(是否可以理解为极大线性无关组???)

它会将一个大的变量集合转化为更少的变量集合,同时保留大的变量集合中的大部分信息。主成分是一个新的变量,他是初始变量的线性组合。新的变量之间是不相关的,第一个主成分中包含了初始变量的大部分信息,是初始变量的压缩和提取。

作用:是数据维数压缩,尽可能降低原数据的维数(复杂度),损失少量信息。

sklearn.decomposition.PCA(n_components=None)

将数据分解为较低维数空间

  • n_components: 小数:表示保留百分之多少的信息 整数:减少到多少特征
  • PCA.fit_transform(X) X:numpy array格式的数据[n_samples,n_features]
  • 返回值:转换后指定维度的array
    #对数据进行PCA降维
def pca_demo():
    data = [[2, 8, 4, 5], [6, 3, 0, 8], [5, 4, 9, 1]]
    transfer = PCA(n_components=0.9) #0.9小数——保留多少信息,若写成整数表减少到多少特征
    data1 = transfer.fit_transform(data)
    print("保留90%的信息,降维结果为:\n", data1)
    return None
保留90%的信息,降维结果为:
 [[ 1.28620952e-15  3.82970843e+00]
 [ 5.74456265e+00 -1.91485422e+00]
 [-5.74456265e+00 -1.91485422e+00]]

二、数据集

一般分为训练集和测试集,常见划分为8:2 、7:3

sklearn有许多数据集,可以直接获取

获取数据集sklearn.datasets
  • datasets.load_datasetName() 获取小规模数据集,数据包含在datasets里
  • datasets.fetch_datasetName(data_home=None) 获取大规模数据集,需要从网络上下载,函数的第一个参数是data_home,表示数据集下载的

load和fetch 返回的数据类型datasets.base.Bunch(字典格式)

常见方法

  • data:特征数据数组,是 [n_samples * n_features] 的二维 numpy.ndarray 数组
  • target:标签数组,是 n_samples 的一维 numpy.ndarray 数组
  • DESCR:数据描述
  • feature_names:特征名,新闻数据,手写数字、回归数据集没有
  • target_names:标签名
数据集划分 train_test_split

sklearn.model_selection.train_test_split(arrays, test_size=None, train_size=None, random_state=None, shuffle=True)

  • x 数据集的特征值
  • y 数据集的标签值
  • test_size 测试集的大小,一般为float
  • random_state 随机数种子,不同的种子会造成不同的随机采样结果。相同的种子采样结果相同。
  • return ,测试集特征训练集特征值值,训练标签,测试标签(默认随机取)

三、估计器和转换器

交叉验证

交叉验证:将拿到的训练数据,分为训练和验证集。以下图为例:将数据分成5份,其中一份作为验证集。然后经过5次(组)的测试,每次都更换不同的验证集。即得到5组模型的结果,取平均值作为最终结果。又称5折交叉验证。

目的:为了让被评估的模型更加准确可信

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-8ZYJH1Cw-1678960641242)(…/picture/grid_search_cross_validation.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-kvWa6Uf3-1678960641243)(D:/picture/QQ%25E5%259B%25BE%25E7%2589%258720230313211413.png)]

常见交叉验证函数

超参数搜索-网格搜索GridSearchCV

1、sklearn.model_selection.GridSearchCV(estimator, param_grid=None,cv=None)

  • estimator:估计器对象
  • param_grid:估计器参数(dict){“n_neighbors”:[1,3,5]}
  • cv:指定几折交叉验证

常用方法:fit:输入训练数据 score:准确率

def knn_irs():
    #1、获取数据
    iris = load_iris()
    #2、划分数据集
    x_train, x_test, y_train, y_test=train_test_split(iris.data,iris.target,random_state=22)
    #3、特征工程:标准化
    transfer = StandardScaler()
    x_train = transfer.fit_transform(x_train)
    x_test = transfer.transform(x_test)

    #4、knn算法预估器
    estimator=KNeighborsClassifier()
    #加入网格搜索与交叉验证
    # K值:算法传入参数不定的值    理论上:k = 根号(样本数)
    # K值:后面会使用参数调优方法,去轮流试出最好的参数[1,3,5,10,20,100,200]
    param_dict ={"n_neighbors":[1,3,5,7,9,11]}
    GridSearchCV(estimator,param_grid=param_dict,cv=10)
    data = estimator.fit(x_train,y_train)

   
    # 预测测试数据集,得出准确率
    y_predict = estimator.predict(x_test)
    print("预测测试集类别:", y_predict)
    print("直接比对\n",y_test==y_predict)
    print("准确率为:", estimator.score(x_test, y_test))
    print("---------------------")
    return None
预测测试集类别: [0 2 1 2 1 1 1 1 1 0 2 1 2 2 0 2 1 1 1 1 0 2 0 1 2 0 2 2 2 2 0 0 1 1 1 0 0
 0]
直接比对
 [ True  True  True  True  True  True  True False  True  True  True  True
  True  True  True  True  True  True False  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True]
准确率为: 0.9473684210526315

2、sklearn.model_selection.cross_val_score(estimator, X, y=None, cv=None)

  • X:自变量数据
  • Y:因变量数据
  • scoring: (string) 选择验证方式

3、sklearn.metrics.confusion_matrix(y_true, y_pred, labels=None, sample_weight=None)

  • y_true: 标签值
  • y_pred: 预测值

结果会是个2*2的混淆矩阵

K折交叉验证

sklearn.model_selection.StratifiedKFold(n_splits=5, shuffle=False, random_state=None

  • n_splits:折叠次数,默认为3,至少为2。
  • shuffle:是否在每次分割之前打乱顺序。
  • random_state:随机种子,在shuffle==True时使用,默认使用np.random。

分类器

sklearn.linear_model.SGDClassifier 随机梯度下降分类器

  • decision_function():样本的预测得分值
from sklearn.linear_model import SGDClassifier
sgd_clf = SGDClassifier(max_iter=5,random_state=42)
sgd_clf.fit(X_train,y_train_5)
sgd_clf.predict([X[35000]])
y_scores = sgd_clf.decision_function([X[35000]])

sklearn.model_selection.StratifiedKFold

将X_train和 X_test 做有放回抽样,随机分三次,取出索引

  • 将全部训练集S分成k个不相交的子集,假设S中的训练样例个数为m,那么每一个自己有m/k个训练样例,相应的子集为{s1,s2,…,sk}
  • 每次从分好的子集里面,拿出一个作为测试集,其他k-1个作为训练集
  • 在k-1个训练集上训练出学习器模型,把这个模型放到测试集上,得到分类率的平均值,作为该模型或者假设函数的真实分类率

混淆矩阵

混淆矩阵是可视化工具,特别用于监督学习,在无监督学习一般叫做匹配矩阵。在图像精度评价中,主要用于比较分类结果和实际测得值,可以把分类结果的精度显示在一个混淆矩阵里面。


TP: Ture Positive FN: False Negative

​ FP: False Positive TN: Ture Negative

精确率

:预测结果为正例样本中真实为正例的比例 precision = TP / (TP + FP)

召回率

:真实为正例的样本中预测结果为正例的比例(查的全,对正样本的区分能力)recall = TP / (TP + FN)

分类评估报告classification_report

sklearn.metrics.classification_report(y_true, y_pred, labels=[], target_names=None

  • y_true:真实目标值
  • y_pred:估计器预测目标值
  • labels:指定类别对应的数字
  • target_names:目标类别名称
  • return:每个类别精确率与召回率
from sklearn.metrics import precision_score,recall_score
precision_score(y_train_5,y_train_pred)
recall_score(y_train_5,y_train_pred)

调和平均值

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-c27qqYZ2-1678960641244)(…/picture/image-20230313230202721.png)]

from sklearn.metrics import f1_score
f1_score(y_train_5,y_tra	in_pred)

decision_function方法

该方法返回每个实例的分数,直接生成不同的阈值,以及阈值对应的精度和召回率

  • TPR = TP / (TP + FN)
    • 所有真实类别为1的样本中,预测类别为1的比例
  • FPR = FP / (FP + FN)
    • 所有真实类别为0的样本中,预测类别为1的比例
ROC曲线

ROC曲线的横轴就是FPRate,纵轴就是TPRate,当二者相等时,表示的意义则是:对于不论真实类别是1还是0的样本,分类器预测为1的概率是相等的,此时AUC为0.5

ROC曲线越接近左上角越好

AUC指标

概率意义:随机取一对正负样本,正样本得分大于负样本的概率

AUC的最小值为0.5,最大值为1,取值越高越好

0.5

sklearn.metrics.roc_auc_score(y_true, y_score)

  • 计算ROC曲线面积,即AUC值
  • y_true:每个样本的真实类别,必须为0(反例),1(正例)标记
  • y_score:每个样本预测的概率值

tips

  • AUC只能用来评价二分类
  • AUC非常适合评价样本不平衡中的分类器性能
#逻辑回归进行癌症预测
def logisticregression():
    """
    
    :return: None
    """
    # 1、读取数据,处理缺失值以及标准化
    column_name = ['Sample code number', 'Clump Thickness', 'Uniformity of Cell Size', 'Uniformity of Cell Shape',
                   'Marginal Adhesion', 'Single Epithelial Cell Size', 'Bare Nuclei', 'Bland Chromatin',
                   'Normal Nucleoli', 'Mitoses', 'Class']

    data = pd.read_csv("https://archive.ics.uci.edu/ml/machine-learning-databases/breast-cancer-wisconsin/breast-cancer-wisconsin.data",
                       names=column_name)
    print(data)

    # 删除缺失值
    data = data.replace(to_replace='?', value=np.nan)
    data = data.dropna()

    # 取出特征值,数据集划分
    x = data[column_name[1:10]]
    y = data[column_name[10]]
    x_train,x_test,y_train,y_test = train_test_split(x,y)

    #标准化
    transform = StandardScaler()
    x_train=transform.fit_transform(x_train)
    x_test = transform.transform(x_test)
    print(x_train)

    #预估器
    estimator = LogisticRegression()
    estimator.fit(x_train,y_train)

    y_predict = estimator.predict(x_test)
    # 比较预测结果
    print("直接比对\n", y_test == y_predict)
    print("得出来的权重:", estimator.coef_)
    
    # 得出准确率
    print("预测的准确率:", estimator.score(x_test, y_test))

    y_test = np.where(y_test > 2.5, 1, 0)

    print("AUC指标:", roc_auc_score(y_test, estimator.predict(x_test)))
    return None
     Sample code number  Clump Thickness  ...  Mitoses  Class
0               1000025                5  ...        1      2
1               1002945                5  ...        1      2
2               1015425                3  ...        1      2
3               1016277                6  ...        1      2
4               1017023                4  ...        1      2
..                  ...              ...  ...      ...    ...
694              776715                3  ...        1      2
695              841769                2  ...        1      2
696              888820                5  ...        2      4
697              897471                4  ...        1      4
698              897471                4  ...        1      4

[699 rows x 11 columns]
[[-0.84728833 -0.06723474 -0.73954386 ... -0.58947385 -0.6290331
  -0.35252639]
 [-0.13553833 -0.71067744 -0.73954386 ... -0.58947385 -0.6290331
  -0.35252639]
 [-0.49141333 -0.71067744 -0.73954386 ... -0.58947385 -0.6290331
  -0.35252639]
 ...
 [ 0.93208667 -0.06723474  0.24225335 ... -0.18652243 -0.3072899
   3.11850272]
 [ 0.57621167 -0.71067744 -0.73954386 ... -0.99242526 -0.6290331
  -0.35252639]
 [ 1.28796167  2.18481473  2.20584776 ... -0.18652243  1.94491253
  -0.35252639]]
直接比对
 241    True
262    True
7      True
78     True
28     True
       ... 
225    True
21     True
614    True
669    True
329    True
Name: Class, Length: 171, dtype: bool
得出来的权重: [[ 1.49519645  0.10037845  0.78658638  0.98335294 -0.13894759  1.06213466
   1.08400189  0.75838489  0.60582909]]
预测的准确率: 0.9766081871345029
AUC指标: 0.9734472049689441

cross_val_predict

  • 从不同模型获得的预测结果的可视化。
  • 模型混合: 在集成方法中,当一个有监督估计量的预测被用来训练另一个估计量时

四、常见算法

无监督学习包含算法

  • 聚类
    • K-means(K均值聚类)
  • 降维
    • PCA

1、用于回归的估计器:

  • sklearn.linear_model.LinearRegression 线性回归
  • sklearn.linear_model.Ridge 岭回归

2、用于分类的估计器:

  • sklearn.neighbors k-近邻算法
  • sklearn.naive_bayes 贝叶斯
  • sklearn.linear_model.LogisticRegression 逻辑回归
  • sklearn.tree 决策树与随机森林

3、用于无监督学习的估计器

  • sklearn.cluster.KMeans 聚类

1、线性回归算法

设有x1,x2,…,xk,k个因素,通常可考虑如下的线性关系式:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-1Ft9jvBu-1678960641245)(…/picture/f654a9b87f182877dad9701c3ba8b1e7.svg)]

于是有

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-99eWzUDZ-1678960641245)(…/picture/5887ea28221d3ae296159b4876585978.svg)]

正规方程 LinearRegression

使用最小二乘法得到[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5FIt5VCs-1678960641246)(…/picture/ea027d6202a985007785bbb2f1642553.svg)]的解

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-MYk9c73f-1678960641246)(…/picture/ae60b716dfd1455e5366e95939243e76.svg)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-L3bZ7AaW-1678960641247)(…/picture/image-20230314205039334.png)]

#构建一个随机数组
X = 2*np.random.rand(100,1)#100行1列的矩阵
Y = 4+3*X + np.random.randn(100,1)
#画图
plt.plot(X,Y,'b.')
plt.xlabel('x1')
plt.ylabel('y1')
plt.axis([0,2,0,15])
plt.show
#求出theta_θ
X_b = np.c_[np.ones((100,1)),X] #多加一列1
# 正规方程的公式!!------
theta_best = np.linalg.inv(X_b.T.dot(X_b)).dot(X_b.T).dot(Y) #linalg 进行矩阵求逆    theta结果:array([[4.01932451],[2.84439032]])
#求出θ的函数
X_new = np.array([[0],[2]])
X_new_b = np.c_[np.ones((2,1)),X_new]
y_predict = X_new_b.dot(theta_best)
#画出直线
plt.plot(X_new,y_predict,'r--')
plt.plot(X,Y,'b.')
plt.axis([0,2,0,15])
plt.show()

sklearn.linear_model.LinearRegression(fit_intercept=True)

通过正规方程优化

  • fit_intercept:是否计算偏置
  • LinearRegression.coef_:回归系数
  • LinearRegression.intercept_:偏置
from sklearn.linear_model import LinearRegression
lr = LinearRegression()
lr.fit(X,Y)
print (lr.coef_)
print (lr.intercept_)
结果:
array([4.01932451])
array([[2.84439032]])

这里的结果与上一段代码结果一致,sklearn提供的LinearRegression API 采用的就是正规方程计算

多项式回归算法

sklearn.preprocessing.PolynomialFeatures(degree=2, interaction_only=False, include_bias=True)

若现在有a、b 两个特征,则degree=2的话,多项式为1、a、b 、ab、a2、b2

  • degree:度数,决定多项式的次数
  • interaction_only: 默认为False,字面意思就是只能交叉相乘,不能有a^2这种.
  • include_bias: 默认为True, 这个bias指的是多项式会自动包含1,设为False就没这个1了.
#制造点数据集
m = 100
X = 6*np.random.rand(m,1) - 3
y = 0.5*X**2+X+np.random.randn(m,1)
#绘画出数据集
plt.plot(X,y,'b.')
plt.xlabel('X_1')
plt.ylabel('y')
plt.axis([-3,3,-5,10])
plt.show()
#用PolynomialFeatures制造出多项式
from sklearn.preprocessing import PolynomialFeatures
poly_features = PolynomialFeatures(degree = 2,include_bias = False)
X_poly = poly_features.fit_transform(X)
#用LinearRegression训练数据,得出θ值
from sklearn.linear_model import LinearRegression
lin_reg = LinearRegression()
lin_reg.fit(X_poly,y)
X_new = np.linspace(-3,3,100).reshape(100,1) #选取100个点来绘制这个曲线
X_new_poly = poly_features.transform(X_new)
y_new = lin_reg.predict(X_new_poly)
plt.plot(X,y,'b.')
plt.plot(X_new,y_new,'r--',label='prediction')
plt.axis([-3,3,-5,10])
plt.legend()
plt.show()

​ 右图是选取了4个点来绘制的曲线,左图是100个点

梯度下降 SGDRegressor
  • BGD 批量梯度下降法(Batch Gradient Descent)

    ​ 在更新参数时使用所有的样本来进行更新,公式为:

    θi=θi−α∑j=1m(hθ(x(j)0,x(j)1,…x(j)n)−yj)x(j)iθi=θi−α∑j=1m(hθ(x0(j),x1(j),…xn(j))−yj)xi(j)

  • SGD 随机梯度下降(Stochastic gradient descent)

    ​ 区别在与求梯度时没有用所有的m个样本的数据,而是仅仅选取一个样本j来求梯度。对应的更新公式是:

    θi=θi−α(hθ(x(j)0,x(j)1,…x(j)n)−yj)x(j)iθi=θi−α(hθ(x0(j),x1(j),…xn(j))−yj)xi(j)

  • MGD 小批量梯度下降法(Mini-batch Gradient Descent)

    小批量梯度下降法是批量梯度下降法和随机梯度下降法的折衷,也就是对于m个样本,我们采用x个样子来迭代,1

    ​ θi=θi−α∑j=tt+x−1(hθ(x(j)0,x(j)1,…x(j)n)−yj)x(j)iθi=θi−α∑j=tt+x−1(hθ(x0(j),x1(j),…xn(j)−yj)xi(j)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7So3Qzgf-1678960641247)(…/picture/image-20230314222816503.png)]

eta = 0.1  #学习率即步长
n_iterations = 500   #迭代次数
m = 1000  #样本个数
theta = np.random.randn(2,1)  #对θ初始化一个随机数
for it in range(n_iterations):
    gradients = 2/m * X_b.T.dot(X_b.dot(theta)-Y) #求出梯度
    theta = theta - eta*gradients  #更新θ
print(theta)
结果:array([[4.12679272],
       [2.75568863]])

sklearn.linear_model.SGDRegressor(loss=“squared_loss”, fit_intercept=True, learning_rate =‘invscaling’, eta0=0.01)

  • SGDRegressor类实现了随机梯度下降学习,它支持不同的loss函数和正则化惩罚项来拟合线性回归模型。
  • loss:损失类型 loss=”squared_loss”: 普通最小二乘法
  • fit_intercept:是否计算偏置
  • learning_rate : string, optional
    • 学习率填充
    • ‘constant’: eta = eta0
    • ‘optimal’: eta = 1.0 / (alpha * (t + t0)) [default]
    • ‘invscaling’: eta = eta0 / pow(t, power_t)
      • power_t=0.25:存在父类当中
    • 对于一个常数值的学习率来说,可以使用learning_rate=’constant’ ,并使用eta0来指定学习率。
  • SGDRegressor.coef_:回归系数
  • SGDRegressor.intercept_:偏置
常用方法
fit(X, y[, sample_weight]) Fit linear model.
get_params([deep]) Get parameters for this estimator.
predict(X) Predict using the linear model.
score(X, y[, sample_weight]) Return the coefficient of determination of the prediction.
set_params(**params) Set the parameters of this estimator.
from sklearn.linear_model import SGDRegressor
sgd = SGDRegressor()
sgd.fit(X_b,Y)
sgd.score(X_b,Y)
结果:0.6825644189067137

sklearn.pipeline.Pipeline(steps, ***, memory=None, verbose=False)[

from sklearn.pipeline import Pipeline
from sklearn.preprocessing import StandardScaler
plt.figure(figsize=(12,6))
for style,width,degree in (('g-',1,100),('b--',1,2),('r-+',1,1)):
    poly_features = PolynomialFeatures(degree = degree,include_bias = False)
    std = StandardScaler()
    lin_reg = LinearRegression()
    polynomial_reg = Pipeline([('poly_features',poly_features),
             ('StandardScaler',std),
             ('lin_reg',lin_reg)])
    polynomial_reg.fit(X,y)
    y_new_2 = polynomial_reg.predict(X_new)
    plt.plot(X_new,y_new_2,style,label = 'degree   '+str(degree),linewidth = width)
plt.plot(X,y,'b.')
plt.axis([-3,3,-5,10])
plt.legend()
plt.show()
#二次项degree 不要太大,也不要太小

平方差函数

sklearn.metrics.mean_squared_error(y_true, y_pred)

欠拟合和过拟合

欠拟合

  • 欠拟合:一个假设在训练数据上不能获得更好的拟合,并且在测试数据集上也不能很好地拟合数据,此时认为这个假设出现了欠拟合的现象。(模型过于简单)

过拟合

  • 过拟合:一个假设在训练数据上能够获得比其他假设更好的拟合, 但是在测试数据集上却不能很好地拟合数据,此时认为这个假设出现了过拟合的现象。(模型过于复杂)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-crIH6xN5-1678960641248)(…/picture/1591423-20210127213913518-911079839.png)]

  • 欠拟合原因以及解决办法

    • 原因:学习到数据的特征过少
    • 解决办法:增加数据的特征数量
  • 过拟合原因以及解决办法

    • 原因:原始特征过多,存在一些嘈杂特征, 模型过于复杂是因为模型尝试去兼顾各个测试数据点
    • 解决办法:正则化

正则化

L1正则化

  • 作用:可以使得其中一些W的值直接为0,删除这个特征的影响
  • LASSO回归

L2正则化

  • 作用:可以使得其中一些W的都很小,都接近于0,削弱某个特征的影响
  • 优点:越小的参数说明模型越简单,越简单的模型则越不容易产生过拟合现象
  • Ridge回归

tip: L1可以让系数等于0,L2只会无限小

2、岭回归算法 (带有L2正则化的线性回归)Ridge

sklearn.linear_model.Ridge(alpha=1.0, fit_intercept=True,solver=“auto”, normalize=False) 具有l2正则化的线性回归

  • alpha:正则化力度,也叫 λ λ取值:0~1 1~10
  • solver:会根据数据自动选择优化方法 sag:如果数据集、特征都比较大,选择该随机梯度下降优化
  • normalize:数据是否进行标准化 normalize=False:可以在fit之前调用preprocessing.StandardScaler标准化数据

常用方法

  • Ridge.coef_:回归权重
  • Ridge.intercept_:回归偏置

3、逻辑回归算法 LogisticRegression

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-HSQwyO0e-1678960641249)(…/picture/%E9%80%BB%E8%BE%91%E5%9B%9E%E5%BD%92%E8%BE%93%E5%85%A5.png)]

逻辑回归的输入就是一个线性回归的结果。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-vBwbVMJd-1678960641250)(…/picture/%E9%80%BB%E8%BE%91%E5%9B%9E%E5%BD%92%E8%BF%90%E7%AE%97%E8%BF%87%E7%A8%8B.png)]

sklearn.linear_model.LogisticRegression(solver=‘liblinear’, penalty=‘l2’, C = 1.0)

  • solver:优化求解方式(默认开源的liblinear库实现,内部使用了坐标轴下降法来迭代优化损失函数)
    • sag:根据数据集自动选择,随机平均梯度下降
  • penalty:正则化的种类
  • C:正则化力度
# 取出特征值
    x = data[column_name[1:10]]
    y = data[column_name[10]]
    x_train,x_test,y_train,y_test = train_test_split(x,y)

    transform = StandardScaler()
    x_train=transform.fit_transform(x_train)
    x_test = transform.transform(x_test)
    print(x_train)

    estimator = LogisticRegression()
    estimator.fit(x_train,y_train)

    y_predict = estimator.predict(x_test)
    # 比较预测结果
    print("预测的类别:", y_predict)
    print("实际的类别:", y_test)
    print("直接比对\n", y_test == y_predict)
    print("得出来的权重:", estimator.coef_)

    # 得出准确率
    print("预测的准确率:", estimator.score(x_test, y_test))

    y_test = np.where(y_test > 2.5, 1, 0)

    print("AUC指标:", roc_auc_score(y_test, estimator.predict(x_test)))
    return None
   Sample code number  Clump Thickness  ...  Mitoses  Class
0               1000025                5  ...        1      2
1               1002945                5  ...        1      2
2               1015425                3  ...        1      2
3               1016277                6  ...        1      2
4               1017023                4  ...        1      2
..                  ...              ...  ...      ...    ...
694              776715                3  ...        1      2
695              841769                2  ...        1      2
696              888820                5  ...        2      4
697              897471                4  ...        1      4
698              897471                4  ...        1      4

[699 rows x 11 columns]
[[ 0.5737557  -0.03352576 -0.07021187 ...  1.04058664 -0.60756478
  -0.34559316]
 [-1.17900633 -0.69372535 -0.73592437 ... -0.99137507 -0.60756478
  -0.34559316]
 [ 0.22320329 -0.69372535 -0.73592437 ... -0.17859038 -0.60756478
  -0.34559316]
 ...
 [ 0.22320329 -0.69372535 -0.73592437 ... -0.99137507 -0.60756478
  -0.34559316]
 [ 0.22320329 -0.03352576 -0.40306812 ... -0.99137507 -0.60756478
  -0.34559316]
 [ 0.22320329 -0.69372535 -0.73592437 ... -0.99137507 -0.60756478
  -0.34559316]]
预测的类别: [4 4 4 2 4 4 2 2 2 2 2 2 4 4 4 4 4 2 2 4 2 2 4 2 2 4 4 2 2 2 4 4 2 2 2 2 2
 2 2 2 2 2 2 2 2 2 4 4 4 2 4 2 2 4 4 4 2 2 2 2 4 2 2 2 2 4 2 2 2 2 2 4 2 4
 2 2 4 4 2 4 2 2 2 4 2 4 2 2 2 2 2 4 4 2 2 4 2 4 2 2 4 2 4 4 2 2 2 2 2 2 2
 4 2 4 2 2 4 4 2 2 2 4 2 4 2 2 2 2 2 2 2 4 2 4 2 2 4 2 4 2 4 2 2 4 4 4 2 2
 4 2 4 2 2 2 4 2 2 2 2 4 4 4 4 4 2 2 2 2 2 4 2]
实际的类别: 213    4
46     4
494    2
119    2
62     4
      ..
298    2
385    2
598    2
570    4
346    2
Name: Class, Length: 171, dtype: int64
直接比对
 213     True
46      True
494    False
119     True
62      True
       ...  
298     True
385     True
598     True
570     True
346     True
Name: Class, Length: 171, dtype: bool
得出来的权重: [[1.21051431 0.23618593 0.81142422 1.25344323 0.01820399 1.51679512
  1.02940528 0.3794014  0.97758642]]
预测的准确率: 0.9473684210526315
AUC指标: 0.9444858420268256

LogisticRegression方法相当于 SGDClassifier(loss=“log”, penalty=" "),SGDClassifier实现了一个普通的随机梯度下降学习,也支持平均随机梯度下降法(ASGD),可以通过设置average=True。而使用LogisticRegression(实现了SAG)

3、K-近邻算法(KNN)

定义

如果一个样本在特征空间中的k个最相似(即特征空间中最邻近)的样本中的大多数属于某一个类别,则该样本也属于这个类别。

距离公式:两个样本的距离可以通过如下公式计算,又叫欧式距离

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-t41eJU3U-1678960641251)(…/picture/%E8%B7%9D%E7%A6%BB%E5%85%AC%E5%BC%8F.png)]

sklearn.neighbors.KNeighborsClassifier(n_neighbors=5,algorithm=‘auto’)

  • n_neighbors:int,可选(默认= 5),k_neighbors查询默认使用的邻居数
  • algorithm:{‘auto’,‘ball_tree’,‘kd_tree’,‘brute’},可选用于计算最近邻居的算法:‘ball_tree’将会使用 BallTree,‘kd_tree’将使用 KDTree。‘auto’将尝试根据传递给fit方法的值来决定最合适的算法。 (不同实现方式影响效率)

4、朴素贝叶斯算法

朴素:各个特征相互独立

贝叶斯公式:[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-UQPRlucf-1678960641252)(…/picture/%E8%B4%9D%E5%8F%B6%E6%96%AF%E5%85%AC%E5%BC%8F.png)]

  • P©:每个文档类别的概率(某文档类别数/总文档数量)
  • P(W│C):给定类别下特征(被预测文档中出现的词)的概率

计算方法:P(F1│C)=Ni/N (训练文档中去计算)

  • Ni为该F1词在C类别所有文档中出现的次数
  • N为所属类别C下的文档所有词出现的次数和

优缺点

  • 优点:
    • 朴素贝叶斯模型发源于古典数学理论,有稳定的分类效率。
    • 对缺失数据不太敏感,算法也比较简单,常用于文本分类。
    • 分类准确度高,速度快
  • 缺点:
    • 由于使用了样本属性独立性的假设,所以如果特征属性有关联时其效果不好

拉普拉斯平滑系数

目的:防止计算出的分类概率为0

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Wxa0mqTC-1678960641253)(…/picture/%E5%B9%B3%E6%BB%91%E7%B3%BB%E6%95%B0%E5%85%AC%E5%BC%8F.png)]

sklearn.naive_bayes.MultinomialNB(alpha = 1.0)

  • 朴素贝叶斯分类
  • alpha:拉普拉斯平滑系数

5、决策树算法

信息熵、信息增益

  • H的专业术语称之为信息熵,单位为比特。

“谁是世界杯冠军”的信息量应该比5比特少,特点(重要):

  • 当这32支球队夺冠的几率相同时,对应的信息熵等于5比特
  • 只要概率发生任意变化,信息熵都比5比特大

sklearn.tree.DecisionTreeClassifier(criterion=’gini’, max_depth=None,random_state=None)

  • 决策树分类器

  • criterion:默认是’gini’系数,也可以选择信息增益的熵’entropy’

  • max_depth:树的深度大小

  • random_state:随机数种子

  • 其中会有些超参数:max_depth:树的深度大小

    • 其它超参数我们会结合随机森林讲解

6、无监督学习-K-means算法

优点:采用迭代式算法,直观易懂并且非常实用

缺点:容易收敛到局部最优解(多次聚类)

K-means聚类步骤

  • 1、随机设置K个特征空间内的点作为初始的聚类中心
  • 2、对于其他每个点计算到K个中心的距离,未知的点选择最近的一个聚类中心点作为标记类别
  • 3、接着对着标记的聚类中心之后,重新计算出每个聚类的新中心点(平均值)
  • 4、如果计算得出的新中心点与原中心点一样,那么结束,否则重新进行第二步过程

sklearn.cluster.KMeans(n_clusters=8,init=‘k-means++’)

  • k-means聚类
  • n_clusters:开始的聚类中心数量
  • init:初始化方法,默认为’k-means ++’
  • labels_:默认标记的类型,可以和真实值比较(不是值比较)

Kmeans性能评估指标

轮廓系数

注:对于每个点i 为已聚类数据中的样本 ,b_i 为i 到其它族群的所有样本的距离最小值,a_i 为i 到本身簇的距离平均值。最终计算出所有的样本点的轮廓系数平均值

分析过程(我们以一个蓝1点为例)

  • 1、计算出蓝1离本身族群所有点的距离的平均值a_i
  • 2、蓝1到其它两个族群的距离计算出平均值红平均,绿平均,取最小的那个距离作为b_i
  • 根据公式:极端值考虑:如果b_i >>a_i: 那么公式结果趋近于1;如果a_i>>>b_i: 那么公式结果趋近于-1

如果b_i>>a_i:趋近于1效果越好, b_i<

sklearn.metrics.silhouette_score(X, labels)

  • 计算所有样本的平均轮廓系数
  • X:特征值
  • labels:被聚类标记的目标值

np

np.random.randn()函数
语法:np.random.randn(d0,d1,d2……dn)

  • 当函数括号内没有参数时,则返回一个浮点数;
  • 当函数括号内有一个参数时,则返回秩为1的数组,不能表示向量和矩阵;
  • 当函数括号内有两个及以上参数时,则返回对应维度的数组,能表示向量或矩阵;
  • np.random.standard_normal()函数与np.random.randn()类似,但是np.random.standard_normal()的输入参数为元组(tuple)。
  • np.random.randn()的输入通常为整数,但是如果为浮点数,则会自动直接截断转换为整数。
    作用:通过本函数可以返回一个或一组服从标准正态分布的随机样本值。
    特点:标准正态分布是以0为均数、以1为标准差的正态分布,记为N(0,1)
    原文链接:https://blog.csdn.net/abc13526222160/article/details/86423754

np.linspace(start, stop, num=50, endpoint=True) 定义均匀间隔创建数值序列

  • start:开始的位置
  • stop:结束的位置
  • num:分隔值总数,控制结果中共有多少个元素

format() : 格式化字符串函数,常用功能是插入数据和数字格式化;

你可能感兴趣的:(学习,scikit-learn,机器学习)