协变量筛选 API#

mas.model.ScmConfig#

class mas.model.ScmConfig#

SCM 运行配置,包含搜索方向、纳排标准与搜索规则。

search_direction#

property search_direction#

搜索方向。默认值为 "both"。可接受的输入值包括:"forward""backward""both"

类型:

SearchDirectionType

p_forward#

property p_forward#

前向搜索过程中假设检验的显著性水平。即若 p 值小于此值,则纳入此协变量关系。默认值为 0.05

类型:

ValueType

p_backward#

property p_backward#

逆向搜索过程中假设检验的显著性水平。即若 p 值大于此值,则剔除此协变量关系。默认值为 0.01

类型:

ValueType

global_init#

property global_init#

所有因纳入协变量关系而新增的固定效应参数(theta)初值。默认值为 1e-3

类型:

ValueType

maxiter#

property maxiter#

最大搜索次数。默认值为 None

类型:

int

accept_rule#

property accept_rule#

用户自定义的接受规则。

类型:

AcceptRuleCallable | None

示例:

例如设置自定义接受规则为:仅当纳入协变量后清除率的个体间变异参数方差估计值 omega["eta_cl", "eta_cl"] 减小 30% 或以上时才接受新的协变量模型。

def custom_rule(context: AcceptRuleContext) -> bool:
    if context.direction == "forward":
        if context.test_params.omega["eta_cl", "eta_cl"] / context.base_params.omega["eta_cl", "eta_cl"] < 0.7:
            return True
    return False

class ModelScmConfig(BaseModel, ScmConfig):
    def __init__(self) -> None:
        super().__init__()
        self.search_direction = "both"
        self.p_forward = 0.01
        self.p_backward = 0.005
        self.cat_cov = multicolumn(["SEX", "GROUP"], is_categorical=True)
        self.con_cov = multicolumn(["AGE", "WT"])
        self.accept_rule = custom_rule

    @spec
    def spec(self):
        self.test(tv=self.tv_cl, covariates=self.cat_cov, states="*")
        self.test(tv=self.tv_cl, covariates=self.con_cov, states="*")

test()#

test(tv, covariates, states, init=None, bounds=None, init_state=None) None

需要被测试的协变量-参数关系。

参数:

  • tv (Theta):需要被引入协变量的固定效应参数。

  • covariates (AnyCategoricalColVar | list[AnyCategoricalColVar] | StrCategoricalColVarCollection | NumericCategoricalColVarCollection | AnyContinuousColVar | list[AnyContinuousColVar] | NumericContinuousColVarCollection):需要被测试的协变量。一般接受自 column()multicolumn() 定义的变量。

  • states (AnyCategoricalValidStates | AnyContinuousValidStates):需要被测试的协变量-参数关系状态。对应的协变量效应参数化形式请参考 协变量效应参数化公式

    • 对于分类型协变量,支持的状态为 "exclude""linear""*"

    • 对于连续型协变量,支持的状态为 "exclude""linear""piecewise""exp""power""*"

  • init (ValueType | list[ValueType | PiecewiseValueType | None], optional):因纳入协变量关系而新增的协变量效应参数初值。若为 None,将自动计算初值。默认值为 None

  • bounds (BoundsType | list[BoundsType | PiecewiseBoundsType | None], optional):协变量效应参数估计的上下边界值。若为 None,将自动计算边界值。默认值为 None

  • init_state (CategoricalValidStateType, optional):在搜索开始时即被引入至模型的协变量关系及其状态。默认值为 None

协变量效应参数化公式#

总则

以乘法的形式结合各协变量效应与原模型固定效应参数,公式如下:

\[ p_{ki} = \theta_{k} \times g_{k}({z}_i) + \eta_{ki} \]
\[ g({z}_i) = \prod_{r = 1}^{q} c_{ir} \]

假设原模型中共有 k 个固定效应参数与 i 个个体。其中,\(p_{ki}\) 为第 i 个个体的第 k 个固定效应参数的估计值;\(\theta_{k}\) 为此固定效应参数的群体典型值;\(\eta_{ki}\) 为此固定效应参数的个体间变异;\({z}_i\) 为第 i 个个体的协变量值向量;\(g_{k}\) 为有关于 \({z}_i\) 的函数,用于描述协变量与固定效应参数间的关系,具体由纳入协变量的个数 r 以及不同的协变量-参数关系状态(\(c_{ir}\))决定。

各状态的参数化公式

  • "exclude":不引入任何协变量。

  • "linear":以线性关系引入协变量,公式如下:

若为连续型协变量:

\[ c_{ir} = 1 + \theta_{r} \times (z_{ir} - median(z_r)) \]

若为分类协变量(以二分类变量为例):

\[\begin{split} c_{ir} = \begin{cases} 1 & 若 \quad z_{ir} = a \\ 1 + \theta_{r} & 若 \quad z_{ir} = b \end{cases} \end{split}\]
  • "piecewise":以分段线性关系引入协变量,公式如下:

\[\begin{split} c_{ir} = \begin{cases} 1 + \theta_{r} \times (z_{ir} - median(z_r)) & 若 \quad z_{ir} ≤ median(z_r) \\ 1 + \theta_{r+1} \times (z_{ir} - median(z_r)) & 若 \quad z_{ir} > median(z_r) \end{cases} \end{split}\]
  • "exp":以指数形式引入协变量,公式如下:

\[ c_{ir} = exp(\theta_{r} \times (z_{ir} - median(z_r))) \]
  • "power":以幂的形式引入协变量,公式如下:

\[ c_{ir} = \theta_{r}^{z_{ir} - median(z_r)} \]

上述公式中,\(\theta_{r}\) 为协变量效应参数,表明了协变量值的变动对固定效应参数的影响大小。

参考文献

Jonsson, E. N., & Karlsson, M. O. (1998). Automated covariate model building within NONMEM. Pharmaceutical research, 15(9), 1463–1468.

示例:

例如,假设在模型固定效应参数清除率(self.tv_cl)上以线性关系引入了协变量体重(self.wt)与年龄(self.age),模型将变为如下形式:

class WarfarinCovariate(EvOneCmtLinear):
    def __init__(self):
        self.tv_cl = theta(0.1, bounds=(0.0, 10))
        self.wt = column('WT')
        self.age = column('AGE')

        self.tv_cl__wt_linear = theta(0.01, bounds=(-1.0, 1.0))
        self.tv_cl__age_linear = theta(0.01, bounds=(-1.0, 1.0))
        ...

    def pred(self):
        tv_cl__wt = 1 + self.tv_cl__wt_linear * (self.wt - 70.0)
        tv_cl__age = 1 + self.tv_cl__age_linear * (self.age - 31)
        tv_cl__with_cov = self.tv_cl * tv_cl__wt * tv_cl__age
        cl = tv_cl__with_cov * exp(self.eta_cl)
        ...

SCM 配置样例#

class ModelScmConfig(BaseModel, ScmConfig):
    def __init__(self) -> None:
        super().__init__()
        self.maxiter = None
        self.search_direction = "both"
        self.p_forward = 0.01
        self.p_backward = 0.005
        self.global_init = 1e-3
        self.con_cov = multicolumn(["COV_1", "COV_2"])
        self.cat_cov = multicolumn(["COV_3", "COV_4"], is_categorical=True)

    @spec
    def spec(self):
        self.test(tv=self.tv_theta, covariates=self.con_cov, states=["exclude", "linear", "piecewise", "exp", "power"])
        self.test(tv=self.tv_theta, covariates=self.cat_cov, states=["exclude", "linear"])

mas.model.spec#

@mas.model.spec(name=None, skip=False, direction=None, p_forward=None, p_backward=None, global_init=None) SpecDef#

用于定义 SCM 搜索规则的装饰器。

一般在 ScmConfig 中使用。示例可见 SCM 配置样例

参数:

  • name (str, optional):此搜索规则的名称。默认值为 None

  • skip (bool, optional):是否跳过此搜索。默认值为 False

  • direction (SearchDirectionType, optional):搜索方向。若为 None 则使用在 ScmConfig 中的设置。默认值为 None

  • p_forward (float, optional):此搜索中前向搜索的假设检验显著性水平。若为 None 则使用在 ScmConfig 中的设置。默认值为 None

  • p_backward (float, optional):此搜索中逆向搜索的假设检验显著性水平。若为 None 则使用在 ScmConfig 中的设置。默认值为 None

  • global_init (ValueType, optional):此搜索中所有因纳入协变量关系而新增的固定效应参数的初值。若为 None 则使用在 ScmConfig 中的设置。默认值为 None

ScmResultCollection#

class ScmResultCollection#

SCM 运行结果汇总,包含所有搜索规则(即带有 @spec 的函数)得到的搜索结果。可以使用 [spec_name] 或者搜索规则的索引值取出对应的 ScmResult

ScmResult#

class ScmResult#

SCM 搜索结果,包含最终模型、运行日志以及各个步骤中的模型结果。

final_model#

property final_model#

SCM 法搜索得到的最终模型。

类型:

ScmFinalModel

示例:

使用 SCM 法对华法林 PK 模型进行协变量筛选,并获取最终的协变量模型:

class WarfarinScm(Warfarin, ScmConfig):
    def __init__(self) -> None:
        super().__init__()
        self.search_direction = "both"
        self.p_forward = 0.01
        self.p_backward = 0.005
        self.sex = column("SEX", is_categorical=True)
        self.wt = column("WT")
        self.age = column("AGE")

    @spec
    def spec(self):
        self.test(tv=self.tv_v, covariates=[self.wt, self.age], states=["exclude", "linear", "exp"])
        self.test(tv=self.tv_v, covariates=self.sex, states="*")

scm_res = fit_res.scm(WarfarinScm)
scm_res[0].final_model
class Warfarin__1_1(EvOneCmtLinear):
    """
    tv_v ~ wt @ linear
    """

    def __init__(self):
        super().__init__()
        self.tv_cl = theta(0.1321535638999604, bounds=(0.0, None), fixed=False)
        self.tv_v = theta(7.978038718308011, bounds=(0.0, None), fixed=False)
        self.tv_ka = theta(1.3539303948551795, bounds=(0.0, None), fixed=False)
        self.tv_alag = theta(0.8242352271177251, bounds=(0.0, None), fixed=False)
        self.tv_v__wt_1 = theta(-3.125e-05, bounds=(-0.03125, 0.03333333333333333), fixed=False)
        self.eta_cl = omega(0.08344571272395199, fixed=False)
        self.eta_v = omega(0.04847460601550199, fixed=False)
        self.eta_ka = omega(0.6980354669901869, fixed=False)
        self.eta_alag = omega(0.1555376480659238, fixed=False)
        self.eps_prop = sigma(0.0074644892041942, fixed=False)
        self.eps_add = sigma(0.06688759015978558, fixed=False)
        self.wt = column('WT', typ='numeric', is_categorical=False)
        self.age = column('AGE', typ='numeric', is_categorical=False)
        self.sex = column('SEX', typ='numeric', is_categorical=True)

    def pred(self):
        tv_v__wt = 1 + self.tv_v__wt_1 * (self.wt - 70.0)
        tv_v__age = 1
        tv_v__sex = 1
        tv_v__with_cov = self.tv_v * tv_v__wt * tv_v__age * tv_v__sex
        cl = self.tv_cl * exp(self.eta_cl)
        v = tv_v__with_cov * exp(self.eta_v)
        ka = self.tv_ka * exp(self.eta_ka)
        alag = self.tv_alag * exp(self.eta_alag)
        pred_res = self.pred_physio(cl=cl, v=v, ka=ka, alag1=alag, s2=v)
        ipred = pred_res.F
        y = ipred * (1 + self.eps_prop) + self.eps_add
        return y

steps#

property steps#

各搜索步骤的模型测试结果。

类型:

list[ScmStepwiseResult]

ScmFinalModel#

class ScmFinalModel#

SCM 搜索得到的最终模型。

code#

property code#

最终模型的模型代码。

类型:

str

fit_result#

property fit_result#

最终模型的拟合结果。

类型:

FitResult

states#

property states#

最终模型中各协变量的状态。

类型:

CompoundRelationControlStates

ScmStepwiseResult#

class ScmStepwiseResult#

SCM 每一轮搜索的搜索结果。

tests#

property tests#

某轮搜索中的各次测试的结果。

类型:

list[ScmStepwiseTestResult]

ScmStepwiseTestResult#

class ScmStepwiseTestResult#

SCM 每一轮搜索中各次测试的结果。

code#

property code

被测试模型的模型代码。

类型:

str

selected#

property selected#

被测试模型是否被接受。

类型:

bool

test_relation#

property test_relation#

被测试模型中被考察的协变量-参数关系。

类型:

AnyRelationControlState

test_tv#

property test_tv#

被测试模型中被考察的需要引入协变量的原模型固定效应参数。

类型:

Theta

test_covariate#

property test_covariate#

被测试模型中被考察的需要被引入的协变量。

类型:

AnyColVar

test_state#

property test_state#

被测试模型中被考察的协变量-参数关系内协变量参数化的状态。

类型:

AnyValidStateType

base#

property base#

被测试模型的基础模型。

类型:

ScmSearchIteration

ScmSearchIteration#

class ScmSearchIteration#

SCM 每一轮搜索对应的上一轮搜索结果。

test_case#

property test_case#

上一轮搜索最终接受的模型。

类型:

ScmTestCase

fit_result#

property fit_result

上一轮搜索最终接受模型的拟合结果。

类型:

FitResult

ofv#

property ofv

上一轮搜索最终接受模型的目标函数值。

类型:

float

n_theta#

property n_theta#

上一轮搜索最终接受模型中所含的固定效应参数数量。

类型:

int

params#

property params#

上一轮搜索最终接受模型的模型参数估计结果。

类型:

PopParams

candidates#

property candidates#

上一轮搜索中所有被测试的模型。

类型:

list[ScmStepwiseSelectionCandidate | None]

best_candidate_index#

property best_candidate_index#

上一轮搜索中最优模型在 candidates 列表中的索引值。

类型:

int | None

base#

property base

上一轮搜索的基础模型。

类型:

ScmSearchIteration

as_table()#

as_table()#

以表格的形式呈现上一轮搜索结果。

返回值:

上一轮搜索结果表格。

返回类型:

str

ScmTestCase#

class ScmTestCase#

SCM 中被测试的协变量模型。

states#

property states

模型测试的协变量-参数关系中协变量参数化的状态。

类型:

CompoundRelationControlStates

descriptor#

property descriptor#

模型描述,包含模型的各类结构信息。

类型:

ModelDescriptor

ScmStepwiseSelectionCandidate#

class ScmStepwiseSelectionCandidate#

SCM 中被测试的协变量模型的测试结果。

acceptance#

property acceptance#

测试结果,包含模型是否被接受、测试的 p 值、目标函数值变动等信息。

类型:

ScmStepwiseAcceptanceTest

states#

property states

被测试模型中包含的协变量-参数关系及协变量参数化状态。

类型:

CompoundRelationControlStates

fit_result#

property fit_result

被测试模型中的拟合结果。

类型:

FitResult

descriptor#

property descriptor

被测试模型的模型描述。

类型:

ModelDescriptor