险型决策的基本方法是将状态变量看成随机变量,用先验分布表示状态变量的概率分布,用期望值准则计算方案的满意程度。
但是在日常生活中,先验分布往往存在误差,为了提高决策质量,需要通过市场调查来收集补充信息,对先验分布进行修正,然后用后验分布来决策,这就是贝叶斯决策。贝叶斯理论是决策领域的一个重要分支,关于风险型决策和贝叶斯决策的理论知识,大家可以查阅相关书籍,没有电子版,这是代码学习,我就不多赘述了。
我手边有三本不同的决策课本,内容基本相当基本大同小异,因此我找了另一本《决策理论与方法》的算例来做贝叶斯决策的代码实现。
第一步验先分布。就是一个简单的sheet数据调用后比较运算。
def step1(df2):
temp1 = df2.loc[0] * df2.loc[1]
temp2 = df2.loc[0] * zeros
print('生产方案 ',temp1.sum())
print('不生产方案 ',temp2.sum())
print('验前最满意方案 ',np.maximum(temp2.sum(),temp1.sum()))
第二步预验分析
先是使用pandas的切片将需要的概率和利润分离出来。
def step2(df1,df2):
w = df2.loc[0]#w是先验概率
q = df2.loc[1]#q是利润,分别切片下来以供之后使用
然后继续使用pandas广播性质计算全概率公式和贝叶斯公式,获得最终的计算结果
temp = w * df1
p = temp.sum(1)
p = np.array(p)
print('全概率公式计算后验概率为 ',p)
pp = p.reshape(3, 1)#这里依旧用到广播必须同纬度这条性质
print(temp)
end= temp / pp
print('贝叶斯公式计算后验概率为\n ',end)
最后计算最大期望值,使用where函数可以提高效率
q = np.array(q)
qq = q.reshape(3, 1)#这里依旧用到广播必须同纬度这条性质
a= end.T*qq
a1 = a.sum()
ending = np.where(a1>zeros,a1,zeros)#计算生产和不生产综合后的最大收益
print('最大收益值和零矩阵比较,得到各方案的最大收益值\n',ending)
l=ending*p
ll= l.sum()
print('最大收益值与后验概率相乘,得到最终利润',ll)
完整代码如下,这次的代码偏向于概率论的理论知识,因此函数内部封装了很多临时变量用来计算,我特地多写了注释以供读者理解。
import pandas as pd
import numpy as np
zeros= np.zeros(3)#定义一个零矩阵之后使用
def getdef(n):
df = pd.read_excel('t6.xlsx',sheet_name=n)
return df
def step1(df):#步骤一,确定是否生产
temp1 = df.loc[0] * df.loc[1]
temp2 = df.loc[0] * zeros
print('生产方案 ',temp1.sum())
print('不生产方案 ',temp2.sum())
print('验前最满意方案 ',np.maximum(temp2.sum(),temp1.sum()))
def step2(df1,df2):#步骤二,第一个形参是销售情况概率,第二个形参是概率分布和利润
w = df2.loc[0]#w是先验概率
q = df2.loc[1]#q是利润,分别切片下来以供之后使用
temp = w * df1
p = temp.sum(1)
p = np.array(p)
print('全概率公式计算后验概率为 ',p)
pp = p.reshape(3, 1)#这里依旧用到广播必须同纬度这条性质
print(temp)
end= temp / pp
print('贝叶斯公式计算后验概率为\n ',end)
q = np.array(q)
qq = q.reshape(3, 1)#这里依旧用到广播必须同纬度这条性质
a= end.T*qq
a1 = a.sum()
ending = np.where(a1>zeros,a1,zeros)#计算生产和不生产综合后的最大收益
print('最大收益值和零矩阵比较,得到各方案的最大收益值\n',ending)
l=ending*p
ll= l.sum()
print('最大收益值与后验概率相乘,得到最终利润',ll)
if __name__ == '__main__':
step1(getdef(0))
step2(getdef(1), getdef(0))
# print(p)
# print(temp)
# print(temp/p)
# t = temp.T/p
# print(t.T)
'''
上面这一段注释代码是我在计算矩阵和一行相乘时候一开始做的方法,直接相乘
结果会产生一个可能是外积的有nah值的矩阵,并没有产生广播的效果,我将矩阵转置后,可以很
惊喜的发现,实现了广播操作,但是结果是正确答案的转置形式,我也没太想明白,把他放在这里供大家思考。
'''
github仓库在https://github.com/rivendelltom/decision-making-study