# 概率分布 - torch.distributions > 原文:[`pytorch.org/docs/stable/distributions.html`](https://pytorch.org/docs/stable/distributions.html) `distributions`包含可参数化的概率分布和采样函数。这允许构建用于优化的随机计算图和随机梯度估计器。该包通常遵循[TensorFlow Distributions](https://arxiv.org/abs/1711.10604)包的设计。 无法直接通过随机样本进行反向传播。但是,有两种主要方法可以创建可以通过反向传播的替代函数。这些是得分函数估计器/似然比估计器/REINFORCE 和路径导数估计器。REINFORCE 通常被视为强化学习中策略梯度方法的基础,而路径导数估计器通常在变分自动编码器中的重参数化技巧中看到。虽然得分函数只需要样本值$f(x)$f(x),但路径导数需要导数$f'(x)$f′(x)。接下来的部分将讨论强化学习示例中的这两种方法。有关更多详细信息,请参见[使用随机计算图进行梯度估计](https://arxiv.org/abs/1506.05254)。 ## 得分函数 当概率密度函数相对于其参数可微时,我们只需要`sample()`和`log_prob()`来实现 REINFORCE: $\Delta\theta = \alpha r \frac{\partial\log p(a|\pi^\theta(s))}{\partial\theta}$Δθ=αr∂θ∂logp(a∣πθ(s))​ 其中$\theta$θ是参数,$\alpha$α是学习率,$r$r 是奖励,$p(a|\pi^\theta(s))$p(a∣πθ(s))是在状态$s$s 中根据策略$\pi^\theta$πθ采取行动$a$a 的概率。 在实践中,我们会从网络的输出中采样一个动作,在环境中应用此动作,然后使用`log_prob`构建等效的损失函数。请注意,我们使用负号,因为优化器使用梯度下降,而上述规则假定梯度上升。对于分类策略,实现 REINFORCE 的代码如下: ```py probs = policy_network(state) # Note that this is equivalent to what used to be called multinomial m = Categorical(probs) action = m.sample() next_state, reward = env.step(action) loss = -m.log_prob(action) * reward loss.backward() ``` ## 路径导数 实现这些随机/策略梯度的另一种方法是使用`rsample()`方法中的重参数化技巧,其中参数化的随机变量可以通过无参数随机变量的参数化确定性函数构造。因此,重参数化样本变得可微。实现路径导数的代码如下: ```py params = policy_network(state) m = Normal(*params) # Any distribution with .has_rsample == True could work based on the application action = m.rsample() next_state, reward = env.step(action) # Assuming that reward is differentiable loss = -reward loss.backward() ``` ## 分布 ```py class torch.distributions.distribution.Distribution(batch_shape=torch.Size([]), event_shape=torch.Size([]), validate_args=None) ``` 基类:[`object`](https://docs.python.org/3/library/functions.html#object "(in Python v3.12)") Distribution 是概率分布的抽象基类。 ```py property arg_constraints: Dict[str, Constraint] ``` 返回一个从参数名到应满足该分布每个参数的`Constraint`对象的字典。不需要出现在此字典中的非张量参数。 ```py property batch_shape: Size ``` 返回参数批处理的形状。 ```py cdf(value) ``` 返回在值处评估的累积密度/质量函数。 参数 **value** (*张量*) – 返回类型 *张量* ```py entropy() ``` 返回分布的熵,批处理在批形状上。 返回 形状为批形状的张量。 返回类型 *张量* ```py enumerate_support(expand=True) ``` 返回包含离散分布支持的所有值的张量。结果将枚举维度 0,因此结果的形状将是(基数,)+批形状+事件形状(其中事件形状=()表示单变量分布)。 请注意,这会枚举所有批处理张量[[0, 0],[1, 1],…]。使用 expand=False,枚举沿 dim 0 进行,但剩余的批处理维度是单例维度,[[0],[1],... 要遍历完整的笛卡尔积,请使用 itertools.product(m.enumerate_support())。 参数 **expand**([*bool*](https://docs.python.org/3/library/functions.html#bool "(在 Python v3.12 中)"))- 是否扩展支持以匹配分布的批量形状。 返回 在维度 0 上迭代的张量。 返回类型 *Tensor* ```py property event_shape: Size ``` 返回单个样本的形状(不包含批处理)。 ```py expand(batch_shape, _instance=None) ``` 返回一个新的分布实例(或填充由派生类提供的现有实例),其批量维度扩展到 batch_shape。此方法在分布的参数上调用`expand`。因此,这不会为扩展的分布实例分配新内存。此外,在首次创建实例时,这不会重复任何 args 检查或参数广播在 __init__.py 中。 参数 + 批量形状(*torch.Size*)- 所需的扩展大小。 + **_instance** - 子类提供的新实例,需要覆盖.expand。 返回 具有批量维度扩展到 batch_size 的新分布实例。 ```py icdf(value) ``` 返回在值处评估的累积密度/质量函数的逆函数。 参数 **value**(*Tensor*)- 返回类型 *Tensor* ```py log_prob(value) ``` 返回在值处评估的概率密度/质量函数的对数。 参数 **value**(*Tensor*)- 返回类型 *Tensor* ```py property mean: Tensor ``` 返回分布的均值。 ```py property mode: Tensor ``` 返回分布的模式。 ```py perplexity() ``` 返回分布的困惑度,批量化到批量形状。 返回 形状为 batch_shape 的张量。 返回类型 *Tensor* ```py rsample(sample_shape=torch.Size([])) ``` 生成一个 sample_shape 形状的重参数化样本或者如果分布参数是批量的,则生成一个 sample_shape 形状的重参数化样本批次。 返回类型 *Tensor* ```py sample(sample_shape=torch.Size([])) ``` 生成一个 sample_shape 形状的样本或者如果分布参数是批量的,则生成一个 sample_shape 形状的样本批次。 返回类型 *Tensor* ```py sample_n(n) ``` 生成 n 个样本或者如果分布参数是批量的,则生成 n 个样本批次。 返回类型 *Tensor* ```py static set_default_validate_args(value) ``` 设置验证是否启用或禁用。 默认行为模仿 Python 的`assert`语句:默认情况下启用验证,但如果 Python 在优化模式下运行(通过`python -O`),则会禁用验证。验证可能很昂贵,因此一旦模型运行正常,您可能希望禁用它。 参数 **value**([*bool*](https://docs.python.org/3/library/functions.html#bool "(在 Python v3.12 中)"))- 是否启用验证。 ```py property stddev: Tensor ``` 返回分布的标准差。 ```py property support: Optional[Any] ``` 返回表示此分布支持的`Constraint`对象。 ```py property variance: Tensor ``` 返回分布的方差。 ## 指数族 ```py class torch.distributions.exp_family.ExponentialFamily(batch_shape=torch.Size([]), event_shape=torch.Size([]), validate_args=None) ``` 基类:`Distribution` 指数族是概率分布的抽象基类,属于指数族,其概率质量/密度函数的形式如下所定义 $p_{F}(x; \theta) = \exp(\langle t(x), \theta\rangle - F(\theta) + k(x))$pF​(x;θ)=exp(⟨t(x),θ⟩−F(θ)+k(x)) 其中$\theta$θ表示自然参数,$t(x)$t(x)表示充分统计量,$F(\theta)$F(θ)是给定族的对数归一化函数,$k(x)$k(x)是载体测度。 注意 这个类是 Distribution 类和属于指数族的分布之间的中介,主要用于检查.entropy()和解析 KL 散度方法的正确性。我们使用这个类来使用 AD 框架和 Bregman 散度计算熵和 KL 散度(感谢:Frank Nielsen 和 Richard Nock,指数族的熵和交叉熵)。 ```py entropy() ``` 使用 Bregman 散度计算熵的方法。 ## 伯努利 ```py class torch.distributions.bernoulli.Bernoulli(probs=None, logits=None, validate_args=None) ``` 基类:`ExponentialFamily` 创建一个由`probs`或`logits`参数化的伯努利分布(但不能同时使用)。 样本是二进制(0 或 1)。它们以概率 p 取值 1,以概率 1-p 取值 0。 示例: ```py >>> m = Bernoulli(torch.tensor([0.3])) >>> m.sample() # 30% chance 1; 70% chance 0 tensor([ 0.]) ``` 参数 + **probs**(*Number**,* *Tensor*) - 采样 1 的概率 + **logits**(*Number**,* *Tensor*) - 采样 1 的对数几率 ```py arg_constraints = {'logits': Real(), 'probs': Interval(lower_bound=0.0, upper_bound=1.0)} ``` ```py entropy() ``` ```py enumerate_support(expand=True) ``` ```py expand(batch_shape, _instance=None) ``` ```py has_enumerate_support = True ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property mode ``` ```py property param_shape ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py support = Boolean() ``` ```py property variance ``` ## Beta ```py class torch.distributions.beta.Beta(concentration1, concentration0, validate_args=None) ``` 基类:`ExponentialFamily` Beta 分布由`concentration1`和`concentration0`参数化。 示例: ```py >>> m = Beta(torch.tensor([0.5]), torch.tensor([0.5])) >>> m.sample() # Beta distributed with concentration concentration1 and concentration0 tensor([ 0.1046]) ``` 参数 + **concentration1**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *or* *Tensor*) - 分布的第一个集中参数(通常称为 alpha) + **concentration0**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *or* *Tensor*) - 分布的第二个集中参数(通常称为 beta) ```py arg_constraints = {'concentration0': GreaterThan(lower_bound=0.0), 'concentration1': GreaterThan(lower_bound=0.0)} ``` ```py property concentration0 ``` ```py property concentration1 ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=()) ``` ```py support = Interval(lower_bound=0.0, upper_bound=1.0) ``` ```py property variance ``` ## 二项式 ```py class torch.distributions.binomial.Binomial(total_count=1, probs=None, logits=None, validate_args=None) ``` 基类:`Distribution` 创建一个由`total_count`和`probs`或`logits`参数化的二项式分布(但不能同时使用)。`total_count`必须与`probs`/`logits`可广播。 示例: ```py >>> m = Binomial(100, torch.tensor([0 , .2, .8, 1])) >>> x = m.sample() tensor([ 0., 22., 71., 100.]) >>> m = Binomial(torch.tensor([[5.], [10.]]), torch.tensor([0.5, 0.8])) >>> x = m.sample() tensor([[ 4., 5.], [ 7., 6.]]) ``` 参数 + **total_count**([*int*](https://docs.python.org/3/library/functions.html#int "(in Python v3.12)") *or* *Tensor*) - 伯努利试验的次数 + **probs**(*Tensor*) - 事件概率 + **logits**(*Tensor*) - 事件对数几率 ```py arg_constraints = {'logits': Real(), 'probs': Interval(lower_bound=0.0, upper_bound=1.0), 'total_count': IntegerGreaterThan(lower_bound=0)} ``` ```py entropy() ``` ```py enumerate_support(expand=True) ``` ```py expand(batch_shape, _instance=None) ``` ```py has_enumerate_support = True ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property mode ``` ```py property param_shape ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property support ``` ```py property variance ``` ## 分类 ```py class torch.distributions.categorical.Categorical(probs=None, logits=None, validate_args=None) ``` 基类:`Distribution` 创建一个由`probs`或`logits`参数化的分类分布(但不能同时使用)。 注意 它等同于`torch.multinomial()`从中采样的分布。 样本是从$\{0, \ldots, K-1\}${0,…,K−1}中的整数,其中 K 是`probs.size(-1)`。 如果 probs 是 1 维的,长度为 K,每个元素是在该索引处采样类的相对概率。 如果 probs 是 N 维的,则前 N-1 维被视为相对概率向量的批处理。 注意 probs 参数必须是非负的、有限的,并且具有非零总和,它将被归一化为沿着最后一个维度总和为 1。`probs`将返回这个归一化值。logits 参数将被解释为未归一化的对数概率,因此可以是任何实数。同样,它将被归一化,以使得得到的概率沿着最后一个维度总和为 1。`logits`将返回这个归一化值。 另请参见:`torch.multinomial()` 示例: ```py >>> m = Categorical(torch.tensor([ 0.25, 0.25, 0.25, 0.25 ])) >>> m.sample() # equal probability of 0, 1, 2, 3 tensor(3) ``` 参数 + **probs**(*张量*) - 事件概率 + **logits**(*张量*) - 事件对数概率(未归一化) ```py arg_constraints = {'logits': IndependentConstraint(Real(), 1), 'probs': Simplex()} ``` ```py entropy() ``` ```py enumerate_support(expand=True) ``` ```py expand(batch_shape, _instance=None) ``` ```py has_enumerate_support = True ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property mode ``` ```py property param_shape ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property support ``` ```py property variance ``` ## 柯西 ```py class torch.distributions.cauchy.Cauchy(loc, scale, validate_args=None) ``` 基类:`Distribution` 来自柯西(洛伦兹)分布的样本。具有均值为 0 的独立正态分布随机变量的比率的分布遵循柯西分布。 示例: ```py >>> m = Cauchy(torch.tensor([0.0]), torch.tensor([1.0])) >>> m.sample() # sample from a Cauchy distribution with loc=0 and scale=1 tensor([ 2.3214]) ``` 参数 + **loc**([*浮点数*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *张量*) - 分布的模式或中位数。 + **scale**([*浮点数*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *张量*) - 半峰宽。 ```py arg_constraints = {'loc': Real(), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(value) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py support = Real() ``` ```py property variance ``` ## 卡方 ```py class torch.distributions.chi2.Chi2(df, validate_args=None) ``` 基类:`Gamma` 创建由形状参数`df`参数化的卡方分布。这与`Gamma(alpha=0.5*df, beta=0.5)`完全等效。 示例: ```py >>> m = Chi2(torch.tensor([1.0])) >>> m.sample() # Chi2 distributed with shape df=1 tensor([ 0.1046]) ``` 参数 **df**([*浮点数*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *张量*) - 分布的形状参数 ```py arg_constraints = {'df': GreaterThan(lower_bound=0.0)} ``` ```py property df ``` ```py expand(batch_shape, _instance=None) ``` ## 连续伯努利 ```py class torch.distributions.continuous_bernoulli.ContinuousBernoulli(probs=None, logits=None, lims=(0.499, 0.501), validate_args=None) ``` 基类:`ExponentialFamily` 创建由`probs`或`logits`(但不是两者都有)参数化的连续伯努利分布。 该分布在[0,1]中支持,并由‘probs’(在(0,1)中)或‘logits’(实值)参数化。请注意,与伯努利不同,‘probs’不对应概率,‘logits’不对应对数几率,但由于与伯努利的相似性而使用相同的名称。有关更多详细信息,请参阅[1]。 示例: ```py >>> m = ContinuousBernoulli(torch.tensor([0.3])) >>> m.sample() tensor([ 0.2538]) ``` 参数 + **probs**(*数字*,*张量*) - (0,1)值参数 + **logits**(*数字*,*张量*) - 实值参数,其 Sigmoid 匹配‘probs’ [1] 连续伯努利:修复变分自动编码器中的普遍错误,Loaiza-Ganem G 和 Cunningham JP,NeurIPS 2019。[`arxiv.org/abs/1907.06845`](https://arxiv.org/abs/1907.06845) ```py arg_constraints = {'logits': Real(), 'probs': Interval(lower_bound=0.0, upper_bound=1.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(value) ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property param_shape ``` ```py property probs ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property stddev ``` ```py support = Interval(lower_bound=0.0, upper_bound=1.0) ``` ```py property variance ``` ## 狄利克雷 ```py class torch.distributions.dirichlet.Dirichlet(concentration, validate_args=None) ``` 基类:`ExponentialFamily` 创建由浓度`concentration`参数化的狄利克雷分布。 示例: ```py >>> m = Dirichlet(torch.tensor([0.5, 0.5])) >>> m.sample() # Dirichlet distributed with concentration [0.5, 0.5] tensor([ 0.1046, 0.8954]) ``` 参数 **concentration**(*Tensor*)– 分布的集中参数(通常称为 alpha) ```py arg_constraints = {'concentration': IndependentConstraint(GreaterThan(lower_bound=0.0), 1)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=()) ``` ```py support = Simplex() ``` ```py property variance ``` ## 指数 ```py class torch.distributions.exponential.Exponential(rate, validate_args=None) ``` 基类:`ExponentialFamily` 创建一个由`rate`参数化的指数分布。 示例: ```py >>> m = Exponential(torch.tensor([1.0])) >>> m.sample() # Exponential distributed with rate=1 tensor([ 0.1046]) ``` 参数 **rate**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– rate = 1 / 分布的比例 ```py arg_constraints = {'rate': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(value) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py property stddev ``` ```py support = GreaterThanEq(lower_bound=0.0) ``` ```py property variance ``` ## FisherSnedecor ```py class torch.distributions.fishersnedecor.FisherSnedecor(df1, df2, validate_args=None) ``` 基类:`Distribution` 创建一个由`df1`和`df2`参数化的 Fisher-Snedecor 分布。 示例: ```py >>> m = FisherSnedecor(torch.tensor([1.0]), torch.tensor([2.0])) >>> m.sample() # Fisher-Snedecor-distributed with df1=1 and df2=2 tensor([ 0.2453]) ``` 参数 + **df1**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– 自由度参数 1 + **df2**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– 自由度参数 2 ```py arg_constraints = {'df1': GreaterThan(lower_bound=0.0), 'df2': GreaterThan(lower_bound=0.0)} ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py support = GreaterThan(lower_bound=0.0) ``` ```py property variance ``` ## Gamma ```py class torch.distributions.gamma.Gamma(concentration, rate, validate_args=None) ``` 基类:`ExponentialFamily` 创建一个由形状`concentration`和`rate`参数化的 Gamma 分布。 示例: ```py >>> m = Gamma(torch.tensor([1.0]), torch.tensor([1.0])) >>> m.sample() # Gamma distributed with concentration=1 and rate=1 tensor([ 0.1046]) ``` 参数 + **concentration**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– 分布的形状参数(通常称为 alpha) + **rate**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– rate = 1 / 分布的比例(通常称为 beta) ```py arg_constraints = {'concentration': GreaterThan(lower_bound=0.0), 'rate': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py support = GreaterThanEq(lower_bound=0.0) ``` ```py property variance ``` ## 几何 ```py class torch.distributions.geometric.Geometric(probs=None, logits=None, validate_args=None) ``` 基类:`Distribution` 创建一个由`probs`参数化的几何分布,其中`probs`是伯努利试验成功的概率。 $P(X=k) = (1-p)^{k} p, k = 0, 1, ...$P(X=k)=(1−p)kp,k=0,1,... 注意 `torch.distributions.geometric.Geometric()` $(k+1)$(k+1)次试验是第一次成功,因此在$\{0, 1, \ldots\}${0,1,…}中抽取样本,而`torch.Tensor.geometric_()`第 k 次试验是第一次成功,因此在$\{1, 2, \ldots\}${1,2,…}中抽取样本。 示例: ```py >>> m = Geometric(torch.tensor([0.3])) >>> m.sample() # underlying Bernoulli has 30% chance 1; 70% chance 0 tensor([ 2.]) ``` 参数 + **probs**(*数字**,* *Tensor*)– 抽样 1 的概率。必须在范围(0, 1]内。 + **logits**(*数字**,* *Tensor*)– 抽样 1 的对数几率。 ```py arg_constraints = {'logits': Real(), 'probs': Interval(lower_bound=0.0, upper_bound=1.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property mode ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py support = IntegerGreaterThan(lower_bound=0) ``` ```py property variance ``` ## Gumbel ```py class torch.distributions.gumbel.Gumbel(loc, scale, validate_args=None) ``` 基类:`TransformedDistribution` 从 Gumbel 分布中抽样。 示例: ```py >>> m = Gumbel(torch.tensor([1.0]), torch.tensor([2.0])) >>> m.sample() # sample from Gumbel distribution with loc=1, scale=2 tensor([ 1.0124]) ``` 参数 + **loc**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– 分布的位置参数 + **scale**([*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *Tensor*)– 分布的比例参数 ```py arg_constraints: Dict[str, Constraint] = {'loc': Real(), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py property stddev ``` ```py support = Real() ``` ```py property variance ``` ## HalfCauchy ```py class torch.distributions.half_cauchy.HalfCauchy(scale, validate_args=None) ``` 基类:`TransformedDistribution` 创建一个由比例参数化的半 Cauchy 分布,其中: ```py X ~ Cauchy(0, scale) Y = |X| ~ HalfCauchy(scale) ``` 示例: ```py >>> m = HalfCauchy(torch.tensor([1.0])) >>> m.sample() # half-cauchy distributed with scale=1 tensor([ 2.3214]) ``` 参数 **scale**(*浮点数*或*张量*)- 完整柯西分布的比例 ```py arg_constraints: Dict[str, Constraint] = {'scale': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(prob) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py property scale ``` ```py support = GreaterThanEq(lower_bound=0.0) ``` ```py property variance ``` ## HalfNormal ```py class torch.distributions.half_normal.HalfNormal(scale, validate_args=None) ``` 基类:`TransformedDistribution` 创建由比例参数化的半正态分布,其中: ```py X ~ Normal(0, scale) Y = |X| ~ HalfNormal(scale) ``` 示例: ```py >>> m = HalfNormal(torch.tensor([1.0])) >>> m.sample() # half-normal distributed with scale=1 tensor([ 0.1046]) ``` 参数 **scale**(*浮点数*或*张量*)- 完整正态分布的比例 ```py arg_constraints: Dict[str, Constraint] = {'scale': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(prob) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py property scale ``` ```py support = GreaterThanEq(lower_bound=0.0) ``` ```py property variance ``` ## 独立 ```py class torch.distributions.independent.Independent(base_distribution, reinterpreted_batch_ndims, validate_args=None) ``` 基类:`Distribution` 将分布的一些批次维度重新解释为事件维度。 这主要用于改变`log_prob()`结果的形状。例如,为了创建一个与多元正态分布具有相同形状的对角正态分布(因此它们可以互换),您可以: ```py >>> from torch.distributions.multivariate_normal import MultivariateNormal >>> from torch.distributions.normal import Normal >>> loc = torch.zeros(3) >>> scale = torch.ones(3) >>> mvn = MultivariateNormal(loc, scale_tril=torch.diag(scale)) >>> [mvn.batch_shape, mvn.event_shape] [torch.Size([]), torch.Size([3])] >>> normal = Normal(loc, scale) >>> [normal.batch_shape, normal.event_shape] [torch.Size([3]), torch.Size([])] >>> diagn = Independent(normal, 1) >>> [diagn.batch_shape, diagn.event_shape] [torch.Size([]), torch.Size([3])] ``` 参数 + **base_distribution**(*torch.distributions.distribution.Distribution*)- 基本分布 + **reinterpreted_batch_ndims**(*整数*)- 要重新解释为事件维度的批次维度数 ```py arg_constraints: Dict[str, Constraint] = {} ``` ```py entropy() ``` ```py enumerate_support(expand=True) ``` ```py expand(batch_shape, _instance=None) ``` ```py property has_enumerate_support ``` ```py property has_rsample ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property support ``` ```py property variance ``` ## InverseGamma ```py class torch.distributions.inverse_gamma.InverseGamma(concentration, rate, validate_args=None) ``` 基类:`TransformedDistribution` 创建由`concentration`和`rate`参数化的逆伽马分布,其中: ```py X ~ Gamma(concentration, rate) Y = 1 / X ~ InverseGamma(concentration, rate) ``` 示例: ```py >>> m = InverseGamma(torch.tensor([2.0]), torch.tensor([3.0])) >>> m.sample() tensor([ 1.2953]) ``` 参数 + **concentration**(*浮点数*或*张量*)- 分布的形状参数(通常称为 alpha) + **rate**(*浮点数*或*张量*)- 分布的比例尺率(通常称为 beta 的倒数) ```py arg_constraints: Dict[str, Constraint] = {'concentration': GreaterThan(lower_bound=0.0), 'rate': GreaterThan(lower_bound=0.0)} ``` ```py property concentration ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py property mean ``` ```py property mode ``` ```py property rate ``` ```py support = GreaterThan(lower_bound=0.0) ``` ```py property variance ``` ## Kumaraswamy ```py class torch.distributions.kumaraswamy.Kumaraswamy(concentration1, concentration0, validate_args=None) ``` 基类:`TransformedDistribution` 从 Kumaraswamy 分布中抽样。 示例: ```py >>> m = Kumaraswamy(torch.tensor([1.0]), torch.tensor([1.0])) >>> m.sample() # sample from a Kumaraswamy distribution with concentration alpha=1 and beta=1 tensor([ 0.1729]) ``` 参数 + **concentration1**(*浮点数*或*张量*)- 分布的第一个浓度参数(通常称为 alpha) + **concentration0**(*浮点数*或*张量*)- 分布的第二个浓度参数(通常称为 beta) ```py arg_constraints: Dict[str, Constraint] = {'concentration0': GreaterThan(lower_bound=0.0), 'concentration1': GreaterThan(lower_bound=0.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py property mean ``` ```py property mode ``` ```py support = Interval(lower_bound=0.0, upper_bound=1.0) ``` ```py property variance ``` ## LKJCholesky ```py class torch.distributions.lkj_cholesky.LKJCholesky(dim, concentration=1.0, validate_args=None) ``` 基类:`Distribution` LKJ 分布用于相关矩阵的下三角 Cholesky 因子。该分布由`concentration`参数$\eta$η控制,使得从 Cholesky 因子生成的相关矩阵$M$的概率与$\det(M)^{\eta - 1}$成正比。因此,当`concentration == 1`时,我们得到一个在相关矩阵的 Cholesky 因子上均匀分布的分布: ```py L ~ LKJCholesky(dim, concentration) X = L @ L' ~ LKJCorr(dim, concentration) ``` 请注意,此分布对相关矩阵的 Cholesky 因子进行采样,而不是相关矩阵本身,因此与[1]中对 LKJCorr 分布的推导略有不同。对于采样,这使用了[1]第 3 节中的 Onion 方法。 示例: ```py >>> l = LKJCholesky(3, 0.5) >>> l.sample() # l @ l.T is a sample of a correlation 3x3 matrix tensor([[ 1.0000, 0.0000, 0.0000], [ 0.3516, 0.9361, 0.0000], [-0.1899, 0.4748, 0.8593]]) ``` 参数 + **dimension**(*dim*) - 矩阵的维度 + **concentration**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的浓度/形状参数(通常称为 eta) **参考** [1] 基于藤和扩展洋葱方法生成随机相关矩阵(2009 年),Daniel Lewandowski,Dorota Kurowicka,Harry Joe。多元分析杂志。100. 10.1016/j.jmva.2009.04.008 ```py arg_constraints = {'concentration': GreaterThan(lower_bound=0.0)} ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py sample(sample_shape=torch.Size([])) ``` ```py support = CorrCholesky() ``` ## 拉普拉斯 ```py class torch.distributions.laplace.Laplace(loc, scale, validate_args=None) ``` 基础:`Distribution` 创建一个由`loc`和`scale`参数化的拉普拉斯分布。 示例: ```py >>> m = Laplace(torch.tensor([0.0]), torch.tensor([1.0])) >>> m.sample() # Laplace distributed with loc=0, scale=1 tensor([ 0.1046]) ``` 参数 + **loc**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的均值 + **scale**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的尺度 ```py arg_constraints = {'loc': Real(), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(value) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py property stddev ``` ```py support = Real() ``` ```py property variance ``` ## 对数正态 ```py class torch.distributions.log_normal.LogNormal(loc, scale, validate_args=None) ``` 基础:`TransformedDistribution` 创建一个由`loc`和`scale`参数化的对数正态分布,其中: ```py X ~ Normal(loc, scale) Y = exp(X) ~ LogNormal(loc, scale) ``` 示例: ```py >>> m = LogNormal(torch.tensor([0.0]), torch.tensor([1.0])) >>> m.sample() # log-normal distributed with mean=0 and stddev=1 tensor([ 0.1046]) ``` 参数 + **loc**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的对数均值 + **scale**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 对数分布的标准差 ```py arg_constraints: Dict[str, Constraint] = {'loc': Real(), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py property loc ``` ```py property mean ``` ```py property mode ``` ```py property scale ``` ```py support = GreaterThan(lower_bound=0.0) ``` ```py property variance ``` ## 低秩多元正态分布 ```py class torch.distributions.lowrank_multivariate_normal.LowRankMultivariateNormal(loc, cov_factor, cov_diag, validate_args=None) ``` 基础:`Distribution` 创建一个具有由`cov_factor`和`cov_diag`参数化的协方差矩阵低秩形式的多元正态分布: ```py covariance_matrix = cov_factor @ cov_factor.T + cov_diag ``` 示例 ```py >>> m = LowRankMultivariateNormal(torch.zeros(2), torch.tensor([[1.], [0.]]), torch.ones(2)) >>> m.sample() # normally distributed with mean=`[0,0]`, cov_factor=`[[1],[0]]`, cov_diag=`[1,1]` tensor([-0.2102, -0.5429]) ``` 参数 + **loc**(*Tensor*) - 具有形状 batch_shape + event_shape 的分布均值 + **cov_factor**(*Tensor*) - 具有形状 batch_shape + event_shape + (rank,)的协方差矩阵低秩形式的因子部分 + **cov_diag**(*Tensor*) - 具有形状 batch_shape + event_shape 的协方差矩阵低秩形式的对角部分 注意 当 cov_factor.shape[1] << cov_factor.shape[0]时,通过[Woodbury 矩阵恒等式](https://en.wikipedia.org/wiki/Woodbury_matrix_identity)和[矩阵行列式引理](https://en.wikipedia.org/wiki/Matrix_determinant_lemma)避免了协方差矩阵的行列式和逆的计算。由于这些公式,我们只需要计算小尺寸“电容”矩阵的行列式和逆: ```py capacitance = I + cov_factor.T @ inv(cov_diag) @ cov_factor ``` ```py arg_constraints = {'cov_diag': IndependentConstraint(GreaterThan(lower_bound=0.0), 1), 'cov_factor': IndependentConstraint(Real(), 2), 'loc': IndependentConstraint(Real(), 1)} ``` ```py property covariance_matrix ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py property precision_matrix ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py property scale_tril ``` ```py support = IndependentConstraint(Real(), 1) ``` ```py property variance ``` ## MixtureSameFamily ```py class torch.distributions.mixture_same_family.MixtureSameFamily(mixture_distribution, component_distribution, validate_args=None) ``` 基础:`Distribution` MixtureSameFamily 分布实现了一个(批量的)混合分布,其中所有组件来自相同分布类型的不同参数化。它由一个分类“选择分布”(选择 k 个组件)和一个组件分布参数化,即具有右侧批量形状(等于[k])的分布,用于索引每个(批量的)组件。 示例: ```py >>> # Construct Gaussian Mixture Model in 1D consisting of 5 equally >>> # weighted normal distributions >>> mix = D.Categorical(torch.ones(5,)) >>> comp = D.Normal(torch.randn(5,), torch.rand(5,)) >>> gmm = MixtureSameFamily(mix, comp) >>> # Construct Gaussian Mixture Model in 2D consisting of 5 equally >>> # weighted bivariate normal distributions >>> mix = D.Categorical(torch.ones(5,)) >>> comp = D.Independent(D.Normal( ... torch.randn(5,2), torch.rand(5,2)), 1) >>> gmm = MixtureSameFamily(mix, comp) >>> # Construct a batch of 3 Gaussian Mixture Models in 2D each >>> # consisting of 5 random weighted bivariate normal distributions >>> mix = D.Categorical(torch.rand(3,5)) >>> comp = D.Independent(D.Normal( ... torch.randn(3,5,2), torch.rand(3,5,2)), 1) >>> gmm = MixtureSameFamily(mix, comp) ``` 参数 + **混合分布** - torch.distributions.Categorical-like 实例。管理选择组件的概率。类别数量必须与 component_distribution 的最右边批次维度匹配。必须具有标量 batch_shape 或与 component_distribution.batch_shape[:-1]匹配的 batch_shape + **component_distribution** - torch.distributions.Distribution-like 实例。最右边的批次维度索引组件。 ```py arg_constraints: Dict[str, Constraint] = {} ``` ```py cdf(x) ``` ```py property component_distribution ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = False ``` ```py log_prob(x) ``` ```py property mean ``` ```py property mixture_distribution ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property support ``` ```py property variance ``` ## 多项式 ```py class torch.distributions.multinomial.Multinomial(total_count=1, probs=None, logits=None, validate_args=None) ``` 基类:`分布` 创建由`total_count`和`probs`或`logits`(但不能同时)参数化的多项式分布。`probs`的最内部维度索引类别。所有其他维度索引批次。 请注意,如果仅调用`log_prob()`,则无需指定`total_count`(请参见下面的示例) 注意 probs 参数必须是非负的、有限的,并且具有非零总和,它将被归一化为沿着最后一个维度总和为 1。`probs`将返回这个归一化值。logits 参数将被解释为未归一化的对数概率,因此可以是任意实数。它也将被归一化,使得最终概率沿着最后一个维度总和为 1。`logits`将返回这个归一化值。 + `sample()`需要所有参数和样本的单个共享 total_count。 + `log_prob()`允许每个参数和样本有不同的 total_count。 示例: ```py >>> m = Multinomial(100, torch.tensor([ 1., 1., 1., 1.])) >>> x = m.sample() # equal probability of 0, 1, 2, 3 tensor([ 21., 24., 30., 25.]) >>> Multinomial(probs=torch.tensor([1., 1., 1., 1.])).log_prob(x) tensor([-4.1338]) ``` 参数 + **total_count**([*int*](https://docs.python.org/3/library/functions.html#int "(在 Python v3.12 中)")) - 试验次数 + **probs**(*张量*, 1), 'probs': Simplex()} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property param_shape ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property support ``` ```py total_count: int ``` ```py property variance ``` ## 多元正态分布 ```py class torch.distributions.multivariate_normal.MultivariateNormal(loc, covariance_matrix=None, precision_matrix=None, scale_tril=None, validate_args=None) ``` 基类:`分布` 创建由均值向量和协方差矩阵参数化的多元正态(也称为高斯)分布。 多元正态分布可以通过正定协方差矩阵$\mathbf{\Sigma}$Σ或正定精度矩阵$\mathbf{\Sigma}^{-1}$Σ−1 或具有正值对角元素的下三角矩阵$\mathbf{L}$L 来参数化,使得$\mathbf{\Sigma} = \mathbf{L}\mathbf{L}^\top$Σ=LL⊤。这个三角矩阵可以通过例如协方差的 Cholesky 分解获得。 示例 ```py >>> m = MultivariateNormal(torch.zeros(2), torch.eye(2)) >>> m.sample() # normally distributed with mean=`[0,0]` and covariance_matrix=`I` tensor([-0.2102, -0.5429]) ``` 参数 + **loc**(*张量*) - 协方差的下三角因子,对角线为正值 注意 只能指定`covariance_matrix`、`precision_matrix`或`scale_tril`中的一个。 使用`scale_tril`将更有效:所有计算内部都基于`scale_tril`。如果传递的是`covariance_matrix`或`precision_matrix`,则仅用于使用 Cholesky 分解计算相应的下三角矩阵。 ```py arg_constraints = {'covariance_matrix': PositiveDefinite(), 'loc': IndependentConstraint(Real(), 1), 'precision_matrix': PositiveDefinite(), 'scale_tril': LowerCholesky()} ``` ```py property covariance_matrix ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py property precision_matrix ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py property scale_tril ``` ```py support = IndependentConstraint(Real(), 1) ``` ```py property variance ``` ## 负二项分布 ```py class torch.distributions.negative_binomial.NegativeBinomial(total_count, probs=None, logits=None, validate_args=None) ``` 基类:`Distribution` 创建一个负二项分布,即在达到`total_count`次失败之前成功独立且相同的伯努利试验次数的分布。每次伯努利试验成功的概率是`probs`。 参数 + **total_count**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 非负的负伯努利试验次数,尽管分布仍然适用于实值计数 + **probs**(*Tensor*) - 成功事件的概率在半开区间[0, 1]中 + **logits**(*Tensor*) - 成功概率的事件对数几率 ```py arg_constraints = {'logits': Real(), 'probs': HalfOpenInterval(lower_bound=0.0, upper_bound=1.0), 'total_count': GreaterThanEq(lower_bound=0)} ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property mode ``` ```py property param_shape ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py support = IntegerGreaterThan(lower_bound=0) ``` ```py property variance ``` ## 正态分布 ```py class torch.distributions.normal.Normal(loc, scale, validate_args=None) ``` 基类:`ExponentialFamily` 创建一个由`loc`和`scale`参数化的正态(也称为高斯)分布。 示例: ```py >>> m = Normal(torch.tensor([0.0]), torch.tensor([1.0])) >>> m.sample() # normally distributed with loc=0 and scale=1 tensor([ 0.1046]) ``` 参数 + **loc**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的均值(通常称为 mu) + **scale**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的标准差(通常称为 sigma) ```py arg_constraints = {'loc': Real(), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(value) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py sample(sample_shape=torch.Size([])) ``` ```py property stddev ``` ```py support = Real() ``` ```py property variance ``` ## OneHotCategorical ```py class torch.distributions.one_hot_categorical.OneHotCategorical(probs=None, logits=None, validate_args=None) ``` 基类:`Distribution` 创建一个由`probs`或`logits`参数化的一位独热分类分布。 样本是大小为`probs.size(-1)`的独热编码向量。 注意 probs 参数必须是非负的、有限的,并且具有非零总和,它将被归一化为沿着最后一个维度总和为 1。`probs`将返回这个归一化值。logits 参数将被解释为未归一化的对数概率,因此可以是任意实数。它也将被归一化,使得最终的概率沿着最后一个维度总和为 1。`logits`将返回这个归一化值。 另请参阅:`torch.distributions.Categorical()`以获取`probs`和`logits`的规格。 示例: ```py >>> m = OneHotCategorical(torch.tensor([ 0.25, 0.25, 0.25, 0.25 ])) >>> m.sample() # equal probability of 0, 1, 2, 3 tensor([ 0., 0., 0., 1.]) ``` 参数 + **probs**(*Tensor*) - 事件概率 + **logits**(*Tensor*) - 事件对数概率(未归一化) ```py arg_constraints = {'logits': IndependentConstraint(Real(), 1), 'probs': Simplex()} ``` ```py entropy() ``` ```py enumerate_support(expand=True) ``` ```py expand(batch_shape, _instance=None) ``` ```py has_enumerate_support = True ``` ```py log_prob(value) ``` ```py property logits ``` ```py property mean ``` ```py property mode ``` ```py property param_shape ``` ```py property probs ``` ```py sample(sample_shape=torch.Size([])) ``` ```py support = OneHot() ``` ```py property variance ``` ## Pareto ```py class torch.distributions.pareto.Pareto(scale, alpha, validate_args=None) ``` 基类:`TransformedDistribution` 从 Pareto Type 1 分布中采样。 示例: ```py >>> m = Pareto(torch.tensor([1.0]), torch.tensor([1.0])) >>> m.sample() # sample from a Pareto distribution with scale=1 and alpha=1 tensor([ 1.5623]) ``` 参数 + **scale**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的比例参数 + **alpha**([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *或* *Tensor*) - 分布的形状参数 ```py arg_constraints: Dict[str, Constraint] = {'alpha': GreaterThan(lower_bound=0.0), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py property mean ``` ```py property mode ``` ```py property support ``` ```py property variance ``` ## 泊松 ```py class torch.distributions.poisson.Poisson(rate, validate_args=None) ``` 基类:`ExponentialFamily` 创建一个由`rate`参数化的泊松分布,即速率参数。 样本是非负整数,其概率质量函数由 $\mathrm{rate}^k \frac{e^{-\mathrm{rate}}}{k!}$ ratekk!e−rate​ 示例: ```py >>> m = Poisson(torch.tensor([4])) >>> m.sample() tensor([ 3.]) ``` 参数 **rate**(*Number**,* *Tensor*) - 速率参数 ```py arg_constraints = {'rate': GreaterThanEq(lower_bound=0.0)} ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py sample(sample_shape=torch.Size([])) ``` ```py support = IntegerGreaterThan(lower_bound=0) ``` ```py property variance ``` ## RelaxedBernoulli ```py class torch.distributions.relaxed_bernoulli.RelaxedBernoulli(temperature, probs=None, logits=None, validate_args=None) ``` 基类:`TransformedDistribution` 创建一个由`temperature`参数化的 RelaxedBernoulli 分布,以及`probs`或`logits`(但不能同时)。这是伯努利分布的松弛版本,因此值在(0, 1)之间,并且具有可重参数化的样本。 示例: ```py >>> m = RelaxedBernoulli(torch.tensor([2.2]), ... torch.tensor([0.1, 0.2, 0.3, 0.99])) >>> m.sample() tensor([ 0.2951, 0.3442, 0.8918, 0.9021]) ``` 参数 + **temperature**(*Tensor*) - 松弛温度 + **probs**(*Number**,* *Tensor*) - 采样 1 的概率 + **logits**(*Number**,* *Tensor*) - 采样 1 的对数几率 ```py arg_constraints: Dict[str, Constraint] = {'logits': Real(), 'probs': Interval(lower_bound=0.0, upper_bound=1.0)} ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py property logits ``` ```py property probs ``` ```py support = Interval(lower_bound=0.0, upper_bound=1.0) ``` ```py property temperature ``` ## LogitRelaxedBernoulli ```py class torch.distributions.relaxed_bernoulli.LogitRelaxedBernoulli(temperature, probs=None, logits=None, validate_args=None) ``` 基类:`Distribution` 创建由`probs`或`logits`(但不是两者)参数化的 LogitRelaxedBernoulli 分布,它是 RelaxedBernoulli 分布的对数几率。 样本是在(0, 1)范围内的值的对数。更多细节请参见[1]。 参数 + **temperature** (*Tensor*) – 松弛温度 + **probs** (*Number**,* *Tensor*) – 采样 1 的概率 + **logits** (*Number**,* *Tensor*) – 采样 1 的对数几率 [1] 具体分布:离散随机变量的连续松弛(Maddison 等人,2017) [2] 使用 Gumbel-Softmax 的分类重参数化(Jang 等人,2017) ```py arg_constraints = {'logits': Real(), 'probs': Interval(lower_bound=0.0, upper_bound=1.0)} ``` ```py expand(batch_shape, _instance=None) ``` ```py log_prob(value) ``` ```py property logits ``` ```py property param_shape ``` ```py property probs ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py support = Real() ``` ## RelaxedOneHotCategorical ```py class torch.distributions.relaxed_categorical.RelaxedOneHotCategorical(temperature, probs=None, logits=None, validate_args=None) ``` 基类:`TransformedDistribution` 创建由`temperature`参数化的 RelaxedOneHotCategorical 分布,并且是由`probs`或`logits`参数化的。这是`OneHotCategorical`分布的松弛版本,因此其样本位于单纯形上,并且可重参数化。 示例: ```py >>> m = RelaxedOneHotCategorical(torch.tensor([2.2]), ... torch.tensor([0.1, 0.2, 0.3, 0.4])) >>> m.sample() tensor([ 0.1294, 0.2324, 0.3859, 0.2523]) ``` 参数 + **temperature** (*Tensor*) – 松弛温度 + **probs** (*Tensor*) – 事件概率 + **logits** (*Tensor*) – 每个事件的未归一化对数概率 ```py arg_constraints: Dict[str, Constraint] = {'logits': IndependentConstraint(Real(), 1), 'probs': Simplex()} ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py property logits ``` ```py property probs ``` ```py support = Simplex() ``` ```py property temperature ``` ## StudentT ```py class torch.distributions.studentT.StudentT(df, loc=0.0, scale=1.0, validate_args=None) ``` 基类:`Distribution` 创建由自由度`df`、均值`loc`和标度`scale`参数化的学生 t 分布。 示例: ```py >>> m = StudentT(torch.tensor([2.0])) >>> m.sample() # Student's t-distributed with degrees of freedom=2 tensor([ 0.1046]) ``` 参数 + **df** ([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *or* *Tensor*) – 自由度 + **loc** ([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *or* *Tensor*) – 分布的均值 + **scale** ([*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)") *or* *Tensor*) – 分布的标度 ```py arg_constraints = {'df': GreaterThan(lower_bound=0.0), 'loc': Real(), 'scale': GreaterThan(lower_bound=0.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py support = Real() ``` ```py property variance ``` ## TransformedDistribution ```py class torch.distributions.transformed_distribution.TransformedDistribution(base_distribution, transforms, validate_args=None) ``` 基类:`Distribution` Distribution 类的扩展,将一系列变换应用于基本分布。设 f 为应用的变换的组合: ```py X ~ BaseDistribution Y = f(X) ~ TransformedDistribution(BaseDistribution, f) log p(Y) = log p(X) + log |det (dX/dY)| ``` 请注意,`TransformedDistribution`的`.event_shape`是其基本分布和变换的最大形状,因为变换可能在事件之间引入相关性。 使用`TransformedDistribution`的示例: ```py # Building a Logistic Distribution # X ~ Uniform(0, 1) # f = a + b * logit(X) # Y ~ f(X) ~ Logistic(a, b) base_distribution = Uniform(0, 1) transforms = [SigmoidTransform().inv, AffineTransform(loc=a, scale=b)] logistic = TransformedDistribution(base_distribution, transforms) ``` 更多示例,请查看`Gumbel`,`HalfCauchy`,`HalfNormal`,`LogNormal`,`Pareto`,`Weibull`,`RelaxedBernoulli`和`RelaxedOneHotCategorical`的实现。 ```py arg_constraints: Dict[str, Constraint] = {} ``` ```py cdf(value) ``` 通过反转变换(s)并计算基本分布的得分来计算累积分布函数。 ```py expand(batch_shape, _instance=None) ``` ```py property has_rsample ``` ```py icdf(value) ``` 使用 transform(s)计算逆累积分布函数,并计算基本分布的得分。 ```py log_prob(value) ``` 通过反转变换(s)并使用基本分布的得分和对数绝对值行列式雅可比矩阵的得分来对样本进行评分。 ```py rsample(sample_shape=torch.Size([])) ``` 生成一个形状为 sample_shape 的重参数化样本或者如果分布参数是批处理的,则生成一个形状为 sample_shape 的重参数化样本批次。首先从基本分布中抽样,然后对列表中的每个变换应用 transform()。 ```py sample(sample_shape=torch.Size([])) ``` 如果分布参数是批处理的,则生成一个形状为 sample_shape 的样本或者形状为 sample_shape 的样本批次。首先从基本分布中抽样,然后对列表中的每个变换应用 transform()。 ```py property support ``` ## 均匀分布 ```py class torch.distributions.uniform.Uniform(low, high, validate_args=None) ``` 基类:`Distribution` 从半开区间`[low, high)`中生成均匀分布的随机样本。 示例: ```py >>> m = Uniform(torch.tensor([0.0]), torch.tensor([5.0])) >>> m.sample() # uniformly distributed in the range [0.0, 5.0) tensor([ 2.3418]) ``` 参数 + **low**(*float*或*Tensor*) - 下限范围(包括)。 + **high**(*float*或*Tensor*) - 上限范围(不包括)。 ```py arg_constraints = {'high': Dependent(), 'low': Dependent()} ``` ```py cdf(value) ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py icdf(value) ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py rsample(sample_shape=torch.Size([])) ``` ```py property stddev ``` ```py property support ``` ```py property variance ``` ## VonMises ```py class torch.distributions.von_mises.VonMises(loc, concentration, validate_args=None) ``` 基类:`Distribution` 圆形 von Mises 分布。 此实现使用极坐标。`loc`和`value`参数可以是任何实数(以便进行无约束优化),但被解释为模 2 pi 的角度。 示例: ```py >>> m = VonMises(torch.tensor([1.0]), torch.tensor([1.0])) >>> m.sample() # von Mises distributed with loc=1 and concentration=1 tensor([1.9777]) ``` 参数 + **loc**(*torch.Tensor*) - 弧度角度。 + **concentration**(*torch.Tensor*) - 集中参数 ```py arg_constraints = {'concentration': GreaterThan(lower_bound=0.0), 'loc': Real()} ``` ```py expand(batch_shape) ``` ```py has_rsample = False ``` ```py log_prob(value) ``` ```py property mean ``` 提供的均值是圆形的。 ```py property mode ``` ```py sample(sample_shape=torch.Size([])) ``` von Mises 分布的抽样算法基于以下论文:D.J. Best 和 N.I. Fisher,“von Mises 分布的高效模拟。”应用统计(1979 年):152-157。 采样始终在内部以双精度进行,以避免在集中值较小时(在单精度约为 1e-4 时)在 _rejection_sample()中出现挂起(请参见问题#88443)。 ```py support = Real() ``` ```py property variance ``` 提供的方差是圆形的。 ## 威布尔 ```py class torch.distributions.weibull.Weibull(scale, concentration, validate_args=None) ``` 基类:`TransformedDistribution` 从双参数威布尔分布中抽样。 示例 ```py >>> m = Weibull(torch.tensor([1.0]), torch.tensor([1.0])) >>> m.sample() # sample from a Weibull distribution with scale=1, concentration=1 tensor([ 0.4784]) ``` 参数 + **scale**(*float*或*Tensor*) - 分布的比例参数(lambda)。 + **浓度**([*浮点数*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *张量*, 'scale': GreaterThan(lower_bound=0.0)} ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py property mean ``` ```py property mode ``` ```py support = GreaterThan(lower_bound=0.0) ``` ```py property variance ``` ## Wishart ```py class torch.distributions.wishart.Wishart(df, covariance_matrix=None, precision_matrix=None, scale_tril=None, validate_args=None) ``` 基类:`指数族` 创建由对称正定矩阵$\Sigma$Σ或其 Cholesky 分解$\mathbf{\Sigma} = \mathbf{L}\mathbf{L}^\top$Σ=LL⊤参数化的 Wishart 分布 示例 ```py >>> m = Wishart(torch.Tensor([2]), covariance_matrix=torch.eye(2)) >>> m.sample() # Wishart distributed with mean=`df * I` and >>> # variance(x_ij)=`df` for i != j and variance(x_ij)=`2 * df` for i == j ``` 参数 + **df**([*浮点数*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)") *或* *张量*、`precision_matrix`或`scale_tril`中的一个。使用`scale_tril`将更有效:所有计算内部都基于`scale_tril`。如果传递的是`covariance_matrix`或`precision_matrix`,则仅用于使用 Cholesky 分解计算相应的下三角矩阵。‘torch.distributions.LKJCholesky’是受限制的 Wishart 分布。[1] **参考** [1] 王,Z.,吴,Y.和楚,H.,2018。LKJ 分布和受限制的 Wishart 分布的等价性。[2] 索耶,S.,2007。Wishart 分布和逆 Wishart 抽样。[3] 安德森,T. W.,2003。多元统计分析导论(第 3 版)。[4] 奥德尔,P. L. & 费夫森,A. H.,1966。生成样本协方差矩阵的数值过程。JASA,61(313):199-203。[5] 顾,Y.-C. & 布鲁姆菲尔德,P.,2010。在 OX 中生成具有分数自由度的随机 Wishart 矩阵。 ```py arg_constraints = {'covariance_matrix': PositiveDefinite(), 'df': GreaterThan(lower_bound=0), 'precision_matrix': PositiveDefinite(), 'scale_tril': LowerCholesky()} ``` ```py property covariance_matrix ``` ```py entropy() ``` ```py expand(batch_shape, _instance=None) ``` ```py has_rsample = True ``` ```py log_prob(value) ``` ```py property mean ``` ```py property mode ``` ```py property precision_matrix ``` ```py rsample(sample_shape=torch.Size([]), max_try_correction=None) ``` 警告 在某些情况下,基于 Bartlett 分解的采样算法可能返回奇异矩阵样本。默认情况下会尝试多次纠正奇异样本,但最终可能会返回奇异矩阵样本。奇异样本可能会在.log_prob()中返回-inf 值。在这种情况下,用户应验证样本,并修复 df 的值或根据需要调整.rsample 中 max_try_correction 参数的值。 ```py property scale_tril ``` ```py support = PositiveDefinite() ``` ```py property variance ``` ## KL 散度 ```py torch.distributions.kl.kl_divergence(p, q) ``` 计算两个分布之间的 Kullback-Leibler 散度$KL(p \| q)$KL(p∥q)。 $KL(p \| q) = \int p(x) \log\frac {p(x)} {q(x)} \,dx$KL(p∥q)=∫p(x)logq(x)p(x)​dx 参数 + **p**(*分布*") - 如果分布类型尚未通过`register_kl()`注册。 KL 散度目前针对以下分布对实现: + `伯努利` 和 `伯努利` + `伯努利` 和 `泊松` + `贝塔` 和 `贝塔` + `贝塔` 和 `连续伯努利` + `贝塔` 和 `指数` + `贝塔` 和 `Gamma` + `贝塔` 和 `正态` + `贝塔` 和 `帕累托` + `贝塔` 和 `均匀` + `二项式` 和 `二项式` + `分类` 和 `分类` + `柯西` 和 `柯西` + `连续伯努利` 和 `连续伯努利` + `连续伯努利` 和 `指数` + `连续伯努利` 和 `正态` + `连续伯努利` 和 `帕累托` + `连续伯努利` 和 `均匀` + `狄利克雷` 和 `狄利克雷` + `指数` 和 `贝塔` + `指数` 和 `连续伯努利` + `指数` 和 `指数` + `指数` 和 `Gamma` + `指数` 和 `Gumbel` + `指数` 和 `正态` + `指数` 和 `帕累托` + `指数` 和 `均匀` + `指数族` 和 `指数族` + `Gamma` 和 `贝塔` + `Gamma` 和 `连续伯努利` + `Gamma` 和 `指数` + `Gamma` 和 `Gamma` + `Gamma` 和 `Gumbel` + `Gamma` 和 `正态` + `Gamma` 和 `帕累托` + `Gamma` 和 `均匀` + `几何` 和 `几何` + `Gumbel` 和 `贝塔` + `Gumbel` 和 `连续伯努利` + `Gumbel` 和 `指数` + `Gumbel` 和 `Gamma` + `Gumbel` 和 `Gumbel` + `Gumbel` 和 `正态` + `Gumbel` 和 `帕累托` + `Gumbel` 和 `均匀` + `半正态` 和 `半正态` + `独立` 和 `独立` + `拉普拉斯` 和 `贝塔` + `拉普拉斯` 和 `连续伯努利` + `拉普拉斯` 和 `指数` + `拉普拉斯` 和 `Gamma` + `拉普拉斯` 和 `拉普拉斯` + `拉普拉斯` 和 `正态` + `拉普拉斯` 和 `帕累托` + `拉普拉斯` 和 `均匀` + `低秩多元正态` 和 `低秩多元正态` + `低秩多元正态` 和 `多元正态` + `多元正态` 和 `低秩多元正态` + `多元正态` 和 `多元正态` + `正态` 和 `贝塔` + `正态` 和 `连续伯努利` + `正态` 和 `指数` + `Normal` 和 `Gamma` + `正态` 和 `Gumbel` + `正态` 和 `拉普拉斯` + `正态` 和 `正态` + `正态` 和 `帕累托` + `正态` 和 `均匀` + `OneHotCategorical` 和 `OneHotCategorical` + `帕累托` 和 `贝塔` + `帕累托` 和 `连续伯努利` + `帕累托` 和 `指数` + `帕累托` 和 `Gamma` + `帕累托` 和 `正态` + `帕累托` 和 `帕累托` + `帕累托` 和 `均匀` + `泊松` 和 `伯努利` + `泊松` 和 `二项式` + `泊松` 和 `泊松` + `变换分布` 和 `变换分布` + `均匀` 和 `贝塔` + `均匀` 和 `连续伯努利` + `均匀` 和 `指数` + `均匀` 和 `Gamma` + `均匀` 和 `Gumbel` + `均匀` 和 `正态` + `均匀` 和 `帕累托` + `均匀` 和 `均匀` ```py torch.distributions.kl.register_kl(type_p, type_q) ``` 装饰器用于使用`kl_divergence()`注册成对函数。用法: ```py @register_kl(Normal, Normal) def kl_normal_normal(p, q): # insert implementation here ``` 查找返回按子类排序的最具体的(类型,类型)匹配。如果匹配不明确,则会引发 RuntimeWarning。例如,要解决模糊的情况: ```py @register_kl(BaseP, DerivedQ) def kl_version1(p, q): ... @register_kl(DerivedP, BaseQ) def kl_version2(p, q): ... ``` 您应该注册第三个最具体的实现,例如: ```py register_kl(DerivedP, DerivedQ)(kl_version1) # Break the tie. ``` 参数 + **type_p**([*type*](https://docs.python.org/3/library/functions.html#type "(in Python v3.12)")) - `Distribution` 的子类。 + **type_q**([*type*](https://docs.python.org/3/library/functions.html#type "(in Python v3.12)")) - `Distribution` 的子类。## 转换[](#module-torch.distributions.transforms "Permalink to this heading") ```py class torch.distributions.transforms.AbsTransform(cache_size=0) ``` 通过映射 $y = |x|$ 进行变换。 ```py class torch.distributions.transforms.AffineTransform(loc, scale, event_dim=0, cache_size=0) ``` 通过逐点仿射映射变换 $y = \text{loc} + \text{scale} \times x$。 参数 + **loc**(*Tensor* *或* [*float*](https://docs.python.org/3/library/functions.html#float "(in Python v3.12)")) - 位置参数。 + **scale**(*Tensor* *或* [*float*](https://docs.python.org/3/library/functions.html#float "(在 Python v3.12 中)")) - 缩放参数。 + **event_dim**([*int*](https://docs.python.org/3/library/functions.html#int "(在 Python v3.12 中)")) - 事件形状的可选大小。对于一元随机变量,应为零;对于向量分布,应为 1;对于矩阵分布,应为 2,依此类推。 ```py class torch.distributions.transforms.CatTransform(tseq, dim=0, lengths=None, cache_size=0) ``` 应用一系列变换 tseq,逐个组件地将每个子矩阵在维度 dim 处的长度为 lengths[dim]的变换,以与`torch.cat()`兼容的方式。 示例: ```py x0 = torch.cat([torch.range(1, 10), torch.range(1, 10)], dim=0) x = torch.cat([x0, x0], dim=0) t0 = CatTransform([ExpTransform(), identity_transform], dim=0, lengths=[10, 10]) t = CatTransform([t0, t0], dim=0, lengths=[20, 20]) y = t(x) ``` ```py class torch.distributions.transforms.ComposeTransform(parts, cache_size=0) ``` 在链中组合多个变换。被组合的变换负责缓存。 参数 + **parts**(`Transform`列表) - 要组合的变换列表。 + **cache_size**([*int*](https://docs.python.org/3/library/functions.html#int "(在 Python v3.12 中)")) - 缓存大小。如果为零,则不进行缓存。如果为一,则缓存最新的单个值。仅支持 0 和 1。 ```py class torch.distributions.transforms.CorrCholeskyTransform(cache_size=0) ``` 将长度为$D*(D-1)/2$的无约束实向量$x$转换为 D 维相关矩阵的 Cholesky 因子。这个 Cholesky 因子是一个下三角矩阵,对角线为正,每行的欧几里得范数为单位。变换如下进行: > 1. 首先,我们按行将 x 转换为下三角矩阵。 > 1. > 1. 对于下三角部分的每一行$X_i$,我们应用类`StickBreakingTransform`的*有符号*版本,将$X_i$转换为单位欧几里得长度向量,步骤如下: - 缩放到区间$(-1, 1)$:$r_i = \tanh(X_i)$。 - 转换为无符号域:$z_i = r_i²$。 - 应用$si = StickBreakingTransform(z_i)$。 - 转换回有符号域:$y_i = sign(r_i) * \sqrt{s_i}$。 ```py class torch.distributions.transforms.CumulativeDistributionTransform(distribution, cache_size=0) ``` 通过概率分布的累积分布函数进行变换。 参数 **distribution**(*Distribution*) - 要用于变换的累积分布函数的分布。 示例: ```py # Construct a Gaussian copula from a multivariate normal. base_dist = MultivariateNormal( loc=torch.zeros(2), scale_tril=LKJCholesky(2).sample(), ) transform = CumulativeDistributionTransform(Normal(0, 1)) copula = TransformedDistribution(base_dist, [transform]) ``` ```py class torch.distributions.transforms.ExpTransform(cache_size=0) ``` 通过映射$y = \exp(x)$进行变换。 ```py class torch.distributions.transforms.IndependentTransform(base_transform, reinterpreted_batch_ndims, cache_size=0) ``` 封装另一个变换,以将`reinterpreted_batch_ndims`-许多右侧维度视为相关。这对前向或后向变换没有影响,但在`log_abs_det_jacobian()`中会对右侧维度进行`reinterpreted_batch_ndims`求和。 参数 + **base_transform**(`Transform`) - 基本变换。 + **reinterpreted_batch_ndims**([*int*](https://docs.python.org/3/library/functions.html#int "(在 Python v3.12 中)")) - 要视为相关的额外右侧维度的数量。 ```py class torch.distributions.transforms.LowerCholeskyTransform(cache_size=0) ``` 从无约束矩阵转换为具有非负对角元的下三角矩阵。 这对于用 Cholesky 分解参数化正定矩阵非常有用。 ```py class torch.distributions.transforms.PositiveDefiniteTransform(cache_size=0) ``` 从无约束矩阵转换为正定矩阵。 ```py class torch.distributions.transforms.PowerTransform(exponent, cache_size=0) ``` 通过映射$y = x^{\text{exponent}}$进行变换。 ```py class torch.distributions.transforms.ReshapeTransform(in_shape, out_shape, cache_size=0) ``` 单位雅可比变换,用于重塑张量的最右侧部分。 请注意,`in_shape`和`out_shape`必须具有相同数量的元素,就像`torch.Tensor.reshape()`一样。 参数 + **in_shape**(*torch.Size*) - 输入事件形状。 + **out_shape**(*torch.Size*) - 输出事件形状。 ```py class torch.distributions.transforms.SigmoidTransform(cache_size=0) ``` 通过映射$y = \frac{1}{1 + \exp(-x)}$和$x = \text{logit}(y)$进行变换。 ```py class torch.distributions.transforms.SoftplusTransform(cache_size=0) ``` 通过映射$\text{Softplus}(x) = \log(1 + \exp(x))$Softplus(x)=log(1+exp(x))进行变换。当$x > 20$时,实现会恢复为线性函数。 ```py class torch.distributions.transforms.TanhTransform(cache_size=0) ``` 通过映射$y = \tanh(x)$y=tanh(x)进行变换。 它等同于`` ComposeTransform([AffineTransform(0., 2.), SigmoidTransform(), AffineTransform(-1., 2.)]) `` 但这可能不是数值稳定的,因此建议改用 TanhTransform。 请注意,当涉及 NaN/Inf 值时,应使用 cache_size=1。 ```py class torch.distributions.transforms.SoftmaxTransform(cache_size=0) ``` 从非约束空间到单纯形的变换,通过$y = \exp(x)$y=exp(x)然后归一化。 这不是双射的,不能用于 HMC。但是这主要是按坐标进行的(除了最终的归一化),因此适用于按坐标优化算法。 ```py class torch.distributions.transforms.StackTransform(tseq, dim=0, cache_size=0) ``` 将变换序列 tseq 逐个组件地应用于维度 dim 中的每个子矩阵的变换函数,以与`torch.stack()`兼容的方式。 示例: ```py x = torch.stack([torch.range(1, 10), torch.range(1, 10)], dim=1) t = StackTransform([ExpTransform(), identity_transform], dim=1) y = t(x) ``` ```py class torch.distributions.transforms.StickBreakingTransform(cache_size=0) ``` 通过一个破棍过程,将非约束空间转换为一个额外维度的单纯形。 这种变换是 Dirichlet 分布的一个迭代 sigmoid 变换的结果:第一个 logit 通过 sigmoid 变换为第一个概率和其他所有概率,然后过程递归进行。 这是双射的,适用于在 HMC 中使用;但是它将坐标混合在一起,不太适合优化。 ```py class torch.distributions.transforms.Transform(cache_size=0) ``` 可计算对数行列式雅可比的可逆变换的抽象类。它们主要用于`torch.distributions.TransformedDistribution`中。 缓存对于其逆变换要么昂贵要么数值不稳定的变换很有用。请注意,必须小心处理记忆值,因为自动求导图可能会被反转。例如,以下内容无论是否缓存都可以工作: ```py y = t(x) t.log_abs_det_jacobian(x, y).backward() # x will receive gradients. ``` 然而,由于依赖关系的反转,以下内容在缓存时会出错: ```py y = t(x) z = t.inv(y) grad(z.sum(), [y]) # error because z is x ``` 派生类应该实现`_call()`或`_inverse()`中的一个或两个。将 bijective=True 的派生类还应该实现`log_abs_det_jacobian()`。 参数 **cache_size**([*int*](https://docs.python.org/3/library/functions.html#int "(in Python v3.12)")) - 缓存的大小。如果为零,则不进行缓存。如果为一,则缓存最新的单个值。仅支持 0 和 1。 变量 + **定义域**(`Constraint`) - 表示此变换的有效输入的约束。 + **值域**(`Constraint`) - 表示此变换的有效输出的约束,这些输出是逆变换的输入。 + **双射**([*bool*](https://docs.python.org/3/library/functions.html#bool "(in Python v3.12)")) - 此变换是否是双射。如果变换`t`是双射,则对于每个域中的`x`和值域中的`y`,`t.inv(t(x)) == x`和`t(t.inv(y)) == y`。不是双射的变换应至少保持较弱的伪逆性质`t(t.inv(t(x)) == t(x)`和`t.inv(t(t.inv(y))) == t.inv(y)`。 + **符号**([*int*](https://docs.python.org/3/library/functions.html#int "(in Python v3.12)") *或* *Tensor*) - 对于双射单变量变换,这应该是+1 或-1,取决于变换是单调递增还是递减。 ```py property inv ``` 返回此变换的逆`Transform`。这应该满足`t.inv.inv is t`。 ```py property sign ``` 返回雅可比行列式的符号,如果适用的话。一般来说,这只对双射变换有意义。 ```py log_abs_det_jacobian(x, y) ``` 计算给定输入和输出的对数行列式雅可比行列式 log |dy/dx|。 ```py forward_shape(shape) ``` 推断前向计算的形状,给定输入形状。默认保留形状。 ```py inverse_shape(shape) ``` 推断逆计算的形状,给定输出形状。默认保留形状。 ## 约束[](#module-torch.distributions.constraints "Permalink to this heading") 以下约束已实现: + `constraints.boolean` + `constraints.cat` + `constraints.corr_cholesky` + `constraints.dependent` + `constraints.greater_than(lower_bound)` + `constraints.greater_than_eq(lower_bound)` + `constraints.independent(constraint, reinterpreted_batch_ndims)` + `constraints.integer_interval(lower_bound, upper_bound)` + `constraints.interval(lower_bound, upper_bound)` + `constraints.less_than(upper_bound)` + `constraints.lower_cholesky` + `constraints.lower_triangular` + `constraints.multinomial` + `constraints.nonnegative` + `constraints.nonnegative_integer` + `constraints.one_hot` + `constraints.positive_integer` + `constraints.positive` + `constraints.positive_semidefinite` + `constraints.positive_definite` + `constraints.real_vector` + `constraints.real` + `constraints.simplex` + `constraints.symmetric` + `constraints.stack` + `constraints.square` + `constraints.symmetric` + `constraints.unit_interval` ```py class torch.distributions.constraints.Constraint ``` 约束的抽象基类。 约束对象表示变量有效的区域,例如变量可以在其中进行优化的区域。 变量 + **is_discrete** ([*bool*](https://docs.python.org/3/library/functions.html#bool "(in Python v3.12)")) – 约束空间是否是离散的。默认为 False。 + **event_dim** ([*int*](https://docs.python.org/3/library/functions.html#int "(in Python v3.12)")) – 定义事件的最右边维度的数量。`check()`方法在计算有效性时将删除这么多维度。 ```py check(value) ``` 返回一个`sample_shape + batch_shape`的字节张量,指示值中的每个事件是否满足此约束。 ```py torch.distributions.constraints.cat ``` 别名为`_Cat` ```py torch.distributions.constraints.dependent_property ``` 别名为`_DependentProperty` ```py torch.distributions.constraints.greater_than ``` 别名为`_GreaterThan` ```py torch.distributions.constraints.greater_than_eq ``` 别名为`_GreaterThanEq` ```py torch.distributions.constraints.independent ``` 别名为`_IndependentConstraint` ```py torch.distributions.constraints.integer_interval ``` 别名为`_IntegerInterval` ```py torch.distributions.constraints.interval ``` 别名为`_Interval` ```py torch.distributions.constraints.half_open_interval ``` 别名为`_HalfOpenInterval` ```py torch.distributions.constraints.less_than ``` 别名为`_LessThan` ```py torch.distributions.constraints.multinomial ``` 别名为`_Multinomial` ```py torch.distributions.constraints.stack ``` 别名为`_Stack` ## 约束注册[](#module-torch.distributions.constraint_registry "Permalink to this heading") PyTorch 提供了两个全局`ConstraintRegistry`对象,将`Constraint`对象链接到`Transform`对象。这些对象都输入约束并返回变换,但它们对双射性有不同的保证。 1. `biject_to(constraint)` 从`constraints.real`查找一个双射的`Transform`到给定的`constraint`。返回的变换保证具有`.bijective = True`,并应实现`.log_abs_det_jacobian()`。 1. `transform_to(constraint)` 从`constraints.real`查找一个不一定双射的`Transform`到给定的`constraint`。返回的变换不保证实现`.log_abs_det_jacobian()`。 `transform_to()`注册表对于在概率分布的约束参数上执行无约束优化非常有用,每个分布的`.arg_constraints`字典指示。这些变换通常过度参数化空间以避免旋转;因此,它们更适合于像 Adam 这样的逐坐标优化算法: ```py loc = torch.zeros(100, requires_grad=True) unconstrained = torch.zeros(100, requires_grad=True) scale = transform_to(Normal.arg_constraints['scale'])(unconstrained) loss = -Normal(loc, scale).log_prob(data).sum() ``` `biject_to()`注册表对于 Hamiltonian Monte Carlo 很有用,其中来自具有约束`.support`的概率分布的样本在无约束空间中传播,并且算法通常是旋转不变的。 ```py dist = Exponential(rate) unconstrained = torch.zeros(100, requires_grad=True) sample = biject_to(dist.support)(unconstrained) potential_energy = -dist.log_prob(sample).sum() ``` 注意 `transform_to`和`biject_to`不同的一个例子是`constraints.simplex`:`transform_to(constraints.simplex)`返回一个`SoftmaxTransform`,它简单地对其输入进行指数化和归一化;这是一种适用于像 SVI 这样的算法的廉价且大多数是坐标轴操作。相比之下,`biject_to(constraints.simplex)`返回一个`StickBreakingTransform`,它将其输入映射到一个维度少一的空间;这是一种更昂贵且数值稳定性较差的变换,但对于像 HMC 这样的算法是必需的。 `biject_to`和`transform_to`对象可以通过它们的`.register()`方法扩展用户定义的约束和变换,可以作为单例约束的函数: ```py transform_to.register(my_constraint, my_transform) ``` 或作为参数化约束的装饰器: ```py @transform_to.register(MyConstraintClass) def my_factory(constraint): assert isinstance(constraint, MyConstraintClass) return MyTransform(constraint.param1, constraint.param2) ``` 您可以通过创建一个新的`ConstraintRegistry`对象来创建自己的注册表。 ```py class torch.distributions.constraint_registry.ConstraintRegistry ``` 将约束链接到变换的注册表。 ```py register(constraint, factory=None) ``` 在此注册表中注册一个`Constraint`子类。用法: ```py @my_registry.register(MyConstraintClass) def construct_transform(constraint): assert isinstance(constraint, MyConstraint) return MyTransform(constraint.arg_constraints) ``` 参数 + **constraint**(`Constraint`的子类) - `Constraint`的子类,或所需类的单例对象。 + **factory**(*Callable*) - 一个可调用对象,输入一个约束对象并返回一个`Transform`对象。