在对数据集划分训练集和测试集的时候,我们经常采用的有三种方法,其中留出法和交叉验证法已经在上一篇中有所说明。
本文将主要讲述自助法(bootstrapping)及其python实现。
在上一篇中,我们说明当数据量很小时,我们可以使用留一法,但是这种方法会造成计算复杂度过高。此时,我们引入自助法来解决问题。
自助法: 给定包含m个样本的数据集 D D D,我们对它进行采样产生数据集 D ′ D' D′:每次随机从 D D D中挑选一个样本,将其复制到 D ′ D' D′中,然后再将其样本放回原始数据集 D D D中,使得该样本在下次采样的时候也可能被采到;这个过程重复执行m次,我们就得到了包含m个样本的数据集 D ′ D' D′。简而言之,就是从数据集 D D D中,有放回随机采样m次,组成一个新样本集 D ′ D' D′。
从定义中,我们可以知道会有一部分样本没有出现在 D ′ D' D′中,会有一部分样本重复出现。一个样本在m次采样过程中始终没有被取到的概率是 ( 1 − 1 m ) m (1-\dfrac{1}{m})^m (1−m1)m。
当样本量m=10时,没有被抽到的概率p=0.3487;
当样本量趋于无穷时, lim x → + ∞ ( 1 − 1 m ) = 1 e ≈ 0.368 {\lim_{x \to +\infty}}(1-\dfrac{1}{m}) = \dfrac{1}{e} \approx 0.368 x→+∞lim(1−m1)=e1≈0.368
所以,采用自助法抽样时,大约会有35%的数据没有出现在 D ′ D' D′中。
所以,我们用抽样所得的 D ′ D' D′作为训练集, D − D ′ D - D' D−D′作为样本的测试集。如此一来,我们训练的模型也使用了m个样本,并且仍有近35%的数据可以用作测试集。
自助法的优势在于处理较小数据集或者难以有效划分训练测试集时;并且,自助法可以产生多组不同的训练集和测试集,这对集成学习有很大帮助。
自助法的劣势在于它所产生的数据集 D ′ D' D′会改变初始数据集的分布,这会引入估计偏差。因此,当数据量足够时,我们常常采用留出法或者交叉验证法。
#自助法
import numpy as np
#任意设置一个数据集
X = [1,4,3,23,4,6,7,8,9,45,67,89,34,54,76,98,43,52]
#通过产生的随机数获得抽取样本的序号
bootstrapping = []
for i in range(len(X)):
bootstrapping.append(np.floor(np.random.random()*len(X)))
#通过序号获得原始数据集中的数据
D_1 = []
for i in range(len(X)):
D_1.append(X[int(bootstrapping[i])])
'''结果
[45, 52, 34, 9, 6, 54, 34, 1, 4, 54, 6, 8, 67, 4, 43, 9, 4, 67]
'''
由结果我们可知,数据如9/6/54重复出现,但是数据如3没有出现。