ADMM(交替方向乘子法)算例

ADMM(交替方向乘子法)算例

目标:用 ADMM 解带约束的最小二乘问题(岭回归)

特点:结构简单、物理意义明确、方便扩展到 LASSO / 分布式优化


一、优化问题定义

原问题(带正则化的最小二乘)

min⁡x  12∥Ax−b∥22+λ2∥x∥22\min_x \; \frac{1}{2}\|Ax - b\|_2^2 + \frac{\lambda}{2}\|x\|_2^2xmin21∥Ax−b∥22+2λ∥x∥22

这是一个凸问题,有解析解,用来验证 ADMM 非常合适。


二、ADMM 形式改写

引入辅助变量 (z),把问题拆开:

min⁡x,z12∥Ax−b∥22+λ2∥z∥22s.t.x−z=0\begin{aligned} \min_{x,z} \quad & \frac{1}{2}\|Ax - b\|_2^2 + \frac{\lambda}{2}\|z\|_2^2 \\ \text{s.t.} \quad & x - z = 0 \end{aligned}x,zmins.t.21∥Ax−b∥22+2λ∥z∥22x−z=0


三、增广拉格朗日函数

Lρ(x,z,u)=12∥Ax−b∥2+λ2∥z∥2ρ2∥x−z+u∥2\mathcal{L}_\rho(x,z,u) = \frac{1}{2}\|Ax-b\|^2 + \frac{\lambda}{2}\|z\|^2\frac{\rho}{2}\|x-z+u\|^2 Lρ(x,z,u)=21∥Ax−b∥2+2λ∥z∥22ρ∥x−z+u∥2

其中:

  • uuu:缩放形式的对偶变量
  • ρ\rhoρ > 0:惩罚参数

四、ADMM 迭代步骤

x-更新(最小二乘子问题)

xk+1=(ATA+ρI)−1(ATb+ρ(zk−uk))x^{k+1} = \left(A^TA + \rho I\right)^{-1} \left(A^Tb + \rho(z^k - u^k)\right)xk+1=(ATA+ρI)−1(ATb+ρ(zk−uk))

z-更新(解析解)

zk+1=ρλ+ρ(xk+1+uk)z^{k+1} = \frac{\rho}{\lambda + \rho}(x^{k+1} + u^k)zk+1=λ+ρρ(xk+1+uk)

对偶变量更新

uk+1=uk+xk+1−zk+1u^{k+1} = u^k + x^{k+1} - z^{k+1}uk+1=uk+xk+1−zk+1


五、MATLAB 源代码

matlab 复制代码
%% ADMM for Ridge Regression
clear; clc; close all;

%% ========== 问题参数 ==========
m = 50;          % 样本数
n = 10;          % 变量维度
A = randn(m, n);
b = randn(m, 1);
lambda = 1.0;    % 正则化系数
rho = 1.0;       % ADMM 惩罚参数

%% ========== ADMM 参数 ==========
maxIter = 200;
tol = 1e-6;
x = zeros(n,1);
z = zeros(n,1);
u = zeros(n,1);

%% 预计算(加速 x 更新)
AtA = A'*A;
Atb = A'*b;
invMat = (AtA + rho*eye(n)) \ eye(n);

%% ========== ADMM 主循环 ==========
residual = zeros(maxIter,1);

for k = 1:maxIter
    % ---- x 更新 ----
    x = invMat * (Atb + rho*(z - u));
    
    % ---- z 更新 ----
    z_old = z;
    z = (rho / (lambda + rho)) * (x + u);
    
    % ---- 对偶变量更新 ----
    u = u + x - z;
    
    % ---- 残差(收敛判据)----
    r = norm(x - z, 'fro');          % 原始残差
    s = norm(rho*(z - z_old), 'fro');% 对偶残差
    residual(k) = max(r, s);
    
    if residual(k) < tol
        fprintf('ADMM converges at iteration %d\n', k);
        break;
    end
end

%% ========== 结果对比 ==========
x_admm = x;

% 解析解(闭式)
x_closed = (A'*A + lambda*eye(n)) \ (A'*b);

fprintf('ADMM 解与解析解的误差: %.2e\n', norm(x_admm - x_closed));

%% ========== 收敛曲线 ==========
figure('Color','white')
semilogy(1:k, residual(1:k), 'b-o', 'LineWidth',1.5)
xlabel('Iteration')
ylabel('Residual')
title('ADMM Convergence Curve')
grid on

六、运行结果说明

  • ADMM 解 ≈ 解析解(误差通常在 1e-10 量级)
  • 残差单调下降,最终进入平台
  • 迭代次数一般在 20~100 次 收敛

参考代码 实现用ADMM算法求解优化问题的一个简单算例 www.youwenfan.com/contentcsw/82535.html

七、如何改成 LASSO(重要扩展)

只要把 z-更新 换成软阈值(Soft-thresholding):

matlab 复制代码
z = soft_threshold(x + u, lambda/rho);
matlab 复制代码
function y = soft_threshold(x, kappa)
    y = sign(x) .* max(abs(x) - kappa, 0);
end

此时问题变为:

min⁡x  12∥Ax−b∥2+λ∥x∥1\min_x \; \frac{1}{2}\|Ax-b\|^2 + \lambda\|x\|_1xmin21∥Ax−b∥2+λ∥x∥1

这是 压缩感知 / 稀疏恢复 的核心模型。


八、工程调参建议

参数 建议
ρ 一般取 0.1~10,太小收敛慢,太大震荡
自适应 ρ 根据原始/对偶残差动态调整
停止准则 `max(
大规模问题 x-更新用 CG / Cholesky
相关推荐
星夜离尘5614 小时前
MATLAB 清洗 CSV 采样日志:重复时间戳、无效行、分组统计与自动出图
开发语言·matlab·数据分析·数据清洗·csv
星夜离尘5615 小时前
MATLAB FFT 单边幅度谱:归一化、奇偶长度与频谱泄漏的完整实验
开发语言·matlab·信号处理·频谱分析·fft
星夜离尘5615 小时前
MATLAB 5 点滑动平均:filter 与 conv 的输出对齐,以及 2 样本延时的含义
开发语言·算法·matlab·滤波·fir
道道_Love1 天前
AI 调 MATLAB 用 MCP 太难用?单元设计规范和测试用例,用原生 AI 一次生成
人工智能·matlab·设计规范
菜鸟~noob2331 天前
【电子战】第31篇:3D AOA 定位——方位+俯仰联合
开发语言·matlab·3d
iCxhust2 天前
Matlab求解发电机的极限切除角
开发语言·算法·matlab·电力系统
LMT_Lanmantech3 天前
MATLAB合规管理:如何避免侵权赔偿和审计风险
开发语言·matlab·信息可视化
Evand J3 天前
【PMSM例程6】永磁同步电机(PMSM)基于增广EKF的d-q轴电感分阶段辨识算法|电机参数估计与误差分析
算法·matlab·电机·ekf
Matlab程序猿3 天前
【MATLAB源码-第460期】基于matlab的OTFS通信系统SLM峰均比抑制及非线性功率放大器失真与误码性能仿真
开发语言·算法·matlab·slm·otfs
chhttty3 天前
Stateflow状态机建模:数据
matlab·simulink