
首先放代碼
function NB(data) { this.fc = {}; //記錄特征的數(shù)量 feature conut 例如 {a:{yes:5,no:2},b:{yes:1,no:6}} this.cc = {}; //記錄分類的數(shù)量 category conut 例如 {yes:6,no:8} }NB.prototype = { infc(w, cls) { //插入新特征值 if (!this.fc[w]) this.fc[w] = {}; if (!this.fc[w][cls]) this.fc[w][cls] = 0; this.fc[w][cls] += 1; }, incc(cls) { //插入新分類 if (!this.cc[cls]) this.cc[cls] = 0; this.cc[cls] += 1; }, allco() { //計(jì)算分類總數(shù) all count var t = 0; for (var k in this.cc) t += this.cc[k]; return t; }, fprob(w, ct) { //特征標(biāo)識(shí)概率 if (Object.keys(this.fc).indexOf(w) >= 0) { if (Object.keys(this.fc[w]).indexOf(ct) < 0) { this.fc[w][ct] = 0 } var c = parseFloat(this.fc[w][ct]); return c / this.cc[ct]; } else { return 0.0; } }, cprob(c) { //分類概率 return parseFloat(this.cc[c] / this.allco()); }, train(data, cls) { //參數(shù):學(xué)習(xí)的Array,標(biāo)識(shí)類型(Yes|No) for (var w of data) this.infc(String(w), cls); this.incc(cls); }, test(data) { var ccp = {}; //P(類別) var fccp = {}; //P(特征|類別) for (var k in this.cc) ccp[k] = this.cprob(k); for (var i of data) { i = String(i); if (!i) continue; if (Object.keys(this.fc).indexOf(i)) { for (var k in ccp) { if (!fccp[k]) fccp[k] = 1; fccp[k] *= this.fprob(i, k); //P(特征1|類別1)*P(特征2|類別1)*P(特征3|類別1)... } } } var tmpk = ""; for (var k in ccp) { ccp[k] = ccp[k] * fccp[k]; if (!tmpk) tmpk = k; if (ccp[k] > ccp[tmpk]) tmpk = k; } return tmpk; }};
學(xué)習(xí)功能非常簡(jiǎn)單,只是將學(xué)習(xí)的數(shù)據(jù)進(jìn)行統(tǒng)計(jì)
代碼實(shí)現(xiàn)你可以查看代碼中的train
函數(shù)
假設(shè),某個(gè)醫(yī)院早上收了六個(gè)門診病人:
癥狀 | 職業(yè) | 疾病 |
---|---|---|
打噴嚏 | 護(hù)士 | 感冒 |
打噴嚏 | 農(nóng)夫 | 過(guò)敏 |
頭痛 | 建筑工人 | 腦震蕩 |
頭痛 | 建筑工人 | 感冒 |
打噴嚏 | 教師 | 感冒 |
頭痛 | 教師 | 腦震蕩 |
我們先統(tǒng)計(jì)記錄這些信息數(shù)據(jù):
var nb = new NB();var data=[ {d:["打噴嚏","護(hù)士"],c:"感冒"}, {d:["打噴嚏","農(nóng)夫"],c:"過(guò)敏"}, {d:["頭痛","建筑工人"],c:"腦震蕩"}, {d:["頭痛","建筑工人"],c:"感冒"}, {d:["打噴嚏","教師"],c:"感冒"}, {d:["頭痛","教師"],c:"腦震蕩"},]; for(var i of data){ nb.train(i.d, i.c);}
統(tǒng)計(jì)結(jié)果:
預(yù)測(cè)功能就要用到樸素貝葉斯算法 首先來(lái)看,貝葉斯公式: 可能你看不懂公式或看懂公式不知道公式怎么用 那我來(lái)簡(jiǎn)單的翻譯一下:
P( Category |Feature) = P ( Feature | Category ) * P( Category)/ P(Feature) 其實(shí)也是就是:
P(類別|特征)=P(特征|類別)*P(類別)/p(特征)
所以我們只要計(jì)算以下數(shù)據(jù)即可:
P(特征|類別) P(類別) p(特征)
假設(shè)兩個(gè)類別,分別是類別1,與類別2
那么類別總次數(shù)就是兩個(gè)類別出現(xiàn)次數(shù)總和
加上可能我們輸入的特征有多個(gè)假設(shè)就3個(gè)把那么也簡(jiǎn)單:
P((特征1、特征2、特征3)|類別1)= P(特征1|類別1)*P(特征2|類別1)*P(特征3|類別1) P(類別1)=類別1的次數(shù)/(類別總數(shù))P(特征1、特征2、特征3)=P(特征1)*P(特征2)*P(特征3)
因?yàn)楦鶕?jù)公式我們知道:
P(類別1|特征)=P(特征|類別1)*P(類別1)/p(特征)P(類別2|特征)=P(特征|類別2)*P(類別2)/p(特征)
剛好p(特征)
為分母所以如果比較P(類別1|特征)
與P(類別2|特征)
的概率
只要比較P(特征|類別1)*P(類別1)
與 P(特征|類別2)*P(類別2)
的大小就行了
代碼實(shí)現(xiàn)查看代碼部分的test
函數(shù)
在已經(jīng)學(xué)習(xí)了
我們預(yù)測(cè)一下打噴嚏的建筑工人是生了什么病
性別 | 身高(英尺) | 體重(磅) | 腳掌(英寸) |
---|---|---|---|
男 | 6 | 180 | 12 |
男 | 5.92 | 190 | 11 |
男 | 5.58 | 170 | 12 |
男 | 5.92 | 165 | 10 |
男 | 6 | 165 | 10 |
男 | 5.72 | 164 | 9 |
女 | 5 | 100 | 6 |
女 | 5.5 | 150 | 8 |
女 | 5.42 | 130 | 7 |
女 | 5.75 | 150 | 9 |
預(yù)測(cè)性別示例:
中文臟話測(cè)試
function defaultTokenizer(text) { // 僅保留英文、中文、數(shù)字 var rgxPunctuation = /[^(a-zA-ZA-Яa-я\u4e00-\u9fa50-9_)+\s]/g; // 英文以空格分詞,中文不分詞,以單個(gè)字為單位 return text.replace(rgxPunctuation, ' ').replace(/[\u4e00-\u9fa5]/g, function(word) { return word + ' '; }).split(/\s+/); }; // 中文測(cè)試 nb.train(defaultTokenizer('我的名字叫司馬萌.'), '正常') nb.train(defaultTokenizer('沒(méi)什么,就是一道測(cè)試程序!!'), '正常') nb.train(defaultTokenizer('不要皺眉,即使在傷心的時(shí)刻,因?yàn)槟銖牟恢烙姓l(shuí)會(huì)醉心于你的笑容。'), '正常') nb.train(defaultTokenizer('去只是一種姿勢(shì),得到并不等同于幸福。'), '正常') nb.train(defaultTokenizer('理和美女都是赤裸裸的。'), '正常') nb.train(defaultTokenizer('們看錯(cuò)了這個(gè)世界,卻說(shuō)世界欺騙了我們。'), '正常') nb.train(defaultTokenizer('們?nèi)诉@一輩子不是別人的楷模,就是別人的借鑒。'), '正常') nb.train(defaultTokenizer('萬(wàn)別說(shuō)直到永遠(yuǎn),因?yàn)槟銐焊恢烙肋h(yuǎn)有多遠(yuǎn)。'), '正常') nb.train(defaultTokenizer('些無(wú)法復(fù)制的浪漫,只能在回憶里慢慢變淡。'), '正常') nb.train(defaultTokenizer('調(diào)是永恒的美德,缺心眼的話就要學(xué)會(huì)沉默。'), '正常') nb.train(defaultTokenizer('用什么優(yōu)勢(shì)贏得人生,就會(huì)用同樣的原因輸?shù)羧松?#39;), '正常') nb.train(defaultTokenizer('人最可悲的是,有自由的思想,卻沒(méi)有沖破羈絆的勇氣。'), '正常') nb.train(defaultTokenizer('愛(ài)情就像倆個(gè)拉著橡皮筋的人,受傷的總是不愿意放手的那一個(gè)。'), '正常') nb.train(defaultTokenizer('人生的經(jīng)歷就像鉛筆一樣…開始很尖…經(jīng)歷的多了也就變得圓滑了…如果承受不了就會(huì)斷了。'), '正常') nb.train(defaultTokenizer('在你往上爬的時(shí)候,一定要保持梯子的整潔,否則你下來(lái)時(shí)可能會(huì)滑倒。'), '正常') nb.train(defaultTokenizer('人生是沒(méi)有窮盡的,所以也就沒(méi)有什么所謂的歸宿。'), '正常') nb.train(defaultTokenizer('幸福是因?yàn)槟憧吹絼e人的不幸,不幸是因?yàn)槟阒豢吹絼e人的幸福。'), '正常') nb.train(defaultTokenizer('我們的安全感,來(lái)自于充分體驗(yàn)不安全感。'), '正常') nb.train(defaultTokenizer('男人最大的武器是眼神,女人最大的武器是眼淚。'), '正常') nb.train(defaultTokenizer('心清如水即是佛,了無(wú)牽掛佛無(wú)邊。'), '正常') nb.train(defaultTokenizer('人活著為了什么?答案:一個(gè)念想。'), '正常') nb.train(defaultTokenizer('有些事遇見(jiàn)了就無(wú)法放手,有些事放開了手就不必再回首。'), '正常') nb.train(defaultTokenizer('我操,你他媽咋回事!!'), '臟話') nb.train(defaultTokenizer('你他媽整個(gè)腦殘了,不惜拿自己的父母家人來(lái)騙別人的精液。!!'), '臟話') nb.train(defaultTokenizer('跟一個(gè)你視為他為狗的人將素質(zhì),你真心逗B,腦子也秀逗了吧!'), '臟話') nb.train(defaultTokenizer('賤人的生活方式就是,只許自己吃屎,不許別人放屁。'), '臟話') nb.train(defaultTokenizer('你爹有點(diǎn)多,我忍不住笑了下,不好意思啊,你不要去想你那悲傷的母親。'), '臟話') nb.train(defaultTokenizer('我們罵不罵關(guān)你個(gè)婊子什么事,草你嗎的瞎眼白內(nèi)脹!'), '臟話') nb.train(defaultTokenizer('你他媽那么喜歡被人擦,我想說(shuō)我退出我不喜歡獸交。'), '臟話') nb.train(defaultTokenizer('我只是你祖宗而已,你怎么可以這樣,你個(gè)傻逼怎么能把你祖宗都忘記了?'), '臟話') nb.train(defaultTokenizer('你要是不扒一扒臉皮,我還真不曉得原來(lái)你的臉皮如此的厚呢!'), '臟話') nb.train(defaultTokenizer('對(duì)不起哈,當(dāng)年老子我沒(méi)忍住,一個(gè)屁把這二逼給蹦出來(lái)了!'), '臟話') nb.train(defaultTokenizer('你是腦子有病還是怎么?你以為你是誰(shuí)?不就是傻逼一個(gè)嘛!'), '臟話') nb.train(defaultTokenizer('整天把逼臉擺給別人看,是想要告訴別人你是黃世仁他媽嗎?'), '臟話') nb.train(defaultTokenizer('你是不是每次拉完屎,然后又自己舔干凈了,還到處?kù)乓约豪汉芟恪?#39;), '臟話') nb.train(defaultTokenizer('你媽是靠賣逼把你養(yǎng)大的吧,到你這代還能繼續(xù)賣逼,真的是母業(yè)女繼承啊。'), '臟話') nb.train(defaultTokenizer('難道你是吃大姨媽拌飯長(zhǎng)大的,怪不得長(zhǎng)那么惡心呢!'), '臟話') nb.train(defaultTokenizer('操你媽,日子那么難過(guò)像被人強(qiáng)奸了,但是經(jīng)典他媽說(shuō)與其掙扎不如學(xué)會(huì)享受!'), '臟話') nb.train(defaultTokenizer('就你那鳥樣還整得跟個(gè)吉娃娃賣燒烤串似得,重口味賣得都是巨根火腿吧。'), '臟話') nb.train(defaultTokenizer('你大哥拉破車、一直拉到耗子窩、耗子給你兩塊糖、你管耗子叫大娘。'), '臟話') nb.train(defaultTokenizer('就你這樣子不好好讀書,以后做雞都沒(méi)人敢要!'), '臟話') nb.train(defaultTokenizer('看你這尖嘴猴腮樣,長(zhǎng)的那么丑還每天學(xué)人家自拍,太惡心人了。'), '臟話') console.log('預(yù)期:臟話,實(shí)際:', nb.test(defaultTokenizer('我操'))); console.log('預(yù)期:正常,實(shí)際:', nb.test(defaultTokenizer('還沒(méi)使用中文分詞就分的這么棒'))); console.log('預(yù)期:臟話,實(shí)際:', nb.test(defaultTokenizer('你大爺?shù)陌?#39;))); // 臟話 console.log('預(yù)期:臟話,實(shí)際:', nb.test(defaultTokenizer('你丫有病吧'))); // 臟話 console.log('預(yù)期:正常,實(shí)際:', nb.test(defaultTokenizer('媽媽,我餓了'))); // 正常 console.log('預(yù)期:正常,實(shí)際:', nb.test(defaultTokenizer('馬克思主義')));
英文臟話測(cè)試
function defaultTokenizer(text) {
// 僅保留英文、中文、數(shù)字
var rgxPunctuation = /[^(a-zA-ZA-Яa-я\u4e00-\u9fa50-9_)+\s]/g;
// 英文以空格分詞,中文不分詞,以單個(gè)字為單位
return text.replace(rgxPunctuation, ' ').replace(/[\u4e00-\u9fa5]/g, function(word) {
return word + ' ';
}).split(/\s+/);
};
// 英文學(xué)習(xí)
// positive
nb.train(defaultTokenizer('What is your name?'), 'positive');
nb.train(defaultTokenizer('amazing, awesome movie!! Yeah!! Oh boy.'), 'positive');
nb.train(defaultTokenizer('Sweet, this is incredibly, amazing, perfect, great!!'), 'positive');
nb.train(defaultTokenizer('Do one thing at a time, and do well.'), 'positive');
nb.train(defaultTokenizer('Never forget to say “thanks”.'), 'positive');
nb.train(defaultTokenizer('Believe in yourself.'), 'positive');
nb.train(defaultTokenizer('Never put off what you can do today until tomorrow.'), 'positive');
nb.train(defaultTokenizer('Do not aim for success if you want it; just do what you love and believe in, and it will come naturally.'), 'positive');
nb.train(defaultTokenizer('Whatever is worth doing is worth doing well.'), 'positive');
nb.train(defaultTokenizer('Keep on going never give up.'), 'positive');
// foul
nb.train(defaultTokenizer('Get out !Beat it! Get lost!'), 'foul');
nb.train(defaultTokenizer('Go to hell! Go to the devil!'), 'foul');
nb.train(defaultTokenizer('Oh, hell is bells!'), 'foul');
nb.train(defaultTokenizer('You SOB (son of a)!'), 'foul');
nb.train(defaultTokenizer('You damned (disgusting) bastard!'), 'foul');
nb.train(defaultTokenizer('Idiot! You damned fool!'), 'foul');
nb.train(defaultTokenizer('Disgusting!'), 'foul');
nb.train(defaultTokenizer('I will see you in hell first!'), 'foul');
nb.train(defaultTokenizer('FUCK Fuck fuck'), 'foul');
nb.train(defaultTokenizer('You pig!'), 'foul');
nb.train(defaultTokenizer('God damn !'), 'foul');
nb.train(defaultTokenizer('Whore! Slut!'), 'foul');
nb.train(defaultTokenizer('You hypocrite!'), 'foul');
nb.train(defaultTokenizer('You ass licker (kisser)!'), 'foul');
// 判斷分類
console.log('預(yù)期:positive,實(shí)際:', nb.test(defaultTokenizer('My name is Surmon.')));
console.log('預(yù)期:positive,實(shí)際:', nb.test(defaultTokenizer('awesome, cool, amazing!! Yay.')));
console.log('預(yù)期:foul,實(shí)際:', nb.test(defaultTokenizer('get out!!!')));
console.log('預(yù)期:foul,實(shí)際:', nb.test(defaultTokenizer('Fuck!')));
作者:關(guān)愛(ài)單身狗成長(zhǎng)協(xié)會(huì)
鏈接:https://www.jianshu.com/p/5d3ea4051f67
來(lái)源:簡(jiǎn)書
版權(quán)所有?2014-2023 錦州辰碩家電維修中心 技術(shù)支持:13840665804 電話:0416-3905144 地址:錦州市古塔區(qū)中央大街26號(hào)
ICP備案/許可證號(hào):遼ICP備2023002984號(hào)-2