《使用Python介绍博弈论》
使用博弈论来提升我的Python技能和开发函数的直觉
什么是博弈论?在肯·宾莫尔Ken Binmore的书《Playing for Real: A Text on Game Theory》中,他将其描述为对人群中的理性互动的研究。
基本上,每当你与他人打交道,你都在进行一场博弈。我第一次接触博弈论是在一门微观经济学入门课程中。它似乎相当奇怪,不太直观。
几年后,我参加了一门高级博弈论课程。这门课程涉及大量的数学符号、图表和痛苦。
与我在计量经济学和计算经济学课程中接触到的编程分别是R和Julia不同,我在学习博弈论时没有写过一行代码。
回顾起来,我在那门课程中培养的技能在我的数据科学之旅中给我带来了巨大的好处。
我决定重新学习博弈论,并将其用于提升我的Python技能并回忆一下那段痛苦的时光。
让我们从经典例子开始:囚徒困境 The Prisoner's Dilemma
我们的两名玩家是朱利安Julian和兰迪Randy。
他们都被逮捕并带到警察局,然后分开关进不同的审讯室。审订他们的侦探没有足够的证据,他们需要一份自白供词。以下是我们玩家的策略和回报:
如果一个玩家坦白而另一个保持沉默,告密者将被释放,而另一名玩家将服刑10年。
如果两名玩家都遵守规则并保持沉默,每名玩家都将因虚假指控而入狱一年。
如果两名玩家互相告密,他们都将被判刑九年(因两人合作而减刑一年)。
我们将保持沉默称为“鸽子策略”,而互相告密称为“鹰策略”
使用Python来创建朱利安的回报矩阵:
import numpy as np
import pandas as pd
# 创建包含朱利安回报的数组
x = np.array([[-1, -10],[0, -9]])
# 重新标记行和列
jpm = pd.DataFrame(x, columns=['鸽子', '鹰'])
jpm.index = ['鸽子', '鹰']
jpm
Out[1]:
dove hawk
dove -1 -10
hawk 0 -9
#中文
-----------
鸽子 鹰
鸽子 -1 -10
鹰 0 -9
朱利安由行表示,而兰迪由列表示。例如,如果朱利安选择鹰而兰迪选择鸽子,朱利安的回报是-10(他入狱的年数)。
如果朱利安选择鹰而兰迪选择鹰,朱利安的回报是0(不入狱)。
现在让我们创建兰迪的回报矩阵。为了实现这一点,我们需要交换行和列,因为兰迪的回报矩阵是朱利安的转置。
装置操作在Python中非常容易实现:
# 创建兰迪的回报矩阵
# 记住,兰迪的回报矩阵是朱利安的转置
rpm = jpm.T
rpm
Out[2]:
dove hawk
dove -1 0
hawk -10 -9
#中文
-----------
鸽子 鹰
鸽子 -1 0
鹰 -10 -9
另一种创建回报矩阵的方法是使用nashpy包,如下所示:
# 朱利安的回报(行玩家)
x = np.array([[-1, -10],[0, -9]])
# 兰迪的回报(列玩家)
y = x.T
import nashpy as nash
Prisoners_Dilemma = nash.Game(x, y)
#囚徒困境
Prisoners_Dilemma
#x,y输入变量下的囚徒困境
Row player:
[[ -1 -10]
[ 0 -9]]
Column player:
[[ -1 0]
[-10 -9]]
现在是创建回报表的时候了。
回报表是一个包含朱利安和兰迪回报矩阵的双矩阵。首先,我会在下面绘制它:
dove hawk
dove [-1, -1] [-10, 0]
hawk [0, -10] [-9, -9]
朱利安的回报是第一个数字,兰迪的回报是第二个数字。所以,如果朱利安选择鹰,兰迪选择鸽子,那么回报是多少?
如果你选择(0, -10),很好!
回报表显示了每个玩家在给定他们的策略和对手策略的情况下的回报。回报表在绘制时看起来很漂亮,但让我们使用quantecon包在Python中创建它:
import quantecon as qe
# 创建一个包含两名玩家回报的列表
pt = [[(-1,-1), (-10,0)], [(0,-10), (-9,-9)]]
g = qe.game_theory.NormalFormGame(pt)
print(g)
[[[ -1, -1], [-10, 0]],
[[ 0, -10], [ -9, -9]]]
你可能已经注意到上面的回报列表通过一个叫做NormalFormGame
的函数传递(它也在输出中)。
囚徒困境代表了一个正常形式博弈。那是什么,你会问?它包括以下三个条件:
一组玩家(朱利安和兰迪)
每个玩家的一组策略(鸽子,鹰)
对于每个玩家,他们对策略概要集合有偏好
一个快速的提示,策略和策略概要不是相同的。策略概要是包含每个玩家一个策略的列表。想象一下石头、纸和剪刀游戏。
策略概要包括:(石头,石头),(纸,石头),(剪刀,石头)等等。
我们游戏的策略概要如下:{(鸽子, 鸽子), (鸽子, 鹰), (鹰, 鸽子), (鹰, 鹰)}
现在我们理解了策略和回报,我们可以编写一个函数来进一步明确我们的理解:
# 编写回报函数
def payoff_function (x=str, y=str):
if x == '鸽子' and y == '鸽子':
print('朱利安 {}'.format(-1),':','兰迪 {}'.format(-1))
elif x == '鸽子' and y == '鹰':
print('朱利安 {}'.format(-10),':','兰迪 {}'.format(0))
elif x == '鹰' and y == '鹰':
print('朱利安 {}'.format(-9),':','兰迪 {}'.format(-9), ':', "纳什均衡")
else:
print('朱利安 {}'.format(0),':','兰迪 {}'.format(-10))
我们前面确定了策略概要(鹰,鸽子)=(0,-10)。如果我们正确编写了函数,那应该是我们的输出:
payoff_function('鹰', '鸽子')
朱利安 0 : 兰迪 -10
就这样!但现在的问题是,我们游戏中的代理如何最大化他们的偏好?看起来朱利安和兰迪都会受益于保持嘴巴紧闭。
然而,每个玩家面临相同的回报和策略。记住,这个游戏是同时进行的。
每个玩家通过选择鹰来最大化他们的回报(这是任何一名玩家都可以避免被关进监狱的唯一方式)。
因此,如果我们的玩家是理性的并寻求最大化他们的偏好,他们将始终选择鹰。用古怪的经济术语来说,鹰严格支配鸽子。
因此,我们游戏的结果将是(鹰,鹰)。这代表了纳什均衡:
payoff_function('鹰', '鹰')
朱利安 -9 : 兰迪 -9 : 纳什均衡
说这篇博客只是浅尝辄止,仅仅对博弈论的轻描淡写。然而,相信博弈论背后的直觉是对于成功进行数据科学所需思维方式的补充。
本文由 mdnice 多平台发布