DOTA2先幹掉中路一塔後有多大勝算?
來自專欄數據冰山
上回在冰山發布的《TI7傷害之王》和《TI7小組賽英雄數據報告》收到冰友反饋:
- 遊戲數據介面API如何調用?我沒有編程基礎,感覺很難的樣子。
- 能不能給一些具體的例子,能一步一步學著操作的那種。
- 內容可以再豐富一點嗎?
我是過來人,道理我都懂。大家其實是希望我給一個故事完整、過程清晰、內容詳實的DOTA2數據分析例子,這樣學起來才會有順藤摸瓜的感覺,比起摸著石頭過河,能夠少踩一些坑。
既然如此,我也只好收拾一下自己的懶癌,再滿足大家一次。
本文敘述結構按照數據分析師的工作流程來:
- 提一個值得分析的問題(中路一塔到底有多重要?)
- 獲取數據源(手把手演示如何使用python調用API獲取需要的數據)
- 確定方法論(統計推斷statistical inference),處理數據,得出結論
【注意:在數據分析師的實際工作過程中,順序可能顛倒,也可能重複多次】
一、提一個好問題
會提問、提好問,是數據分析師最重要的技能之一。
大家平時聽講座,經常看到演講者眼冒精光的對某個提問者說:「你這個問題提的非常好!很有水平!(加雞腿)」。演講者覺得問題好,是因為這個問題觸及了事情的本質,回答好這個問題,就可以把事情說清楚。
和他問自答的演講者相比,自問自答的數據分析師自由度更高,更需要借一雙慧眼,在紛繁複雜的數據和千頭萬緒的可能性之中,找到最接近真相的那些問題。
本文提出的問題是:DOTA2這款免費遊戲的中路一塔有多重要?
喜歡看比賽的朋友,對這個問題應該不陌生。主播解說比賽時經常講:這個中路一塔絕對不能放!這個塔放了之後,視野黑一大片,活動範圍減小,打錢空間被壓縮...就不好打了!那麼,主播們說的對嗎?如何衡量中路一塔的重要性?
在DOTA2的世界裡,所謂「重要」,只有兩個字:能贏。比如刀塔中最重要的建築毫無疑問是基地——因為基地一炸,比賽就結束了。如果我們可以把「先拆掉敵方中路一塔」和「比賽勝負」聯繫起來,就可以得出答案。按這個思路,對每場比賽,我們需要的數據是:
- 哪一方先拆掉敵方中路一塔
- 哪一方贏得了比賽
二、獲取數據源
如何獲取一場比賽的「拆塔信息」和「比賽勝負」?
上篇文章講過,可以調用OPENDOTA提供的API來獲取公開比賽數據。查閱API介面文檔後,發現有一個名叫matches的api提供了一場比賽(match)的詳細信息。我們需要的數據很可能在api返回的結果里。
我們不妨找一場比賽調用這個API試一下(反正又不要錢),看看它到底提供了哪些數據。以剛剛結束的長沙MDL MAJOR最後一場比賽為例(LGD奪冠那場),它的比賽編號(也就是調用api要傳入的參數:match_id)是3903099199。
?同學們不要緊張,現在還不用寫代碼。
這種webapi是可以在瀏覽器中調用的。只需要按API的介面說明構建出網址https://api.opendota.com/api/matches/3903099199,然後把鏈接複製到你常用的瀏覽器中,按回車就可以得到結果:
為什麼數據這麼多?平時打完一局DOTA2,賽後統計數據沒這麼多啊?
同學們不要緊張。Opendota提供的matches介面,不僅返回了「基礎賽後統計數據」,還包含了許多「通過解析錄像得到的遊戲中數據」。以防禦塔數據為例,基礎的賽後統計數據只能告訴你比賽結束時,雙方隊伍的防禦塔存亡狀態(哪些拆掉了,哪些還在);而解析錄像得到的遊戲中數據,可以告訴你每座塔是什麼時候被誰拆掉的。
如果你願意,你甚至可以通過解析錄像知道拆塔的過程中,每一個英雄每一下A出了多少傷害。也就是說,DOTA2這款遊戲的數據源很開放(其他類DOTA遊戲沒法比),這也正是我在市面上已經有非常多數據分析入門教程的前提下,執意要寫「DOTA2數據分析入門」教程的原因——因為對大家來講,那些教材使用的數據源都不對口,學起來很容易半途而廢(特別是基礎不好的朋友)。而DOTA2這款遊戲內涵豐富,可以分析的維度很多,如果你本身是一名刀塔玩家,使用DOTA2數據源來學習數據分析,學習過程一定會很愉快。
比如,當你看到上圖中的「"radiant_win":false」時,你一定會知道radiant表示天輝,所以radiant_win就是天輝勝利,合起來就是:天輝勝利為假,那就是夜魘(Dire)獲勝咯!(如果不放心,你可以找第三方數據產品驗證一下)
是不是很簡單?
接下來我們在API返回的結果中尋找第二個數據「拆塔信息」。經過一番折騰(比如搜索關鍵字"tower"或者"building"),我們可以發現數據出現了一些奇怪的東西:
- npc_dota_goodguys_tower1_mid
- npc_dota_badguys_tower1_mid
- npc_dota_goodguys_tower2_bot
- npc_dota_goodguys_tower3_top
tower1是什麼鬼?一塔?midot op是中塔下塔上塔?那goodguys和badguys是不是天輝和夜魘???
是的,上面的猜測都是對的,V社就是這麼任性(不好好用radiant,還要搞個goodguys...)。
所以,上圖中的兩條拆塔信息是:
- 名叫npc_dota_hero_gyrocopter(矮人直升機)的單位,於20分10秒,拆掉(反補)了天輝方的中路一塔。
- 名叫npc_dota_hero_gyrocopter(矮人直升機)的單位,於20分37秒,拆掉了夜魘方的中路一塔。
如果你不放心,仍然可以用第三方數據產品(DOTABUFF、OPENDOTA、刀魔數據等)來驗證數據的準確性:
OK,到現在為止,我們終於獲取了LGD對陣VGJ.S的第三局所有想要的信息:夜魘方先拆掉天輝方的中路一塔,夜魘獲勝。
但是,使用瀏覽器調用介面,人工統計信息的操作會很麻煩(比如你想查詢100場比賽的信息,估計眼睛都要看瞎)。
接下來我們必須開始寫代碼了。關於代碼有兩點說明:
- 本系列教程不會教大家寫代碼,請自行學習python、requests、notebook等編程知識(自律且時間充裕的朋友,可以Google搜關鍵字自學;基礎太差或者想有人一起學的朋友,可以考慮報網課,比如「優達學城(Udacity)」)
- 文中用到的所有代碼,都會放在GitHub上(repository叫dota2_analysis_tutorial)。給大家作為參考~
寫代碼的時候,我們可以再簡化一下,把「拆塔和比賽勝負的聯繫」用一個bool類型表示。比如我們可以寫一個名叫is_destroy_mid_tower_induce_win的函數,對每一場比賽(用match_id標識)返回:
- True,表示先拆掉敵方中路一塔的隊伍,取得了勝利
- False,表示先拆掉地方中路一塔的隊伍,遭受了失敗
- None,表示獲取不到數據(錄像損壞或者解析出錯)
三、處理數據,得出結論
孤證不立,一場比賽的情況不足以反映規律,我們需要看更多比賽的數據。DOTA2進入7.0時代以來,一共打了13574場職業比賽(可用下圖的SQL在OpenDota - Dota 2 Statistics上查詢)。
難道我們要把1萬3千多場比賽的信息都弄下來?這樣做確實可以,但是太耗時間了——OpenDota提供的API限制訪問速度是1分鐘60次,也就是需要4個小時才能獲取這些比賽的信息(而且代碼沒有處理網路異常,很有可能跑到一半就GG了,重來又是4小時...)
怎麼辦?這個時候就需要一些統計學知識了。我們先隨機抽取200場比賽看看情況。
200場比賽的結果是這樣的:
- 93場比賽無法獲得「拆塔信息」數據,屬於無效樣本。
- 剩下的107場比賽中,先拆掉敵方中一塔獲勝的場次是67場,67/107=62.6%。
62.6%!意思是只要先拆掉敵方中一塔,就有6成以上的勝率?不好說,因為這只是107場比賽的數據(總共有1萬多場比賽),比如我們再重新抽107場比賽,結果很可能會不一樣。那麼問題來了,這個62.6%的可信度有多高?
這需要用到「統計推斷」的知識(推薦一本書《OpenIntro Statistics》)。我們採樣的每場比賽之間相互獨立,同時正負樣本的數量都大於10(說明採樣結果的分布沒有嚴重偏曲)。根據「中心極限定理」,採樣結果的分布近似服從正態分布。
先算出標準差為0.047,然後算出95%置信區間為[53.4%, 71.8%]。也就是說,根據107場抽樣比賽來看,我們有95%的把握:先拆掉敵方中路一塔的隊伍,獲勝概率在53.4%~71.8%之間。
但是這個結論太粗糙了,只能說明先拆掉中路一塔是件好事(獲勝概率>50%),但無法說清楚這件事到底有多好(53%和71%的差距還是很大的)。
為了縮小置信區間的寬度使估計值更精確,我們可以增加樣本數量:
- 隨機抽取223場比賽(先拆掉中路一塔的隊伍獲勝場次為142,142/223=63.7%),獲勝概率的95%置信區間為[57.4%, 70%]
- 隨機抽取528場比賽(先拆掉中路一塔的隊伍獲勝場次為347,347/528=65.7%),獲勝概率的95%置信區間為[61.7%, 69.8%]
- 隨機抽取1979場比賽(先拆掉中路一塔的隊伍獲勝場次為1280,1280/1979=64.7%),獲勝概率的95%置信區間為[62.6%, 66.8%]
- ...
不需要更多的樣本了——當樣本數量為2000場時,我們已經可以很自信的說(95%的概率):先拆掉中路一塔的隊伍,具有一定的優勢,獲勝概率在62.6%~66.8%之間。
那麼問題又來了,這64.7%左右的勝率算高嗎?(老隊長:我就問你有什麼影響?)到目前為止,我們可以用於比較的參考值只有「先拆掉基地的勝率為100%」,沒啥意義,但我們完全可以用相同的方法論給出更多、更有意義的benchmark(基準):【以下都是95%置信區間】
- 拿到第一個肉山盾的隊伍,獲勝概率是[73.5%,77.3%]
- 拿到一血的隊伍,獲勝概率是[52.7%, 57.1%]
- 先拆掉第一座防禦塔(上中下任意一座)的隊伍,獲勝概率是[59.4%,63.7%]
有了對比,我們就可以得出結論:中路一塔的戰略地位確實高於邊路一塔(只要先於敵方拆掉中一塔,就能建立優勢,提升勝率),但也沒有特別重要(不如第一個肉山盾)。
寫到這裡,一個完整的數據分析例子就算完成了。但「完整」並不代表「完結」:
- 從深度上來講:大家可以對比分析中一塔被拆掉前後,有沒有影響隊伍的打錢速度、活動範圍?找出中一塔具體的影響因素,從而在實戰中調整策略。
- 從廣度上來講:大家可以加入戰隊、版本號等維度,對樣本進行拆分,描述中一塔戰略地位的變化和隊伍風格。
當然,我覺得更好的學習方法是:從興趣出發,找到自己認為有意義問題,用相同的方法論處理數據,得出結論。
ps. 新晉奶爸,工作繁忙,每篇文章耗時幾十個小時,本系列教程爭取能「月更」吧。
希望能對大家有一些幫助~
5-24更新,回復兩個觀點:
第一,質疑「置信區間的解釋有誤」。我重新讀了一下文章,確實表述有誤。文中「根據107場抽樣比賽來看,我們有95%的把握:先拆掉敵方中路一塔的隊伍,獲勝概率在53.4%~71.8%之間。」應該換成「如果重複使用該方法計算無數個置信區間,則有95%的置信區間包含獲勝概率」。按照 @何明科 @張戎 的建議,換一個方式敘述:「拆掉中路一塔之後的勝率」,是一個確定的數字,但是只有上帝知道,我們人類無法知道(擲硬幣出正面的概率也是這樣)。但是,我們人類可以利用「統計推斷」,划出置信區間,讓這個上帝才能知道的概率有95%的機會落在區間內。【置信區間的解釋是複雜的、一定程度上偏離人類直覺概念的。感謝評論中 @老胡 的評論,我又漲知識了~】
第二,「因果關係(Causal)還是相關關係(Correlation )」,有讀者質疑「文章只能說明有相關性不能說明因果關係,可能只是隊伍實力更強->更早拆塔->更容易取得勝利」,質疑「先拿到肉山盾,比賽獲勝概率更高,但肉山盾不見得是比賽獲勝的原因(不一定戰略地位更高),也可能是實力強、裝備好的一方更容易獲取肉山盾,所以更容易贏得比賽」。回應一下:本文原本只想進行描述性的分析(拿到第一個肉山盾的隊伍,獲勝概率是[73.5%,77.3%]),不報告推論性統計(中路一塔很重要,優先拆掉勝率更高)。但是,確實也使用了一些帶有推斷含義的語句,比如「中路一塔的戰略地位確實高於邊路一塔(只要先於敵方拆掉中一塔,就能建立優勢,提升勝率),但也沒有特別重要(不如第一個肉山盾)」。這樣就不可避免的要回答一個問題:到底存在「因果關係」嗎?(這裡必須說明一點,我贊同「不存在100%的因果關係」的觀點,比如牛頓萬有引力也會被推翻、失效)。所以,我要說明的是:本文沒有證明因果關係,我也不知道要如何證明(無法設計隨機單盲對照實驗)。但是從應用上來講,我個人覺得這種相關關係,可以當成結論來用。當然也可以向大家說的那樣,繼續控制變數,深挖下去~
?
?
推薦閱讀:
※聊聊CMEG2017國家級移動電競賽事
※China Dota2 Supermajor - 首日回顧
※創造歷史!TYLOO2-0完勝牛仔晉級4強
※職業選手clearlove到底強在哪裡?
※The Bucharest Major - 第二日回顧