贝叶斯ADAPTive实验设计
项目描述
BADAPTED:贝叶斯ADAPTive实验设计
状态:工作代码,但仍在开发中 🔥
运行高效的贝叶斯自适应实验。
此代码与以下预印本相关。但是,当最终发表时,预印本可能以相当不同的形式出现。
Vincent, B. T., & Rainforth, T. (2017, October 20). The DARC Toolbox: automated, flexible, and efficient delayed and risky choice experiments using Bayesian adaptive design. Retrieved from psyarxiv.com/yehjb
在badapted
之上构建自己的自适应实验工具箱
以下我们将概述如何使用badapted
包运行自适应实验。仅凭自身,此badapted
包不会做任何事情。它还需要一些类(以及可能的一些辅助函数),开发者必须为其特定的实验范式创建这些类。这形成了一个“工具箱”,将允许在特定的实验领域中运行自适应实验。
这个例子(第一个例子)是我们的DARC工具箱,它允许进行延迟和风险选择任务的适应性实验。
但以下我们将概述如何为您感兴趣的实验领域创建一个新的“工具箱”。
步骤1:定义设计空间
首先,我们使用我们编写的函数创建一个名为designs
的pandas dataframe。每一列是一个设计变量。每一行是一个特定的设计。
def build_my_design_space(my_arguments):
designs = # CREATE PANDAS DATAFRAME OF THE DESIGN SPACE HERE
return designs
步骤2:定义自定义设计生成器
为了生成自己的设计生成器,该生成器使用贝叶斯自适应设计(在您的实验领域),则需要创建一个继承自badapted.BayesianAdaptiveDesignGenerator
的类。您还需要实现一些特定于您的实验领域的方法,特别是
将设计响应添加到数据框
df_to_design_tuple
目前,我们将仅提供我们在DARC工具箱中使用的示例。首先,我们的具体设计生成器类定义如下
from badapted.designs import BayesianAdaptiveDesignGenerator
class BayesianAdaptiveDesignGeneratorDARC(DARCDesignGenerator, BayesianAdaptiveDesignGenerator):
'''This will be the concrete class for doing Bayesian adaptive design
in the DARC experiment domain.'''
def __init__(self, design_space,
max_trials=20,
allow_repeats=True,
penalty_function_option='default',
λ=2):
# call superclass constructors - note that the order of calling these is important
BayesianAdaptiveDesignGenerator.__init__(self, design_space,
max_trials=max_trials,
allow_repeats=allow_repeats,
penalty_function_option=penalty_function_option,
λ=λ)
DARCDesignGenerator.__init__(self)
请注意,这具有多重继承,所以我们还有一个名为DARCDesignGenerator
的类,它仅包含DARC特定方法(add_design_response_to_dataframe
,df_to_design_tuple
)。这被定义为
from badapted.designs import DesignGeneratorABC
from darc_toolbox import Prospect, Design
class DARCDesignGenerator(DesignGeneratorABC):
'''This adds DARC specific functionality to the design generator'''
def __init__(self):
# super().__init__()
DesignGeneratorABC.__init__(self)
# generate empty dataframe
data_columns = ['RA', 'DA', 'PA', 'RB', 'DB', 'PB', 'R']
self.data = pd.DataFrame(columns=data_columns)
def add_design_response_to_dataframe(self, design, response):
'''
This method must take in `design` and `reward` from the current trial
and store this as a new row in self.data which is a pandas data frame.
'''
trial_data = {'RA': design.ProspectA.reward,
'DA': design.ProspectA.delay,
'PA': design.ProspectA.prob,
'RB': design.ProspectB.reward,
'DB': design.ProspectB.delay,
'PB': design.ProspectB.prob,
'R': [int(response)]}
self.data = self.data.append(pd.DataFrame(trial_data))
# a bit clumsy but...
self.data['R'] = self.data['R'].astype('int64')
self.data = self.data.reset_index(drop=True)
return
@staticmethod
def df_to_design_tuple(df):
'''User must impliment this method. It takes in a design in the form of a
single row of pandas dataframe, and it must return the chosen design as a
named tuple.
Convert 1-row pandas dataframe into named tuple'''
RA = df.RA.values[0]
DA = df.DA.values[0]
PA = df.PA.values[0]
RB = df.RB.values[0]
DB = df.DB.values[0]
PB = df.PB.values[0]
chosen_design = Design(ProspectA=Prospect(reward=RA, delay=DA, prob=PA),
ProspectB=Prospect(reward=RB, delay=DB, prob=PB))
return chosen_design
我们之所以这样做多重继承,是因为我们想要其他(非贝叶斯自适应)设计生成器,这些生成器在DARC领域中工作,但没有贝叶斯自适应设计组件。在大多数情况下,仅关注贝叶斯自适应设计,您只需在单个具体设计生成器类中定义add_design_response_to_dataframe
,df_to_design_tuple
类。
步骤 3:定义一个模型
您必须提供一个继承自Model
的模型类。您还必须提供以下方法
__init__
predictive_y
以下是一个用户定义的最小模型实现的示例
from badapted.model import Model
from badapted.choice_functions import CumulativeNormalChoiceFunc, StandardCumulativeNormalChoiceFunc
from scipy.stats import norm, halfnorm, uniform
import numpy as np
class MyCustomModel(Model):
'''My custom model which does XYZ.'''
def __init__(self, n_particles,
prior={'logk': norm(loc=-4.5, scale=1),
'α': halfnorm(loc=0, scale=2)}):
'''
INPUTS
- n_particles (integer).
- prior (dictionary). The keys provide the parameter name. The values
must be scipy.stats objects which define the prior distribution for
this parameter.
We provide choice functions in `badapted.choice_functions.py`. In this
example, we define it in the __init__ but it is not necessary to happen
here.
'''
self.n_particles = int(n_particles)
self.prior = prior
self.θ_fixed = {'ϵ': 0.01}
self.choiceFunction = CumulativeNormalChoiceFunc
def predictive_y(self, θ, data):
'''
INPUTS:
- θ = parameters
- data =
OUTPUT:
- p_chose_B (float) Must return a value between 0-1.
'''
# Step 1 - calculate decision variable
k = np.exp(θ['logk'].values
VA = data['RA'].values * 1 / (1 + k * data['DA'].values)
VB = data['RB'].values * 1 / (1 + k * data['DB'].values)
decision_variable = VB - VA
# Step 2 - apply choice function
p_chose_B = self.choiceFunction(decision_variable, θ, self.θ_fixed)
return p_chose_B
步骤 4:构建实验试验循环
这相当直接,这里不需要进行任何重大定制。
def run_experiment(design_generator, model, max_trials):
'''Run an adaptive experiment
INPUTS:
- design_generator: a class
'''
for trial in range(max_trials):
design = design_generator.get_next_design(model)
if design is None:
break
response = get_response(design)
design_generator.enter_trial_design_and_response(design, response)
model.update_beliefs(design_generator.data)
return model
请注意,response = get_response(design)
这一行由您来实现。您在这里所做的工作取决于您是在模拟响应还是从PsychoPy等获取真实响应。run_experiment
函数只是代码各部分如何协同工作的一个示例。当使用PsychoPy运行实际实验时,最好参考我们提供的DARC工具箱中的示例,以了解如何进行操作。
步骤 5:设置和运行实验
designs = build_my_design_space(my_arguments)
design_generator = MyCustomDesignGenerator(designs, max_trials=max_trials)
model = MyCustomModel()
model = run_experiment(design_generator, model, max_trials)
请注意,run_experiment
函数的使用只是展示事物如何组合的逻辑。如前所述,请参考DARC工具箱中的PsychoPy示例实验,以了解如何在PsychoPy实验中将其组合在一起。
使用badapted
的工具箱
- DARC工具箱用于适应性延迟和风险选择任务。
- 适应性心理物理工具箱用于心理物理实验。[注意:仍在积极开发中。]
项目详情
下载文件
下载适用于您的平台的文件。如果您不确定选择哪一个,请了解更多关于安装包的信息。
源分布
构建分布
badapted-0.0.3.tar.gz的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 33a610cd202a4746a387482be894c0d4860865f79781aed902a6b46b83de81a7 |
|
MD5 | d7eeda8f23820e564be759f380a91a8a |
|
BLAKE2b-256 | 901579985965f3ce7843615a15b3330bf35a9e76eb6064cd991b037df9807977 |
badapted-0.0.3-py3-none-any.whl 的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 4cabe6344fc5d8350418b8bcd8b81bc014b42378c21cc824cb602ceeffaa0b85 |
|
MD5 | 17a22de7ac604a06b6562829f2d69a51 |
|
BLAKE2b-256 | 3761a23de53fbb0e238f3faeec5311748f52295d0b2e29e49fa34a9bd8b9f194 |