智駕峰會
您正在使用IE低版瀏覽器,為了您的雷鋒網賬號安全和更好的產品體驗,強烈建議使用更快更安全的瀏覽器
此為臨時鏈接,僅用于文章預覽,將在時失效
人工智能開發者 正文
發私信給skura
發送

0

如何教神經網絡玩 21 點游戲(附代碼)?

本文作者:skura 2019-10-08 18:56
導語:深度學習是否能改善 21 點游戲的策略?

如何教神經網絡玩 21 點游戲(附代碼)?

不久前,我們開發了代碼來模擬 21 點游戲。通過這些模擬,我們發現了賭場之所以具有優勢的關鍵驅動因素。主要是以下 2 點:

  • 賭場迫使玩家在莊家面前采取行動(面對的是不完整的信息),從而獲得了 21 點玩家的優勢。這首先會讓玩家面臨破產的風險(所以他們可能在莊家有機會采取行動之前就已經破產了)。

  • 當玩家的手牌值總數在 12 到 16 之間時,他們處于尤其危險的情況中(他們可能會被下一張牌打爆),而莊家則顯示出一張高數值牌。在這些情況下,假設莊家手中的牌總點數很多,則玩家要么拿牌要么不動。我們可以通過玩家在 12 到 16 之間獲勝或平局的概率來直觀地看到這一點。

如何教神經網絡玩 21 點游戲(附代碼)?

獲勝或平局的概率與玩家手中牌值總數(21 未顯示,因為概率為 100%)

最后,我們觀察到一個簡單的策略:只有在沒有機會打爆的情況下才拿牌,這大大提高了我們獲勝的幾率,因為它將打爆的風險完全轉移到了賭場。

如果你不熟悉 21 點游戲,我之前的文章描述了玩這個游戲的規則。

但是深度學習能做得更好嗎?

本文的目標是討論我們是否可以用深度學習來找到一個比上面更好的策略。我們將:

  1. 使用我們上次編碼的 BLUJACK 模擬器生成數據(通過一些修改,使其更適合于訓練算法)。

  2. 編碼訓練神經網絡玩 21 點。

如果你不熟悉神經網絡,我在這篇文章中寫過它們的簡介

如何教神經網絡玩 21 點游戲(附代碼)?


一個簡單神經網絡的視覺缺陷

在我們開始訓練之前,讓我們退一步,快速討論一下在這種情況下使用神經網絡的優缺點。神經網絡是高度靈活的算法——像軟粘土一樣,神經網絡調整自己,以適應數據的輪廓。神經網絡可以很容易地處理那些會給線性回歸等帶來麻煩的數據。此外,網絡中的層和神經元將學習數據中可能存在的任何深度嵌入的非線性關系。

然而,這種功能是有代價的——神經網絡是一個黑箱模型。與回歸不同的是,我們可以通過觀察回歸系數來了解模型是如何做出決策的,神經網絡并不具備這種透明性。此外,神經網絡也有可能把我們的數據擬合得太好,以致于不能很好地概括樣本外數據。在我看來,這些缺點值得牢記,并為其設計保護措施,但它們并不是回避使用神經網絡的理由。

生成我們的訓練數據

在訓練神經網絡之前,我們首先需要弄清楚如何構造訓練數據,這樣我們用它建立的模型才會是有用的。

我們想要預測什么?在我看來,我們的目標變量有兩個:

  1. 輸掉比賽的可能性。考慮到這種情況,我們可能希望模型告訴我們輸的概率是多少。再說一次,只有當我們可以增加或減少賭注時,這才有用,而在 21 點游戲中我們不能這樣做。

  2. 相反,我們希望我們的神經網絡能夠識別正確的動作,拿牌或不動。所以我們的目標變量應該是「正確的動作是拿牌還是不動」。

實際上我花了一段時間才找到最好的方法來設置這個。下面這是我想到的。

我們需要一種方法讓神經網絡知道給定的動作是否正確。它不需要萬無一失,只需要大體正確。所以我決定一個動作是否正確的方法是模擬 21 點游戲:把牌交給玩家和莊家,檢查是否有人有 21 點,只做一個動作(拿牌或不動),模擬游戲結束并記錄結果。由于模擬玩家只做一個決定,我們可以通過他是贏還是輸來評估這個決定的質量:

  • 如果玩家拿牌并獲勝,那么拿牌(y=1)是正確的決定。

  • 如果玩家打輸了,那么不動(y=0)是正確的決定。

  • 如果玩家不動并獲勝,那么不動(Y=0)是正確的決定。

  • 如果玩家不動并輸了,那么拿牌(y=1)是正確的決定。

這允許我們訓練出一個模型,其輸出是一個預測是拿牌或者不動。其代碼與上一次類似,因此我不會在這里給出詳細的概述(你也可以在我的 github 上找到它)。其主要特點是:

  1. 莊家的正面卡(另一張隱藏起來)。

  2. 玩家手上牌的總值。

  3. 玩家是否有王牌。

  4. 玩家的動作(拿牌或不動)。

目標變量是由上述邏輯定義的正確決策。

訓練神經網絡

我們將使用 keras 庫訓練我們的神經網絡。我們需要導入的庫文件為:

from keras.models import Sequential
from keras.layers import Dense, LSTM, Flatten, Dropout

現在我們設置輸入變量來訓練神經網絡。變量 feature_list 是一個列表,其中列有我在上面列出的特征(x 個變量)的列名。dataframe model_df 是存儲我運行的 21 點模擬的所有數據的地方。

# Set up variables for neural net
feature_list = [i for i in model_df.columns if i not in
               ['dealer_card','Y','lose','correct_action']
              ]
train_X = np.array(model_df[feature_list])
train_Y = np.array(model_df['correct_action']).reshape(-1,1)

實例化和訓練神經網絡的代碼行非常簡單。第一行(第 1 行)創建一個順序型神經網絡,它是神經網絡層的線性序列。第一行之后的代碼逐個地向我們的模型中添加層。

最后,對于最后一層,我們需要選擇一個激活函數。這將神經網絡的原始輸出轉換成我們可以解釋的東西。在最后一層需要注意兩件事。首先,它只包含一個神經元,因為我們正在預測兩種可能的結果(二分類問題)。第二,我們使用 sigmoid 函數激活,因為我們希望我們的神經網絡像邏輯回歸一樣,并預測正確的動作是拿牌(y=1)還是不動(y=0)——換句話說,我們想知道拿牌是否是正確的動作。

最后兩行告訴我們的神經網絡模型使用什么損失函數將模型匹配到我們的數據。我沒有花太多的時間來調整層數或神經元的數量,但是如果有人玩我的代碼,我會建議他對這些潛在的地方進行改進。

# Set up a neural net with 5 layers
model = Sequential()                         # line 1
model.add(Dense(16))
model.add(Dense(128))
model.add(Dense(32))
model.add(Dense(8))

model.add(Dense(1, activation='sigmoid'))    # final layer


model.compile(loss='binary_crossentropy', optimizer='sgd')
model.fit(train_X, train_Y, epochs=20, batch_size=256, verbose=1)

檢查我們模型的性能

檢查我們的模型是否增加任何值的一種快速方法是使用 ROC 曲線。ROC 曲線告訴我們,我們的模型在收益(真陽性率)和成本(假陽性率)之間的權衡情況——曲線下的面積越大,模型越好。

下面的圖片顯示了我們玩 21 點的神經網絡的 ROC 曲線——神經網絡似乎是增加了一個合理的猜測值(紅色虛線)。曲線下面積(AUC)為 0.73,明顯高于隨機猜測的 AUC(0.50)。

如何教神經網絡玩 21 點游戲(附代碼)?

21 神經網絡的 ROC 曲線

我用我的訓練數據繪制 ROC 曲線。通常我們希望使用驗證或測試數據繪制它,但在這種情況下,我們知道只要樣本足夠大,它就能代表總體(假設我們繼續使用相同的規則玩 21 點)。我們希望我們的模型能夠很好地概括任何新的數據都與訓練數據相同的基本統計特征。

玩游戲的時間到了!

在我們的神經網絡正式開始工作之前,我們需要給它一個決策規則。記住,sigmoid 激活(從我們最后的神經網絡層)使我們的神經網絡輸出一個正確的動作的概率。我們需要一個決策規則,在給定這個概率的情況下,我們決定是拿牌還是不動。

我寫了下面的函數來實現這一點——model_decision 函數具有神經網絡所需的特征,使用這些特征進行預測,并將預測與預定義的閾值進行比較,以決定是拿牌還是不動。我使用 0.52,因為我們已經從上一次就知道,對 21 點玩家來說,爆破是最大的風險。因此,使用 0.52 作為拿牌的截止值會使我們的模型爆破的可能性稍微降低,因此輸掉的可能性稍微降低。

def model_decision(model, player_sum, has_ace, dealer_card_num):
   input_array = np.array([player_sum, 0, has_ace,
                           dealer_card_num]).reshape(1,-1)
   predict_correct = model.predict(input_array)
   if predict_correct >= 0.52:
       return 1
   else:
       return 0

現在我們只需要將上面的函數添加到代碼中,在這里我們可以決定是否拿牌。因此,當決定該做什么時,神經網絡將根據莊家出示的牌、自己牌的總面值以及是否持有王牌來做出決定。

我們的模型很好!

最后,我們將神經網絡的性能與原始策略和隨機策略進行比較。需要提醒大家的是:

  • 我為每種策略類型(神經網絡、簡單和隨機策略)運行了大約 300000 個 21 點模擬實驗。

  • 簡單策略只有在沒有破發機會的情況下才出手(手牌總數低于 12 時拿牌,手牌總數為 12 或更多時才出手)。

  • 隨機的策略就像是擲硬幣——如果它出現頭部則拿牌,否則不動。如果你拿牌了,但沒有爆破,那么再擲硬幣,重新開始整個過程。

讓我們看看我們的神經網絡是否能找到更好的策略。下表顯示了每種策略類型的結果分布。我有兩件事要做。首先,我們的神經網絡在玩游戲時只損失了不到一半(49%)。我認為這是相當體面的游戲,賠率對你來說是固定的。第二,它實際上不會比簡單的策略更容易獲勝,相反,它能夠產生更多的關系。

如何教神經網絡玩 21 點游戲(附代碼)?

各種戰略的結果

我們還可以看看策略如何利用我們的主要特征(莊家的牌數和玩家手牌總值)。首先,讓我們來看看在我們的三個策略中,莊家出示的牌對獲勝或平手概率的影響。在下面的圖形中,如果莊家牌數很少,我們的神經網絡執行效果。但是當經莊家牌數更高(7或更多)時,我們的神經網絡表現得更好。

如何教神經網絡玩 21 點游戲(附代碼)?

與莊家出示的牌平手或勝出的概率(牌數越多越好!)

我們可以看看贏或平手的概率是如何隨玩家的初始牌數而變化的。這看起來很有希望——我們的神經網絡也表現得很好或者更好。與簡單的策略不同,它比玩家手牌值在 12 和 16 之間時的結果更壞,我們的神經網絡表現更好。

如何教神經網絡玩 21 點游戲(附代碼)?

平局或獲勝的概率與玩家的初始手牌值的關系

上面的圖展示了神經網絡如何超越簡單的策略。簡單的策略不愿意冒險,甚至遠離爆破風險。另一方面,神經網絡經常命中 12、13、14 或 15。這是更細微的決策,而承擔計算風險的能力似乎將它與簡單的策略區分開來。

如何教神經網絡玩 21 點游戲(附代碼)?

神經網絡和簡單策略隨玩家初始手值的變化趨勢

我們可以看看當玩家的手值總數在 12 到 16 之間時,神經網絡會做些什么來改善我們的簡單策略,以免損失太多的錢到賭場。

當莊家出示一張高值的牌(8、9 或 10)時,似乎有強烈的偏好。但是即使當莊家出示低值牌,如 3 時,神經網絡仍然在 60% 的情況下選擇拿牌——這是因為神經網絡是考慮到所有的特征然后才作出決定。因此,我們似乎不能輕易地將它的決定提煉成幾個簡單的經驗法則。

如何教神經網絡玩 21 點游戲(附代碼)?

神經網絡的拿牌頻率與莊家出示的牌值

結論

希望這篇文章給了你一個關于如何使用機器學習輔助現實生活中決策的不錯介紹。以下是當你訓練自己的模型時要記住的一些事情(不管它們是決策樹、回歸或神經網絡):

  • 我的目標變量的結構是否能讓我預測它,然后我就能解決我的問題?在你開始收集數據和構建你的模型之前,確保你的預測是正確的至關重要。

  • 新的數據和我訓練過的數據有什么不同?如果它變化很大,那么統計模型甚至可能不是你的問題的正確答案。至少,你必須認識到這一點,并建立保障措施,例如用正規化和嚴格的驗證和測試集對模型進行基準測試。

  • 無法理解模型是如何到達它的決策的,所以你沒有辦法去理解和檢驗你的模型在嚴格的測試之外做出的決策,而這些測試是在模型訓練過程中進行的。

最后一句關于 21 點的話。我可能暫時不會再寫關于賭博的文章了(我還有太多其他的話題想探討)。但是,如果有人對使用或擴展我的代碼有興趣,這里有幾個對這個項目潛在的有趣擴展:

  1. 嘗試通過更優化的神經網絡結構來改進模型,或者添加用于拆分 A 的代碼(我沒有把它構建到我原來的模擬器中),或者選擇比我使用的基本特征更好的特征。

  2. 給模型計算卡片的能力,看看它對一副牌和六副牌的性能有什么影響(這是拉斯維加斯的標準)。

希望你和我一樣發現它們的樂趣……干杯!

via:https://towardsdatascience.com/teaching-a-neural-net-to-play-blackjack-8ec5f39809e2

雷鋒網雷鋒網雷鋒網(公眾號:雷鋒網)

雷鋒網版權文章,未經授權禁止轉載。詳情見轉載須知

如何教神經網絡玩 21 點游戲(附代碼)?
分享:
相關文章

文章點評:

表情
最新文章
請填寫申請人資料
姓名
電話
郵箱
微信號
作品鏈接
個人簡介
為了您的賬戶安全,請驗證郵箱
您的郵箱還未驗證,完成可獲20積分喲!
請驗證您的郵箱
立即驗證
完善賬號信息
您的賬號已經綁定,現在您可以設置密碼以方便用郵箱登錄
立即設置 以后再說
2019087期双色球走势图