联邦学习中的差分隐私
差分隐私(Differential Privacy, DP)为联邦学习提供严格的数学隐私保证。本文介绍 DP-SGD、DP-FedAvg 及隐私预算分析。
差分隐私基础
(ε, δ)-差分隐私定义:
对于任意相邻数据集 D, D' 和任意输出 S:
P[M(D) ∈ S] ≤ e^ε × P[M(D') ∈ S] + δ
其中:
- ε: 隐私预算(越小越隐私)
- δ: 失败概率(通常设为 1/n^2)
- M: 随机化机制DP-SGD
在梯度级别添加噪声:
python
class DPSGDOptimizer:
def __init__(self, model, lr=0.01, noise_multiplier=1.0, max_grad_norm=1.0):
self.model = model
self.lr = lr
self.noise_multiplier = noise_multiplier
self.max_grad_norm = max_grad_norm
def step(self, dataloader):
for batch in dataloader:
# 1. 计算每个样本的梯度(per-sample gradient)
per_sample_grads = self.compute_per_sample_grads(batch)
# 2. 裁剪梯度(限制敏感度)
for i in range(len(per_sample_grads)):
grad_norm = torch.norm(per_sample_grads[i])
if grad_norm > self.max_grad_norm:
per_sample_grads[i] *= self.max_grad_norm / grad_norm
# 3. 聚合裁剪后的梯度
clipped_grad = torch.mean(per_sample_grads, dim=0)
# 4. 添加高斯噪声
noise = torch.normal(
0, self.noise_multiplier * self.max_grad_norm,
size=clipped_grad.shape
)
noisy_grad = clipped_grad + noise
# 5. 更新参数
for param, grad in zip(self.model.parameters(), noisy_grad):
param.data -= self.lr * gradDP-FedAvg
将 DP-SGD 与 FedAvg 结合:
python
class DPFedAvgServer:
def __init__(self, model, noise_multiplier=1.0, z_clip=1.0):
self.global_model = model
self.noise_multiplier = noise_multiplier
self.z_clip = z_clip
def aggregate(self, client_updates, num_clients):
# 1. 裁剪客户端更新
for i, update in enumerate(client_updates):
update_norm = compute_norm(update)
if update_norm > self.z_clip:
scale_update(update, self.z_clip / update_norm)
# 2. 计算平均更新
avg_update = average_updates(client_updates)
# 3. 添加高斯噪声
noise_std = self.noise_multiplier * self.z_clip / num_clients
noise = torch.normal(0, noise_std, size=avg_update.shape)
noisy_update = avg_update + noise
# 4. 更新全局模型
apply_update(self.global_model, noisy_update)隐私预算计算
使用 Rényi 差分隐私(RDP)进行更紧的隐私分析:
python
from opacus.accountants import RDPAccountant
accountant = RDPAccountant()
# 每轮消耗的隐私预算
for round in range(num_rounds):
accountant.step(
noise_multiplier=1.0,
sample_rate=0.01, # 采样率
)
# 转换为 (ε, δ)-DP
epsilon = accountant.get_epsilon(delta=1e-5)
print(f"总隐私消耗: ε = {epsilon:.2f}")隐私-效用权衡
| noise_multiplier | ε (100轮) | 模型精度 | 隐私等级 |
|---|---|---|---|
| 0.5 | ~50 | 接近无DP | 极弱 |
| 1.0 | ~8 | 略降 | 中等 |
| 2.0 | ~3 | 明显下降 | 较强 |
| 5.0 | ~1 | 严重下降 | 极强 |
隐私预算分配
- 确定可接受的 ε(通常 1-10)
- 根据总轮数反推 noise_multiplier
- 使用 RDP 会计师获得更紧的界
- 子采样本身提供隐私放大效应
精度损失
DP 对模型精度的影响不可忽视。对于复杂任务(如大模型微调),ε < 3 时精度下降显著。实际应用中需要仔细权衡隐私与效用。