Python 拒绝采样算法优化与多峰分布模拟
拒绝采样(Rejection Sampling)是一种从复杂分布中生成样本的蒙特卡洛方法,也是 LLM 微调优化的关键技术之一。本文基于 Python 模拟并对比多种拒绝采样的实现策略,重点探讨如何通过优化提议分布和参数选择来提升采样效率。
核心原理与优化方向
拒绝采样的核心在于从提议分布(Proposal Distribution)中生成样本,并以一定概率接受或拒绝。关键约束是存在常数 M,使得目标概率密度函数 target_pdf(x) 始终小于等于 M * proposal_pdf(x)。
常见的优化思路包括:
- 自适应调整:根据已接受的样本动态更新提议分布的参数,自动优化 M 值。
- 分层采样:将定义域划分为多个子区域,为每个区域匹配最合适的提议分布,平衡采样数量。
- 混合分布:使用多个提议分布的加权和,特别适合匹配多峰目标分布。
Python 模拟实现
为了直观展示不同策略的效果,我们构建了一个基于双峰高斯混合分布的目标模型,并实现了基础、自适应、分层及混合四种采样器。
环境准备与目标分布定义
首先引入必要的科学计算库,并定义目标概率密度函数。这里我们设定一个由两个高斯分布组成的混合模型:
import numpy as np
import matplotlib.pyplot as plt
from scipy import stats
import time
# 设置绘图风格
plt.rcParams['font.family'] = 'Arial Unicode MS'
# 定义目标分布:混合高斯分布
def target_pdf(x):
return 0.7 * stats.norm.pdf(x, -2, 1) + 0.3 * stats.norm.pdf(x, 3, 1.5)
基础拒绝采样
这是最经典的实现方式。我们需要确定一个足够大的 M 值来覆盖整个目标分布。虽然简单,但在高维或多峰场景下,接受率往往较低。
def basic_rejection_sampling(target_pdf, proposal_pdf, proposal_rv, M, n_samples=1000, max_iter=10000):
samples = []
attempts = 0
while len(samples) < n_samples attempts < max_iter:
attempts +=
x = proposal_rv()
u = np.random.uniform(, )
u < target_pdf(x) / (M * proposal_pdf(x)):
samples.append(x)
acceptance_rate = (samples) / attempts attempts >
np.array(samples), acceptance_rate

