本文是我在学习西瓜书和python大战机器学习两本书时的一些读书笔记。主要参考着两本书,我学习时两本书结合着看,西瓜书理论写的非常好,python大战机器学习主要是对算法的一些提炼以及利用sklearn库的实现。

集成学习通过构建并结合多个学习器来完成学习任务,也被称为多分类器系统。集成学习就是将多个“学习器”通过某种策略结合起来。个体学习器通常由一个现有的学习算法从数据中产生,由单一种类的学习器集成的是“同质”的,由不同种类的学习器集成是“异质”的,同质集成中的个体称为“基学习器”。

图片来自:lib.csdn.net/article/ma

集成学习通过组合多个学习期来获得比单个个体学习期显著优越的泛化性能。根据个体学习器的生成方式大概可以分为以下两类:

(1)Boosting算法:在这类算法中,个体学习器之间存在强依赖关系,必须串行生成。
(2)Bagging算法:在这类算法中,个体学习器之间不必存在强依赖关系,可以同时生成。

Boost算法步骤如下:

(1)首先从初始训练集得到一个基学习器

(2)根据基学习器的表现对训练样本的权重进行调整,使得先前被基学习器误判的训练样本在后续受到更多的关注

(3)然后基于调整后的样本权重来训练下一个基学习器

(4)一直重复,直到达到基学习器的指定上限或者已经完美的训练好

(5)最终将这些基学习器进行加权组合得到集成学习器

AdaBoost算法是Boost算法的典型代表,最核心的两个步骤就是权值调整和基分类器组合。

权值调整:AdaBoost算法提高了那些被上一轮分类器错误分类的样本权值,降低了正确分类的权值,这样使得上一轮被分类错误的在下一轮受到了更大的重视。

基分类器组合:组合采取线性加权的方式,加大了分类错误率较小的基分类器的权重,减小分类误差较大的基分类器的权重。

AdaBoost算法如下:

输入:训练集,基分类器(比如决策树,贝叶斯等)

输出:集成分类器

  1. 初始化权重

2.使用具有权重向量的数据集学习,得到一个学习器

3.计算这个学习器在训练集上的错误率:

注意:这里要求错误率要小于0.5

4.计算这个分类器在集成分类器中的权重:

5.更新下一次训练集的权重向量:





它保证了更新后的权重依旧是一个概率分布。

6.构建基本分类器的线性组合:

关于第三步为何错误率一定要小于0.5的解释:

AdaBoost算法是通过降低正确分类样本的权重,提高错误分类样本的权重来实现提升分类器性能,这个权重是通过每一轮的权重更新实现的。

假定正确为1,错误为-1,那么对于分类正确的样本,那么下一轮的权重为:

对于分类错误的样本,在下一轮的权重为:

比较两者的大小,很明显用比做除法比做差法更直接,通过比较两者的商,可以发现分类错误的样本权重与分类正确的样本权重之商为:

这样就可以得到:



下面是python大战机器学习的代码,我也贴出来,我在这里比较了一下单个高斯贝叶斯分类器做分类和以它为基学习器的集成学习的效果。数据集采用的sklearn自带的手写识别数据集。

首先还是介绍一下函数:

# -*- coding: utf-8 -*-
"""
Created on Mon Jul 24 20:46:58 2017

@author: Thinkpad
集成学习
AdaBoost
首先介绍用于分类的提升(AdaBoost)算法,AdaBoostClassifier
class AdaBoostClassifier(base_estimator=None,n_estimators=50,
                         learning_rate=1.0,algorithm="SAMME.R",random_state=None)
参数说明:
base_estimator:一个基础分类器对象,默认为决策树分类,这类分类器必须支持带样本权重的学习

n_estimators:一个整数,指定基础分类器的上限数目,默认是50,若提前训练好,则分类器
              数目可以小于该值

learning_rate:步长,通常该值越小,需要的基础分类器越多。是加法模型里面的一个概念Hm(X)=Hm-1(X)+vah(x),它就
               是这里的v

algorithm:是一个字符串,指定算法,该算法用于多分类问题
       "SAMME.R":使用SAMME.R算法。基础分类器必须支持计算类别的概率
       "SAMME":使用SAMME算法

random_state:一个整数,或者一个RandomState实例,或者None
     如果为整数,则它指定的随机数生成器的种子
     如果为实例,则指定随机数生成器
     如果为None,使用默认的随机数生成器

"""

import matplotlib.pyplot as plt
from sklearn import datasets,cross_validation,ensemble,naive_bayes
def load_data():
    digits=datasets.load_digits()
    return cross_validation.train_test_split(digits.data,digits.target,test_size=0.25,
                                             random_state=0)
def test_GaussianNB(*data):
    X_train,X_test,y_train,y_test=data
    cls=naive_bayes.GaussianNB()
    cls.fit(X_train,y_train)
    print("train score:%f"%(cls.score(X_train,y_train)))
    print("test score:%f"%(cls.score(X_test,y_test)))    



def test_AdaBoostClassifier(*data):
    X_train,X_test,y_train,y_test=data
    clf=ensemble.AdaBoostClassifier(learning_rate=0.1,
                                    base_estimator=naive_bayes.GaussianNB(),
                                    n_estimators=100)
    clf.fit(X_train,y_train)
    ##绘图
    fig=plt.figure()
    ax=fig.add_subplot(1,1,1)
    estimators_num=len(clf.estimators_)
    X=range(1,estimators_num+1)
    ax.plot(list(X),list(clf.staged_score(X_train,y_train)),label="Train score")
    ax.plot(list(X),list(clf.staged_score(X_test,y_test)),label="Test score")
    ax.set_xlabel("estimator num")
    ax.set_ylabel("score")
    ax.legend(loc="best")
    ax.set_title("AdaBoostClassifier")
    plt.show()
    print("Train score:%f"%(clf.score(X_train,y_train)))
    print("Test score:%f"%(clf.score(X_test,y_test)))
if __name__=="__main__":
    X_train,X_test,y_train,y_test=load_data()
    test_GaussianNB(X_train,X_test,y_train,y_test)
    test_AdaBoostClassifier(X_train,X_test,y_train,y_test)


根据代码运行的效果的,单个高斯贝叶斯分类器训练正确率0.85746,测试集正确率0.83333.采用集成学习之后的贝叶斯分分类器训练正确率0.91239,测试集正确率0.88222.