王者榮耀這么久了,還沒上王者?哈哈哈,看過來,是不是對英雄理解的不夠透徹呢,是不是還沒有很好的為英雄分類呢,今天就來看看英雄分類
技術(shù)棧
一、EM 聚類簡介
二、爬取網(wǎng)上的英雄初始屬性值
三、做成餅圖
EM 聚類簡介
EM 英文名是 Expectation Maximization,也叫最大期望算法。
在統(tǒng)計計算中,最大期望(EM)算法是在概率(probabilistic)模型中尋找參數(shù)最大似然估計或者最大后驗估計的算法,其中概率模型依賴于無法觀測的隱藏變量(Latent Variable)。
最大期望算法經(jīng)過兩個步驟交替進行計算,第一步是計算期望(E),利用對隱藏變量的現(xiàn)有估計值,計算其最大似然估計值;第二步是最大化(M),最大化在 E 步上求得的最大似然值來計算參數(shù)的值。M 步上找到的參數(shù)估計值被用于下一個 E 步計算中,這個過程不斷交替進行。
在此推薦小編創(chuàng)建的Python學習交流群:835017344,這里是python學習者聚集地,有大牛答疑,有資源共享!有想學習python編程的,或是轉(zhuǎn)行,或是大學生,還有工作中想提升自己能力的,正在學習的小伙伴歡迎加入學習。
進行英雄聚類
使用 sklearn 庫中的的 EM 聚類算法框架,采用高斯混合模型
from sklearn.mixture import GaussianMixture
復制代碼
一些主要參數(shù)意義如下,其他參數(shù)可以查看相關(guān)文檔
-
n_components:混合高斯模型個數(shù),也就是想要的聚類個數(shù),默認為1
-
covariance_type:協(xié)方差類型,包括{‘full’,‘tied’, ‘diag’, ‘spherical’}四種,分別對應(yīng)完全協(xié)方差矩陣(元素都不為零),相同的完全協(xié)方差矩陣(HMM會用到),對角協(xié)方差矩陣(非對角為零,對角不為零),球面協(xié)方差矩陣(非對角為零,對角完全相同,球面特性),默認‘full’ 完全協(xié)方差矩陣
-
max_iter:最大迭代次數(shù),默認100
所以可以構(gòu)造 GMM 聚類如下:
# 構(gòu)造 GMM 聚類
gmm = GaussianMixture(n_components=20, covariance_type='full')
復制代碼
有一份如下結(jié)構(gòu)的數(shù)據(jù):
[圖片上傳中...(image-5dab6a-1562219826453-6)]
可以看到,涉及到的屬性非常多,初始的屬性設(shè)置如下:
feature = ['1級物理攻擊', '15級物理攻擊', '每級成長',
'1級生命', '15級生命', '生命成長值', '1級物理防御',
'15級物理防御', '每級物理防御成長', '攻速成長',
'1級每5秒回血', '15級每5秒回血', '1級最大法力',
'15級最大法力', '最大法力成長', '1級每五秒回藍',
'15級每5秒回藍', '近/遠程?', '移速', '定位', '個人建議分路']
復制代碼
屬性降維
可以先通過熱力圖來判斷下哪些屬性是強相關(guān)的,只保留唯一屬性
import seaborn as sns
import matplotlib.pyplot as plt
corr = data[feature].corr()
plt.figure(figsize=(14, 14))
sns.heatmap(corr, annot=True)
plt.show()
復制代碼
[圖片上傳中...(image-232849-1562219826453-5)]
可以看到,其中”1級最大法力“,”15級最大法力“,”最大法力成長“,是強相關(guān)的,由此可以做出屬性篩選,最終保留的屬性如下:
features_remain = ['15級生命', '15級物理攻擊',
'15級物理防御', '15級最大法力',
'15級每5秒回血', '15級每5秒回藍', '移速',
'攻速成長', '近/遠程?']
復制代碼
數(shù)據(jù)規(guī)范化
將攻擊范圍字段(”近/遠程?“)轉(zhuǎn)換為 0 和 1
data_new['近/遠程?'] = data_new['近/遠程?'].map({'遠程': 1, '近程': 0})
復制代碼
EM 聚類計算
采用高斯混合模式,并把生成的類別寫入 csv 文件中
# 構(gòu)造 GMM 聚類
gmm = GaussianMixture(n_components=20, covariance_type='full')
gmm.fit(data_new)
# 訓練數(shù)據(jù)
prediction = gmm.predict(data_new)
# print(prediction)
hero_data.insert(0, '分組', prediction)
hero_data.to_csv('hero_out.csv', index=False, sep=',', encoding='gb18030')
復制代碼
餅圖輸出
為了更加直觀的查看各個英雄的分組情況,這里使用餅圖來做可視化 首先取出數(shù)據(jù)的”分組“和”名稱“兩個字段,并對”分組“字段進行分組處理
df = hero_data[['分組', '名稱']]
grouped = df.groupby(['分組'])
復制代碼
然后取出分組中的數(shù)值,并用 pyecharts 來畫餅圖
from pyecharts import Pie
k = []
for name, group in grouped:
k.append({name: list(group['名稱'].values)})
kk = []
for i in k:
for k, v in i.items():
kk.append(v)
length = []
key = []
for i in kk:
key.append(str(i))
length.append(len(i))
pie = Pie('英雄完全屬性分類圖', title_pos='center')
pie.add("", key, length,
is_label_show=True, legend_pos="bottom", legend_orient="vertical",)
pie.render()
復制代碼
[圖片上傳中...(image-3be250-1562219826453-4)]
抓取英雄初始屬性
要想獲得更加全的英雄數(shù)據(jù),還是需要到網(wǎng)上抓取,這樣才能夠保證英雄的數(shù)量是最新的。這里我使用的是 db.18183.com/ 網(wǎng)站的數(shù)據(jù),頁面如下:
[圖片上傳中...(image-9bb357-1562219826453-3)]
[圖片上傳中...(image-ce0f68-1562219826453-2)]
獲取英雄頁面 URL
使用 BeautifulSoup 來定位到 class 為 mod-iconlist 的 ul 元素,里面保存的就是各個英雄的頁面
url = 'http://db.18183.com/'
url_list = []
res = requests.get(url + 'wzry').text
content = BeautifulSoup(res, "html.parser")
ul = content.find('ul', attrs={'class': "mod-iconlist"})
hero_url = ul.find_all('a')
for i in hero_url:
url_list.append(i['href'])
復制代碼
抓取詳細信息
循環(huán)抓取到的 URL 列表,抓取每個英雄的詳細信息
base_url = 'http://db.18183.com/'
detail_list = []
for i in url:
# print(i)
res = requests.get(base_url + i).text
content = BeautifulSoup(res, "html.parser")
name_box = content.find('div', attrs={'class': 'name-box'})
name = name_box.h1.text
hero_attr = content.find('div', attrs={'class': 'attr-list'})
attr_star = hero_attr.find_all('span')
survivability = attr_star[0]['class'][1].split('-')[1]
attack_damage = attr_star[1]['class'][1].split('-')[1]
skill_effect = attr_star[2]['class'][1].split('-')[1]
getting_started = attr_star[3]['class'][1].split('-')[1]
details = content.find('div', attrs={'class': 'otherinfo-datapanel'})
# print(details)
attrs = details.find_all('p')
attr_list = []
for attr in attrs:
attr_list.append(attr.text.split(':')[1].strip())
detail_list.append([name, survivability, attack_damage,
skill_effect, getting_started, attr_list])
復制代碼
保存到 csv 文件
open 一個文件,把對應(yīng)的列表字段存入
with open('all_hero_init_attr.csv', 'w', encoding='gb18030') as f:
f.write('英雄名字,生存能力,攻擊傷害,技能效果,上手難度,最大生命,最大法力,物理攻擊,'
'法術(shù)攻擊,物理防御,物理減傷率,法術(shù)防御,法術(shù)減傷率,移速,物理護甲穿透,法術(shù)護甲穿透,攻速加成,暴擊幾率,'
'暴擊效果,物理吸血,法術(shù)吸血,冷卻縮減,攻擊范圍,韌性,生命回復,法力回復\n')
for i in details:
try:
rowcsv = '{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{},{}'.format(
i[0], i[1], i[2], i[3], i[4], i[5][0], i[5][1], i[5][2], i[5][3], i[5][4], i[5][5],
i[5][6], i[5][7], i[5][8], i[5][9], i[5][10], i[5][11], i[5][12], i[5][13], i[5][14], i[5][15],
i[5][16], i[5][17], i[5][18], i[5][19], i[5][20]
)
f.write(rowcsv)
f.write('\n')
except:
continue
復制代碼
數(shù)據(jù)清理
因為這個網(wǎng)站可能做的不是很用心,有些屬性會存在兩個百分號和為空的情況,如圖:
[圖片上傳中...(image-ced2dd-1562219826452-1)]
所以需要處理下。
對于兩個百分號,直接使用 notepad++ 把所有的 %% 的替換為單 % 即可
對于為空的字段,使用如下代碼處理,填為 0
# 把空值設(shè)置為0
data_init = data_init.fillna(0)
復制代碼
完成
對于數(shù)據(jù)規(guī)范化,GMM 聚類和餅圖呈現(xiàn),都和前面類似,不再贅述,下面來看看餅圖效果
[圖片上傳中...(image-13f8ec-1562219826452-0)]
雖然通過這兩張餅圖,沒有辦法一下子提高你手殘的毛病,但是明確了英雄的分類,不是離王者更近了一步嗎
更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號聯(lián)系: 360901061
您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對您有幫助就好】元
