机器学习:使用python生成训练集和测试集的方法实现
注意:所有函數(shù)僅針對(duì)西瓜數(shù)據(jù)集,如果需要對(duì)其他數(shù)據(jù)集進(jìn)行分類,只需找到數(shù)據(jù)集中目標(biāo)值(西瓜數(shù)據(jù)集中目標(biāo)值為是否是好瓜的"是"和"否")所在的列(西瓜數(shù)據(jù)集中其在最后一列),然后將需要按照目標(biāo)值進(jìn)行運(yùn)行的代碼替換即可
留出法實(shí)現(xiàn)
實(shí)現(xiàn)思路:根據(jù)留出法的原理,需要將數(shù)據(jù)集分為互斥的兩個(gè)集合,一個(gè)作為訓(xùn)練集,另一個(gè)作為測(cè)試集,在數(shù)據(jù)劃分過(guò)程中需要分層采樣,為了生成多組數(shù)據(jù),需要每次隨機(jī)劃分。
首先統(tǒng)計(jì)一下數(shù)據(jù)集中的正例的個(gè)數(shù):
然后計(jì)算一下需要的訓(xùn)練集的大小:
# 計(jì)算訓(xùn)練集大小train_set_size = int(percent / 100 * len(data_set)+0.5)其中,percent是訓(xùn)練集占數(shù)據(jù)集的百分比,需要人為輸入。
再然后計(jì)算一下訓(xùn)練集中需要的正例個(gè)數(shù):
為了每次劃分都隨機(jī)且訓(xùn)練集和測(cè)試集互斥,使用sample生成隨機(jī)數(shù)作為即將采集訓(xùn)練的下標(biāo):
# 每組訓(xùn)練集和數(shù)據(jù)集保證隨機(jī)劃分index_list = random.sample(range(0, len(data_set)), len(data_set))使用for循環(huán)分層訓(xùn)練集和測(cè)試集:
# 劃分訓(xùn)練集、數(shù)據(jù)集for j in index_list:if data_set[j][-1] == "是":if positive_count < positive_train_data_size:train_set.append(data_set[j])positive_count += 1else:test_set.append(data_set[j])else:if negative_count < train_set_size - positive_train_data_size:train_set.append(data_set[j])negative_count += 1else:test_set.append(data_set[j])每生成完一組訓(xùn)練集和測(cè)試集就將其存起來(lái)
k_train_set.append(train_set) k_test_set.append(test_set)總的程序如下:
def setAside(data_set):'''使用留出法生成數(shù)據(jù)集'''positive_size = 0# 計(jì)算數(shù)據(jù)集中的正例數(shù)for data in data_set:if data[-1] == "是" or data[-1] == "1":positive_size += 1percent = int(input("訓(xùn)練集占總數(shù)據(jù)集百分比(1~99):"))# 計(jì)算訓(xùn)練集大小train_set_size = int(percent / 100 * len(data_set)+0.5)# 計(jì)算訓(xùn)練集中需要的正例大小positive_train_data_size = int(train_set_size / len(data_set) * positive_size + 0.5)group_num = int(input("需要多少組? "))k_train_set, k_test_set = [], []# 生成訓(xùn)練集、測(cè)試集for i in range(group_num):# 每組訓(xùn)練集和數(shù)據(jù)集保證隨機(jī)劃分index_list = random.sample(range(0, len(data_set)), len(data_set))# 存放一組數(shù)據(jù)集和訓(xùn)練集train_set, test_set = [], []# 訓(xùn)練集中正反例計(jì)數(shù),為了確定正反例已存夠positive_count, negative_count = 0, 0# 劃分訓(xùn)練集、數(shù)據(jù)集for j in index_list:if data_set[j][-1] == "是" or data[-1] == "1":if positive_count < positive_train_data_size:train_set.append(data_set[j])positive_count += 1else:test_set.append(data_set[j])else:if negative_count < train_set_size - positive_train_data_size:train_set.append(data_set[j])negative_count += 1else:test_set.append(data_set[j])k_train_set.append(train_set)k_test_set.append(test_set)# 返回訓(xùn)練集、數(shù)據(jù)集組,組數(shù)return k_train_set, k_test_set, group_numk折交叉驗(yàn)證法實(shí)現(xiàn)
實(shí)現(xiàn)思路:K折交叉驗(yàn)證法是將數(shù)據(jù)集劃分為k個(gè)互斥子集,取出一個(gè)作為測(cè)試集,其余作為訓(xùn)練集,且要分層采樣,如果像留出法那樣計(jì)算各個(gè)子集需要的各種數(shù)據(jù),會(huì)導(dǎo)致程序太復(fù)雜,所以采用另外一種思路,就是將其按照是否是好瓜進(jìn)行排序,然后依次存入各個(gè)列表。
首先,將數(shù)據(jù)集排序
然后將排好序的數(shù)據(jù)集依次存入大小為k的list
# 分層劃分?jǐn)?shù)據(jù)集為k份for i in range(len(data_set)):k_list[i % k].append(data_set[i])這樣,數(shù)據(jù)就被分層分為了互斥的k份
然后將k份數(shù)據(jù)中的一份作為測(cè)試集,其他作為訓(xùn)練集來(lái)分類,每劃分一次就將其結(jié)果存下來(lái)
總的程序如下:
def crossValidate(data_set):'''使用k折交叉驗(yàn)證法生成數(shù)據(jù)集'''# 按照表中最后一個(gè)元素來(lái)排序,便于分層data_set.sort(key=lambda k: k[-1])k = int(input("輸入折數(shù)k(k>1):"))# 生成k個(gè)列表放在一個(gè)列表中k_list = list([] for i in range(k))k_train_set = list([])k_test_set = list([])# 分層劃分?jǐn)?shù)據(jù)集為k份for i in range(len(data_set)):k_list[i % k].append(data_set[i])# 生成k個(gè)數(shù)據(jù)集和k個(gè)訓(xùn)練集for i in range(k):temp_set = []for j in range(k):if j != i:temp_set.extend(k_list[j])else:k_test_set.append(k_list[j])k_train_set.append(temp_set)# 返回訓(xùn)練集、數(shù)據(jù)集組,組數(shù)return k_train_set, k_test_set, k自助法實(shí)現(xiàn)
實(shí)現(xiàn)思路:自助法就是從大小的m數(shù)據(jù)集中隨機(jī)采樣(本隨機(jī)采樣類似于放回抽樣)m次數(shù)據(jù),作為訓(xùn)練集,其余的作為測(cè)試集。
首先得到m的大小
為了可以生成多組訓(xùn)練集和測(cè)試集,所以生成需要的組數(shù)組隨機(jī)數(shù),每組隨機(jī)數(shù)的范圍為0~m-1,因?yàn)閿?shù)據(jù)集的下標(biāo)范圍是從0開始到m-1結(jié)束
# 生成group組隨機(jī)數(shù),每組有m個(gè),隨機(jī)數(shù)的范圍為0~m-1 ran_lis = list([[random.randint(0, m-1)for i in range(m)] for j in range(group)])然后分出訓(xùn)練集和測(cè)試集
# 生成訓(xùn)練集,測(cè)試集for i in range(group):train_set = []test_set = []# 隨機(jī)采樣m個(gè)數(shù)據(jù)放在訓(xùn)練集中for j in ran_lis[i]:train_set.append(data_set[j])# 余下的數(shù)據(jù)放在測(cè)試集中for data in data_set:if data not in train_set:test_set.append(data)k_train_set.append(train_set)k_test_set.append(test_set) 總的程序如下: def bootstrap(data_set):m = len(data_set)group = int(input("需要多少組? "))# 生成group組隨機(jī)數(shù),每組有m個(gè),隨機(jī)數(shù)的范圍為0~m-1ran_lis = list([[random.randint(0, m-1)for i in range(m)] for j in range(group)])k_train_set = []k_test_set = []# 生成訓(xùn)練集,測(cè)試集for i in range(group):train_set = []test_set = []# 隨機(jī)采樣m個(gè)數(shù)據(jù)放在訓(xùn)練集中for j in ran_lis[i]:train_set.append(data_set[j])# 余下的數(shù)據(jù)放在測(cè)試集中for data in data_set:if data not in train_set:test_set.append(data)k_train_set.append(train_set)k_test_set.append(test_set)# 返回訓(xùn)練集、數(shù)據(jù)集組,組數(shù)return k_train_set, k_test_set, group其它讀取數(shù)據(jù)集文件,保存生成的訓(xùn)練集和測(cè)試集到文件中以及調(diào)用這三個(gè)函數(shù)的程序等其他輔助程序不在此贅述,可點(diǎn)擊此鏈接下載全部的文件。
總結(jié)
以上是生活随笔為你收集整理的机器学习:使用python生成训练集和测试集的方法实现的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: SpringBoot+Mybatis-p
- 下一篇: 异常数据剔除---格拉布斯准则(java