機器學習A-Z~置信區間上界算法 Upper Confidence Bound or UCB

本文將要開始介紹機器學習中的強化學習, 這裏首先應用一個多臂老虎機(The Multi-Armed Bandit Problem)問題來給大家解釋什麼是強化學習。

多臂老虎機問題

如圖所示,我們有幾個單臂老虎機,組成一起我們就稱作多臂老虎機,那麼我們需要制定什麼樣的策略才能最大化得到的獎勵。這裏假設每個老虎機獎勵的隨機分佈是不一樣的。

比如第一個分佈,D1這個老虎機的分佈大概率落在中間這部分,很小概率在兩頭的地方。假設用戶是知道這些分佈的,那麼用戶應當怎麼選擇?答案很簡單,我們應當選擇D5這個老虎機,因爲它的平均值最高,而且有很大概率在靠右也就是正數範圍內。但現在的問題是,用戶實際上是不知道這些老虎機的概率分佈的。那麼我們需要一次次的嘗試,儘可能快速的找到這五個老虎機的分佈,並利用最佳的分佈最大化收益。這個在機器學習上叫做,探索利用。

探索和利用這兩步實際上並不是那麼的兼容,爲了解釋這個概念,這裏引入一個定義,叫做遺憾。也就是我們知道D5的分佈是最高的,那麼最佳策略是應對不停的選擇D5這個機器,但當我們不知道的時候,可能會選擇其他的機器,當沒有選擇最佳機器時,都會得到一個得到的獎勵和最佳獎勵的差,這個差就是遺憾。

那麼現在可以解釋爲什麼探索和利用爲什麼並不是那麼兼容,比如我們探索很多,每個機器玩了一百次,對於每個機器都能得到很好的分佈估計,但同時也會帶來很多的遺憾。如果探索比較少,可能會找不到最佳的分佈,探索得到的結論可能是錯的。所以說,最佳的策略應該是,通過探索找到最佳分佈的老虎機,並且以一種快速而高效的方法找到這個老虎機,且不斷的利用它來獲得最大化的獎勵。

在實際上生活或商業案例上也有很多相似的情形。比如可口可樂公司設計出了5個不同的廣告,那麼現在的問題就是不知道哪個廣告是最好的,能帶來最佳的用戶轉換率,即不知道哪一個投放後會吸引用戶點擊或購買產品。非常傳統的方式就是把每個廣告都投放到市場上幾天,然後看看得到的結果。但這是很消耗人力和財力的,而且這本質上只進行了探索卻沒進行利用。因此我們需要對此進行利用,比如其中某個廣告投放第一天就顯然沒有任何的效果,那麼後面幾天的投放的意義就不是很大了,可以考慮不再投放此廣告來節省人力財力。即應用強化學習可以優化成本和支出,又可以得到最高的收益。

置信區間上界算法

現在來介紹強化學習中的一個算法,叫做置信區間上界算法(UCB)。這裏依然用上述的多臂老虎機問題引出的廣告案例。

下面來描述下這個算法,現在假設我們知道五臺老虎機的分佈,那麼我們會不斷的選擇D5這個老虎機。假如說不知道這幾個的概率分佈,那麼就要開始我們的算法。

第一步,在我們開始之前,假設每個老虎機的概率分佈是相同的,即平均值或期望是相同的。如圖紅色虛線表示平均值或期望,縱軸表示老虎機可能帶來的收益。這些彩色的橫線代表每個老虎機實際的平均或期望,這些期望我們是不知道的,這個問題的核心就是我們要進行不斷的嘗試去估算出每個老虎機的平均期望。

置信區間,Confidence Bound,之前有講過Confidence Interval,這兩個詞的意義是類似的。 這個Confidence Interval指的是當我們有一定的概率分佈的時候,置信區間是和每個概率分佈的累積分佈曲線有關係。對於每個老虎機,我們講置信區間,用灰色的方框表示。對於每個老虎機,我們按的概率有很大的概率是在這個區間當中的。我們每一輪將要選擇的就是擁有最大的區間上界的老虎機,也就是頂上的這條線最大的老虎機,我們要在每一輪中選擇它並按下它。在第一輪中,他們的區間上界是一樣的。

比如選擇3號老虎機,按下去,首先會發現區間所代表的方框下降了。因爲按下去後我們會發現其給予的獎勵,3號老虎機的實際期望比較低,那麼觀察得到的獎勵也是比較低,那麼重新計算觀察到的所有平均值時,那麼這個平均值就降低了。第二點,我們會發現這個置信區間變得更小了,因爲比起上一輪的遊戲,我們總共的觀察次數變多了,也就是信心升高了,那麼這個置信區間的長度就會變小。

那麼此時第三個機器的置信區間上界比其他的要低,所以下一輪要選擇其他四個機器,比如選擇第四個,那麼它的置信區間上界會變高,區間大小會變小。

在下一步,125三個機器的上界時一樣的,因此可以在他們三個中間選一個,比如第一個,它的實際平均值比較低,但當我們按下老虎機的時候,它實際是個隨機事件,因此可能高也可能低。雖然它的平均值,但假設此時運氣比較好,投下去的錢翻倍了,那麼他的區間上限變高,長度變小。

再然後在25中間選擇一個,比如第二個,此時他的置信區間上界變低,寬度變小。

那麼最後按下第五個機器,這時得到一個非常高的觀察值,那麼上限變高,寬度變小。但由於D5實際上是最佳的機器,那麼就算置信區間變小了,但它的上界依然比其他的都要高。

那麼我接下來選擇的老虎機依然是它,當我們選擇了一個最佳的解時,我們可能在這個選擇上停留很多輪,但由於對他的信心會越來越高,因此這個區間會越來越小,此時的區間上界可能就會變成不是最高。

UCB算法有一個特點,當我們選擇了一個機器很多次後,他的置信區間會變得很小,要給其他的機器一些機會,看看其他機器顯示的觀察結果所對應的新的置信區間上界是否會更高。這樣經過很多輪後,最終D5的選擇次數依然會很多很多,他的置信區間會越來越扁,一直到最終輪。

以上就是置信區間算法的一個基本原理。

代碼實現

這裏用一個商業案例來做例子。假設有一個汽車公司爲了一個車做了十個廣告ad1-ad10,這個公司需要知道哪個廣告投放後,點擊率最高。這組數據集是在模擬環境得到的,若值爲1則指的是這個用戶點擊了這個廣告。總結一下問題就是,我們有十個廣告,要決定哪個廣告有最高的點擊率,並對逐步得到的信息來決定,第n個用戶投放哪個廣告得到最高的點擊數。我們先看看如果對於每一個用戶,我們隨機抽選廣告,會得到怎樣的點擊數。這裏提供一個隨機選擇的算法,不是此次算法的重點。

# Importing the libraries
import matplotlib.pyplot as plt
import pandas as pd

# Importing the dataset
dataset = pd.read_csv('Ads_CTR_Optimisation.csv')

# Implementing Random Selection
import random
N = 10000
d = 10
ads_selected = []
total_reward = 0
for n in range(0, N):
    ad = random.randrange(d)
    ads_selected.append(ad)
    reward = dataset.values[n, ad]
    total_reward = total_reward + reward

# Visualising the results
plt.hist(ads_selected)
plt.title('Histogram of ads selections')
plt.xlabel('Ads')
plt.ylabel('Number of times each ad was selected')
plt.show()

運行後得到的ads_selected代表對於每一個用戶,哪一個廣告被選擇,total_reward指的是所有的點擊數。得到的圖像表示每個廣告被點擊的次數。每個廣告的到點擊次數是接近的,大致在1000左右。

對於UCB算法,我們沒有直接的工具包來使用,因此需要自己實現,下面是算法邏輯:

這裏就不解釋太多,只貼代碼,最終運行後得到的總的點擊數爲2178,明顯高於上面用隨機得到的結果。且查看ads_selected會發現編號4出現的次數最多,即第五個廣告ad5。


import matplotlib.pyplot as plt
import pandas as pd
import math

# import the dataset
dataset = pd.read_csv('Ads_CTR_Optimisation.csv')

# Implementing UCB
N = 10000
d = 10
ads_selected = []
numbers_of_selections = [0] * d
sums_of_rewards = [0] * d
total_reward = 0
for n in range(0, N):
    ad = 0
    max_upper_bound = 0
    for i in range(0, d):
        if numbers_of_selections[i] > 0:
            average_reward = sums_of_rewards[i] / numbers_of_selections[i]
            delta_i = math.sqrt(3/2 * math.log(n + 1) / numbers_of_selections[i])
            upper_bound = average_reward + delta_i
        else:
            upper_bound = 1e400
        if upper_bound > max_upper_bound:
            max_upper_bound = upper_bound
            ad = i
    ads_selected.append(ad)
    reward = dataset.values[n, ad]
    numbers_of_selections[ad] = numbers_of_selections[ad] + 1
    sums_of_rewards[ad] = sums_of_rewards[ad] + reward
    total_reward = total_reward + reward

# Visualising the results
plt.hist(ads_selected)
plt.title('Histogram of ads selections')
plt.xlabel('Ads')
plt.ylabel('Number of times each ad was selected')
plt.show()

以上,就是強化學習置信區間算法的相關基礎知識。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章