国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學院 > 開發設計 > 正文

K近鄰算法(三)--kaggle競賽之Titanic

2019-11-08 01:45:59
字體:
來源:轉載
供稿:網友

小白好難得會用python做第分類,實踐一下用于kaggle入門賽之泰坦尼克生還預測

問題介紹:泰坦尼克電影大家都看過,大災難過后有些人生還了,有些人卻遭遇了不信,官方提供了1309名乘客的具體信息以及提供了其中891名乘客的最后的存活情況,讓我們去預測另外418乘客的存活情況。是很基本的二分類問題。

一、數據分析

官方所給的數據長這樣:

Survived:是否存活(0代表否,1代表是)Pclass:社會階級(1代表上層階級,2代表中層階級,3代表底層階級)Name:船上乘客的名字Sex:船上乘客的性別Age: 船上乘客的年齡(可能存在 NaN)SibSp:乘客在船上的兄弟姐妹和配偶的數量Parch:乘客在船上的父母以及小孩的數量Ticket:乘客船票的編號Fare:乘客為船票支付的費用Cabin:乘客所在船艙的編號(可能存在 NaN)Embarked:乘客上船的港口( S 代表從 Southampton 登船, C 代表從 Cherbourg 登船,Q 代表從 Queenstown 登船,)

我們面臨的主要問題有兩個,一個是age和cabin存在很多缺失值(Age(年齡)屬性只有714名乘客有記錄,Cabin(客艙)只有204名乘客是已知的),很可能會影響模型性能;另一個是訓練樣本就891個,訓練集過小,很容易造成過擬合。

二、數據處理

由于影響因素太多,我們先對特征向量進行篩選。根據信息增益比進行排序畫圖(詳細知識點見《機器學習》周志華)

故我們就保留前三個影響因子。推測性別女士優先,年齡小孩優先,票價可能影響到其所在船艙而影響其存活率。

def file2matrix(filename):    fr = open(filename)    numberOfLines = len(fr.readlines())         #get the number of lines in the file    returnMat = zeros((numberOfLines,3))        #PRepare matrix to return    classLabelVector = []                       #prepare labels return       fr = open(filename)    index = 0#確保指針在最前面    for line in fr.readlines():        line = line.strip()        listFromLine = line.split(',')        if listFromLine[5]=='male':            listFromLine[5]='0'        else:            listFromLine[5]='1'        if listFromLine[6]=='':            listFromLine[6]=29.7         if listFromLine[7]=='':            listFromLine[7]=35.6                 #年齡的缺省用平均年齡29.7代替               returnMat[index,:] = listFromLine[5:8]      #對應著性別,年齡和船票價        classLabelVector.append(int(listFromLine[1]))        index += 1    return returnMat,classLabelVector#return的位置一定要找對

二、分析數據

import matplotlib  import matplotlib.pyplot as plt from os import listdirimport numpy as npdataset,classlabel=file2matrix('train1.csv')classlabel=array(classlabel)id0=np.where(classlabel==0)id1=np.where(classlabel==1)fig=plt.figure()  ax=fig.add_subplot(111) p1=ax.scatter(dataset[id1,1],dataset[id1,2],color = 'r',label='1',s=20)p0=ax.scatter(dataset[id0,1],dataset[id0,2],color ='b',label='0',s=10)plt.legend(loc = 'upper right')plt.show 

這是以年齡和船票價分的

這是以年齡和性別分的

這是以性別和船票價分的

其實這里應該繼續探討特征間的相互聯系,做集成算法。不過初步先直接選定年齡和船票價為分類標準吧(誰叫小白還不會處理定性特征值呢閉嘴

三、準備數據

歸一化數值

    def autoNorm(dataSet):          minVals = dataSet.min(0)          maxVals = dataSet.max(0)          ranges = maxVals - minVals          normDataSet = zeros(shape(dataSet))#建立框架          m = dataSet.shape[0]#行數          normDataSet = dataSet - tile(minVals, (m,1))#每個數減該列最小          normDataSet = normDataSet/tile(ranges, (m,1))   #差再除以max-min          return normDataSet, ranges, minVals  

四、測試算法

導入核心算法

def classify0(inX, dataSet, labels, k):    dataSetSize = dataSet.shape[0]#4l    diffMat = tile(inX, (dataSetSize,1)) - dataSet#inx按4*1重復排列再與sataset做差    sqDiffMat = diffMat**2#每個元素平方    sqDistances = sqDiffMat.sum(axis=1)#一個框里的都加起來    distances = sqDistances**0.5#加起來之后每個開根號    sortedDistIndicies = distances.argsort() #返回的是數組值從小到大的索引值,最小為0    classCount={}              for i in range(k):#即0到k-1.最后得到的classCount是距離最近的k個點的類分布,即什么類出現幾次如{'A': 1, 'B': 2}        voteIlabel = labels[sortedDistIndicies[i]]#返回從近到遠第i個點所對應的類        classCount[voteIlabel] = classCount.get(voteIlabel,0) + 1#字典模式,記錄類對應出現次數.這里.get(a,b)就是尋找字典classcount的a對應的值,如果沒找到a,就顯示b    sortedClassCount = sorted(classCount.iteritems(),key=Operator.itemgetter(1), reverse=True)    return sortedClassCount[0][0]測試算法

def surviorclasstest():    hoRatio = 0.10      #hold out 10%    dataset,classlabel=file2matrix('train1.csv')     #load data setfrom file    normMat, ranges, minVals = autoNorm(dataset)    m = normMat.shape[0]    numTestVecs = int(m*hoRatio)    errorCount = 0.0    for i in range(numTestVecs):        classifierResult = classify0(normMat[i,:],normMat[numTestVecs:m,:],classlabel[numTestVecs:m],3)        print "the classifier came back with: %d, the real answer is: %d" % (classifierResult, classlabel[i])        if (classifierResult != classlabel[i]): errorCount += 1.0    print "the total error rate is: %f" % (errorCount/float(numTestVecs))    print errorCount

得到

the total error rate is: 0.269這里要提到一點,此時我們可以調節K值來使錯誤率變小,實際上K值越大錯誤率越小(驗證了一下k=10時0.235,k=15時0.224,k=100時0.191)

如果選擇較小的k值,就相當于用較小的領域中的訓練實例學習,其近似誤差會小,但估計誤差會大,其泛化性能會比較差,因為預測結果會對近鄰的實例點非常敏感,即k值越小就意味著整體模型越復雜,容易發生過擬合;相對地,用較大的k值,可以減小學習的估計誤差,但是近似誤差會增大,這時與輸入實例較遠的不相似的訓練實例也會起預測作用,使預測發生錯誤,夸張一點k=N時無論輸入什么實例都返回整個訓練集占多數的類,k值越大意味著整體模型變得簡單,有可能欠擬合。在應用中,通常采用交叉驗證法來選取較優的k值。

(from《機器學習》周志華)

這里我比較懶加上之前提過這里樣本少很容易過擬合,再加上能上75%的準確率我已經很滿意啦。這里就選擇k=10吧。

五、使用算法

def classifyperson():    dataset,classlabel=file2matrix('train1.csv')    normMat, ranges, minVals = autoNorm(dataset)    testset,whatever=file2matrix('test.csv')    normMattest, rangestset, minValstest = autoNorm(testset)    h=testset.shape[0]    for i in range(h):        classifierResult = classify0(normMattest[i,:],normMat[:,:],classlabel[:],10)        print classifierResult得到一串01的序列就可以提交啦。

果然還是太粗糙,換成k=3排名立馬上升150,這臉打得好疼。

六、優化方向

1、其實性別影響很大的,后期要加入2、關于K值的選擇和過擬合問題,可以引入正則化和交叉驗證3、數據挖掘分類算法辣么多,都試試

感覺靠譜的還有邏輯回歸,決策樹和支持向量機(SVM)另外可以嘗試集成學習

另外可以Bagging :有放回的自助采樣,生成多棵決策樹訓練以及在此基礎上再引入隨機屬性,進一步增加“多樣性”(隨機森林)(據說這一串下來可以到81%)


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 额敏县| 玛沁县| 桦川县| 肇东市| 海淀区| 镇沅| 信宜市| 响水县| 四川省| 南京市| 康平县| 丰都县| 广河县| 手游| 大宁县| 星子县| 临武县| 梅河口市| 称多县| 应用必备| 彰化市| 根河市| 聂荣县| 汶上县| 阿拉善左旗| 商水县| 张家川| 紫云| 石楼县| 合川市| 聂拉木县| 高唐县| 深泽县| 石狮市| 安图县| 甘德县| 明星| 白沙| 岳普湖县| 修水县| 临城县|