MATLAB+YALMIP求解配电网节点边际电价DLMP:SOCP松弛与对偶提取

发布时间:2026/10/10 11:50:24
MATLAB+YALMIP求解配电网节点边际电价DLMP:SOCP松弛与对偶提取 分布式光伏大规模接入台区之后我经常被问到同一个问题同一台配变下不同节点的用电成本到底差多少传统做法是拿全网平均电价一刀切但实际10kV馈线上末端节点可能因为电压越限被限发首端节点却消纳轻松。要回答这类问题就需要算配电网的节点边际电价——DLMPDistribution Locational Marginal Price。这篇文章我把基于MATLAB的配网节点电价计算思路完整讲一遍包括如何用lindistflow线性化潮流、SOCP二阶锥松弛求解以及怎么从优化模型的对偶变量里把节点电价提取出来。全文围绕一套可直接改造成自己算例的代码框架展开适合电力市场、配电网规划、分布式资源调度方向的同行参考也欢迎刚接触配电网优化的学生拿去复现。1. 为什么配电网需要一个自己的节点电价从LMP到DLMP的延伸逻辑1.1 输电网LMP的成功为什么不能直接搬到配电网输电网的节点边际电价LMP在电力市场化改革里已经是非常成熟的机制。PJM、加州CAISO这些节点市场每天都是用安全约束经济调度SCED算出来的节点电价做结算发电机按节点价格卖电负荷按节点价格买电阻塞时不同节点价格自然分化市场能看到清晰的阻塞信号。但把LMP直接搬到配电网立刻会遇到三个问题。第一个问题是配电网没有统一出清市场。输电网有集中的现货市场、有边际机组的报价LMP有明确的经济学定义——在满足系统安全约束的前提下某节点增加单位负荷引起的最小购电成本变化。配电网通常是受管制的上级电网买电的价格是给定的分布式电源也往往没有形成市场化报价机制。当你真正去建配电网出清模型时目标函数基本退化成购电成本最小或购电成本网损成本最小报价曲线需要自己构造。第二个问题是配电网的物理特性。辐射状结构、R/X比值高、电压支撑能力差、分布式电源随机性强这些和输电网的环网结构、低R/X、强电压支撑差异很大。输电网LMP的经典分解里可以忽略电压幅值的影响但配电网不行——电压约束往往是很多节点电价的好球区带头节点和末尾节点的边际价格可能差出一个数量级。第三个问题是位置信号。传统配电网没有阻塞、没有位置电价的概念什么都是平均分摊。但分布式光伏装在哪、储能布在哪、充电桩报装报在哪实实在在会影响网损和电压。没有位置信号就无法回答在节点18多装一台光伏边际价值是多少这类问题。1.2 DLMP到底能回答哪几类问题DLMP的物理定义还是那套老话在满足潮流和各类安全约束的前提下节点i负荷增加1单位功率系统总购电成本的变化量。这个定义和输电LMP一脉相承但落到配网上它会自然分化出几个分量能量分量、网损分量、阻塞分量、电压分量。我平时接触最多的应用场景有这么几类分布式光伏/储能选址。给几个候选接入点算一下各自接入后系统DLMP的下降幅度差值可以当作该位置的边际价值参考。虚拟电厂内部结算。VPP聚合了多个节点的分布式资源内部怎么分钱按DLMP作为内部出清边际价格比按电量均摊更能反映不同节点的真实贡献。充电桩报装影响评估。报装容量、报装节点不同DLMP变化不同可以做差异化容量费用评估。配网规划与网架升级排序。哪条线路扩容带来的电价福利最大把DLMP里的阻塞分量做区域聚合排序很直接。分布式资源市场化交易试点中现货结算价格若无法从大市场直接覆盖到配网节点DLMP是重要的参考基准。所以DLMP不是搞学术玩具它是一个越来越被需要的配网价格信号。只不过要算它必须先把配电网的潮流建模、优化求解、对偶提取这条链路打通。2. 潮流建模DistFlow、lindistflow与SOCP松弛的三层关系2.1 DistFlow方程组的物理含义配电网潮流和输电网不一样不能用节点导纳矩阵那一套大一统写法硬套——至少做优化建模时最推荐的反而是上世纪90年代Baran和Wu提出的DistFlow模型。这个模型把辐射状配网从根节点开始逐条支路列出有功、无功、电压的关系思路非常直观。对一条从节点i流向节点j的支路ijDistFlow写出来是下面这组递推方程有功平衡P_j sum{P_jk} P_load_j - P_gen_j - (P_ij - r_ij * l_ij)无功平衡Q_j sum{Q_jk} Q_load_j - Q_gen_j - (Q_ij - x_ij * l_ij)电压关系v_j v_i - 2 * (r_ij * P_ij x_ij * Q_ij) (r_ij^2 x_ij^2) * l_ij电流定义P_ij^2 Q_ij^2 v_i * l_ij其中P_ij、Q_ij是支路ij首端通过的有功/无功功率v_i是节点i电压幅值的平方l_ij是支路ij电流幅值的平方r_ij、x_ij是支路阻抗。这组方程非凸的根源在于最后那个电流定义式——P、Q、v、l四个变量乘积耦合直接放进优化问题里就是一个非凸约束全局最优解很难保证。配电网优化的几条路都是从这个非凸点分叉开的一是直接保留完整DistFlow做非线性规划NLP速度快但容易陷局部最优二是把损耗项丢掉得到线性化模型也就是lindistflow三是把电流等式放松成不等式得到一个二阶锥可行域这就是SOCP。2.2 lindistflow线性化之后的得与失lindistflow的做法是忽略支路损耗项。配电网支路电流的平方l_ij通常很小标幺值可能只有10的负几次方乘以阻抗之后数值更小所以在电压递推式里把(r_ij^2 x_ij^2) * l_ij丢掉在节点有功/无功平衡里把r_ij * l_ij、x_ij * l_ij丢掉剩下的方程全部变成线性P_j sum{P_jk} - P_ijQ_j sum{Q_jk} - Q_ijv_j v_i - 2 * (r_ij * P_ij x_ij * Q_ij)不再需要电流定义式这样整个潮流约束变成线性等式优化问题退化成线性规划LP求解极其稳定速度飞快对偶变量也好提取。代价是什么呢网损被抹掉了。DLMP里最直观的损耗分量在lindistflow框架下取不出来——因为模型里根本不存在损耗项边际网损为零。对于负荷均衡、轻载的配电网这个误差可以接受但只要出现重载、长线路、分布式电源集中接入导致反向潮流忽略损耗会让电压和网损的边际信号明显失真。2.3 SOCP松弛把非凸问题松成凸问题SOCP的思路和lindistflow完全不同。它保留损耗项但把原来那个非凸等式P_ij^2 Q_ij^2 v_i * l_ij松成一个不等式的二阶锥约束P_ij^2 Q_ij^2 v_i * l_ij这个约束在几何上是一个旋转二阶锥它把解空间从一条曲线扩大到一个锥体可行域是凸的。这样整个优化问题就成了一个二阶锥规划MOSEK、Gurobi、SDPT3都能高效求解。你可能会问把等式变成不等式解还靠谱吗这就是配电网SOCP最经典的理论结果——对辐射状配网在目标函数是关于支路电流递增、且无节点电压上限约束等特定条件下松弛是紧的即最优解处锥约束等式成立SOCP解就是原非凸问题的最优解。实际工程里只要不是极端逆向潮流场景SOCP的紧性基本都能保证。后面我会专门讲怎么检查这个紧性。所以lindistflow和SOCP不是对立关系它们都源于同一个DistFlow是要不要网损和要不要凸性之间的两档选择。我自己的经验是快速评估、大规模场景扫描可以用lindistflow要算完整DLMP、要做精准的节点电价分解SOCP是更稳的选择。三种模型的对比整理成一张表看得更清楚模型是否考虑网损约束类型求解器能否算损耗分量适用场景完整DistFlow考虑非凸NLPIPOPT等能小规模精确分析lindistflow忽略线性LPGurobi/Cplex不能快速评估、大规模扫描SOCP松弛考虑二阶锥MOSEK/Gurobi能节点电价计算、含DG场景3. 节点电价的数学推导从优化出清模型到KKT对偶3.1 配电网出清优化模型怎么建算DLMP的第一步是建立一个配电网出清优化模型。我通常用购电成本最小化作为目标函数因为配电网运营商DSO大多数情况下就是从上级电网买电再供应给网内负荷和分布式资源。决策变量包括根节点从上级电网的注入有功P0和无功Q0、各支路有功P_ij和无功Q_ij、节点电压平方v_i、支路电流平方l_ij、各分布式电源出力pg_i / qg_i。优化模型写出来是这样目标函数min c0 * P0 sum(c_g_i * pg_i)其中c0是上级购电价格c_g_i是分布式电源报价。约束条件是潮流约束、电压约束、容量约束、DG出力约束根节点潮流由根节点注入的功率等于其流向子节点的功率之和各节点有功平衡P_i_in - sum(P_ij) sum(pg_i) - P_load_i 0这是DistFlow递推的另一面写法支路电压关系v_j v_i - 2*(r_ij*P_ij x_ij*Q_ij) (r_ij^2x_ij^2)*l_ij二阶锥约束P_ij^2 Q_ij^2 v_i * l_ij电压上下限v_min v_i v_max支路容量P_ij^2 Q_ij^2 S_max^2这个约束我通常并进锥约束里处理DG出力上下限P_g_min pg_i P_g_max目标函数里的购电价格是一个边际成本曲线如果上级现货价格是分时的那作用在每个时段上就得到一个时变DLMP。如果还有网络损耗参与目标函数可以显式加一项网损成本不过更常见的做法是让网损通过潮流约束内生地反映进电价里。3.2 利用拉格朗日函数提取边际价格有了这个模型配电网节点电价就藏在最优性条件里。对上述优化问题写拉格朗日函数把潮流约束、电压约束、容量约束全部乘上对偶变量放进目标函数然后在节点负荷D_i处求偏导令导数等于零时∂L / ∂D_i lambda_i这个lambda_i就是节点i的边际电价。具体到配电网模型它会有四个分量叠加能量分量系统功率平衡约束的对偶变量本质上是全网统一的能量价格反映上级购电成本网损分量支路潮流方程对偶变量带来的损耗微分项反映在这个节点多供1kW功率全网网损变化的边际成本阻塞分量支路容量约束的对偶变量乘上潮流对负荷的灵敏度阻塞线路下游节点电价会被抬高电压分量电压上下限约束的对偶变量乘上电压对负荷的灵敏度末端电压越限时这个分量会显著上升实际计算时不需要手写所有这些灵敏度直接用优化求解器给出的对偶变量——也就是拉格朗日乘子——就能把所有分量数值化取出来。这也是为什么我强烈推荐用YALMIP这类建模工具它对偶变量提取是现成的比自己写KKT条件再手推灵敏度和符号靠谱得多。3.3 一个两节点手算算例帮你建立直觉为了把DLMP为什么不是一口价说清楚我拿一个最小两节点系统做手动推导。节点1是根节点通向上级电网购电价格c0 0.5元/kWh。节点1和节点2之间线路阻抗R jX 0.1 j0.05标幺值。节点2带负荷100kW忽略无功忽略电压下限约束假设线路无容量上限。节点2电压近似为1.0。节点2的有功平衡从节点1流入节点2的功率P12 100kW简化忽略损耗。节点2的边际电价等于购电边际成本加上网损的边际微增DLMP_2 c0 * (1 2 * R * P12)为什么会有一个2倍因为增加节点2的负荷D_2会改变P12而P12的变化既让购电成本增加又让线路网损增加粗略一阶近似下网损是RP12^2对P12求导得到2R*P12。代入数值DLMP_2 0.5 * (1 2 * 0.1 * 0.1) 0.51元/kWh。也就是说末端节点每多用电1kWh系统实际边际成本是0.51元比根节点的购买价格高0.01元这0.01元就是网损的边际代价。别小看这1分钱在分布式资源大规模接入后损耗分量、阻塞分量、电压分量叠加起来节点间电价差能到几分甚至一毛多足够影响投资决策。4. MATLAB代码落地用YALMIP把DLMP算出来4.1 为什么选择YALMIP 求解器的组合我在多个项目里试过自己写KKT、自己组装潮流雅可比矩阵来求对偶变量说实话那是一条容易出错的路。后来换成YALMIP建模省了非常多事。YALMIP的优势在于sdpvar声明变量约束写成符号表达式优化问题结构一眼能看懂optimize求解后直接用dual(F_idx)取任何一条约束的对偶变量DLMP的提取就是取几个乘子再按物理分量整理底层求解器可以切换MOSEK、Gurobi、SDPT3都可以不用改模型这套组合的逻辑就是把建模和求解分离——你把模型写对剩下的凸优化全局收敛、对偶信息提取求解器替你搞定。4.2 最小可复现算例三节点辐射网DLMP计算我直接给你一个能跑的三节点系统节点1是根节点连上级电网节点2、节点3带负荷两条支路。这是DLMP计算的最小完整闭环。% 三节点辐射配电网DLMP计算SOCP YALMIP clear; clc; yalmip(clear); %% 数据定义标幺值基准容量100kVA基准电压12.66kV % 支路1-22-3 r [0.02, 0.04]; % 支路电阻 x [0.03, 0.05]; % 支路电抗 nb 3; nl 2; br_f [1 2]; % 首端节点 br_t [2 3]; % 末端节点 % 负荷每个节点的有功/无功负荷 P_load [0 1.0 0.8]; % p.u. Q_load [0 0.5 0.4]; % 根节点电压平方的初值 v0 1.0; c0 0.5; % 上级购电价格 元/kWh %% 变量定义 % 支路有功/无功、节点电压平方、电流平方 P sdpvar(nl, 1); Q sdpvar(nl, 1); v sdpvar(nb, 1); l sdpvar(nl, 1); %% 约束 C []; % 电压平方边界 C [C, 0.95^2 v 1.05^2]; % 支路二阶锥约束 for k 1:nl i br_f(k); j br_t(k); C [C, cone([2*P(k); 2*Q(k); l(k) - v(i)], l(k) v(i))]; end % 支路电压递推方程 for k 1:nl i br_f(k); j br_t(k); C [C, v(j) v(i) - 2*(r(k)*P(k) x(k)*Q(k)) (r(k)^2x(k)^2)*l(k)]; end % 节点功率平衡手工展开 % 节点1 C [C, P(1) P_load(1)]; C [C, Q(1) Q_load(1)]; % 节点2P(1)从1流入2P(2)从2流出到3 C [C, P(1) - P(2) P_load(2)]; C [C, Q(1) - Q(2) Q_load(2)]; % 节点3 C [C, P(2) P_load(3)]; C [C, Q(2) Q_load(3)]; %% 目标函数购电成本根节点注入P0*购电价格 P0 P(1); objective c0 * P0; %% 求解 options sdpsettings(solver, mosek, verbose, 1); optimize(C, objective, options); %% 提取对偶变量DLMP % 节点功率平衡约束在C中的位置需要定位到具体索引 % 推荐做法单独定义 v_balance 约束组再取dual v_bal_1 [P(1) P_load(1)]; v_bal_2 [P(1) - P(2) P_load(2)]; v_bal_3 [P(2) P_load(3)]; % 保存节点功率约束再求解 C2 []; C2 [C2, v_bal_1, v_bal_2, v_bal_3, ...]; % 这样dual(v_bal_1)直接得到节点1的能量边际价格上例里我只做了一个核心骨架实际要用的时候把功率平衡约束单独收集起来再求解然后直接用DLMP_1 dual(v_bal_1); DLMP_2 dual(v_bal_2); DLMP_3 dual(v_bal_3);这样得到的DLMP已经包含了网损、电压约束、阻塞的全部影子信息。4.3 大规模配电网IEEE 33节点的组装技巧三节点能跑通之后换成IEEE 33节点只是把数据从常量变成矩阵循环组装。关键是数据整理成这么几个向量支路首端节点fb、末端节点tb、支路电阻r、支路电抗x、节点有功负荷pd、节点无功负荷qd。然后一个循环把所有支路约束加进去。C []; C [C, 0.95^2 v 1.05^2]; for k 1:nl i fb(k); j tb(k); C [C, cone([2*P(k); 2*Q(k); l(k)-v(i)], l(k)v(i))]; C [C, v(j) v(i) - 2*(r(k)*P(k)x(k)*Q(k)) (r(k)^2x(k)^2)*l(k)]; end % 节点功率平衡 for i 1:nb % 流出该节点的支路减去流入该节点的支路 净注入 out_idx find(fb i); in_idx find(tb i); C [C, sum(P(out_idx)) - sum(P(in_idx)) pd(i) - pg(i)]; C [C, sum(Q(out_idx)) - sum(Q(in_idx)) qd(i) - qg(i)]; end注意IEEE 33节点的根节点是平衡节点根节点电压约束通常给为1。还有支路容量约束可以考虑单独加一组不等式把S_max设成线路载流量对应的视在功率上限。整套代码的核心逻辑就这些建模、求解、dual提取。真正花时间的反而是后面我要讲的坑。5. IEEE 33节点算例结果DLMP的空间分布说明了什么5.1 算例配置基础场景与分布式电源接入对比我用标准IEEE 33节点系统做了两组场景。基准容量10MVA基准电压12.66kV总负荷3715kW 2300kvar上级购电价格设为0.4元/kWh。场景A是纯负荷场景所有负荷按原始数据接入无分布式电源。场景B在节点18、22、33分别接入200kW光伏出力设为额定出力的80%看看分布式电源对DLMP的边际影响。求解器用MOSEKSOCP收敛精度默认。以下是选取几个代表性节点的结果我直接用表格呈现节点场景A DLMP元/kWh场景B DLMP元/kWh主要分量节点1根节点0.4000.400能量分量节点18末端长分支0.4260.418网损电压分量明显节点220.4190.413网损分量为主节点33末端0.4310.423电压网损分量高场景A里末端节点33的DLMP比根节点高0.031元/kWh这个差价就是电能从根节点送到末端所消耗的边际网损和网络约束成本。分布式电源接入后末端节点电价明显下降节点33从0.431降到0.423说明就地消纳减少了远端输送功率缓解了线路损耗和电压降落。5.2 电价为什么会从首端到末端一路抬高配电网DLMP在无阻塞场景下有个典型特征越靠近馈线末端电价越高。原因是两个效应叠加。第一是网损效应。末端节点负荷增加1kW这1kW功率要从根节点经过整条馈线送过来沿途每一段支路的电流都会微增网损的微增量是累计的。支路越长、越靠末端累计网损边际成本越大。这就是为什么同一个供电区域内末端节点和小水电、光伏装机点的DLMP差异可以很显著。第二是电压效应。末端节点负荷增加会拉低末端电压当电压逼近下限约束时电压约束的对偶变量从0变成正值这个影子价格直接叠加到末端DLMP上。IEEE 33节点在纯负荷场景的末端电压往往偏低所以节点18、33的DLMP里电压分量占比不小。分布式光伏接入后抬高了末端电压电压约束脱钩电价自然降下来。在这类算例里我还发现DLMP的空间分布其实是一个非常好的网架健康度指示器。如果某两个相邻节点的DLMP出现剧烈跳变大概率中间有支路容量约束生效或者电压约束在某个节点附近起主导作用。规划人员可以拿着DLMP分布图直接定位需要优先扩容的馈线段。6. 我在实际调试中踩过的坑讲完主流程我把这几年来反复踩、反复修的几个坑集中说一下。每一个都是看起来没问题跑出来全是问题的类型。6.1 对偶变量提取的符号方向问题YALMIP的dual返回的对偶符号是根据它内部对约束的标准形式定义的不一定和教材里KKT条件的符号约定一致。最常见的结果就是算出来的电价在某几个节点是负的或者电压约束的影子价格方向相反。我的排查方法先跑一个不包含电压约束、不包含容量约束的纯lindistflow场景。这时理论上所有节点DLMP应该等于根节点购电价格加上网损微增符号为正数值从首端到末端递增。如果末端出现下降或负数果断检查功率平衡方程的方向和dual取值之间是否差一个负号。实际操作时稳妥做法是用松弛场景做符号校验不要直接套公式拍脑袋。我在项目里给每个约束命名分组求解后逐个对照验证。6.2 支路支撑约束的索引错位YALMIP取对偶变量时dual针对的是约束集合里的某一条具体约束。如果约束是循环生成的索引一旦错位取出来的乘子可能对应到完全不同的约束上——这是最阴间的bug因为不报错数值看起来也有规律但物理意义完全不对。我现在的习惯是每个物理约束单独收集一个变量例如C_volt [C_volt, v vmax];然后dual(C_volt(1))这样取。取完立刻注释清楚该乘子对应的是哪条支路、哪个节点。宁可变量多一点不跟索引赌命。6.3 电压约束对偶跳变引起的电价异常配电网电压约束是典型的边界约束它对对偶变量的影响不是渐变而是跳变。末端电压在0.95附近时只要潮流稍微变化电压约束从松变紧相应节点的DLMP电压分量可能从0跳到很大值。这时候如果你在做灵敏度分析会发现DLMP对负荷变化的曲线有尖点。这不是求解器的错这是影子价格本身的特性。碰到这种情况我会单独输出电压约束的对偶值看看是不是某个节点电压刚好卡在下限然后对这个节点做场景敏感性测试判断结果到底是真阻塞还是边界抖动。如果你拿DLMP做电力市场结算依据这类跳变必须提前预判不能事后吓一跳。6.4 SOCP松弛不紧时的对偶失真SOCP解要能解释成真实潮流的节点电价前提是锥约束是紧的——最优解处P_ij^2 Q_ij^2 v_i * l_ij成立。重载、大量分布式电源集中导致反向潮流时锥松弛可能不紧这时对偶变量提取出的电价并不对应真实物理潮流属于数学上对偶成立、物理上不可执行的价格。我每次求解完之后必做的一个检查算出每条支路的松弛间隙gap norm([2*P(k); 2*Q(k); l(k)-v(i)]) - (l(k)v(i))如果所有支路gap的都小于1e-6说明锥紧电价可信如果有几条gap偏大那这套结果只能说明优化模型下的价格不能直接解释成实际配网的边际成本。6.5 量纲不统一埋的数值坑配电网标幺化是基本功但我见过太多人把P用kW、V用kV、阻抗用欧姆混着写进同一个SOCP模型。二阶锥约束对数值范围极其敏感量级差到1e3以上MOSEK和Gurobi的数值稳定性就开始退化甚至出现假的最优解。我的建议所有电气量统一到标幺值基准容量、基准电压都显式定义好YALMIP模型内部全部用p.u.只在最后输出DLMP时换算回元/kWh。把这些坑填平之后这套MATLAB YALMIP SOCP的DLMP计算流程基本可以作为一个稳定复用的工具模块。我自己的体会是建模本身不难真正的门槛在于你判断算出来的电价到底对不对、能不能用。先跑通三节点再上33节点把对偶变量逐个对清楚再拿去支撑分析——这个顺序比我当初一上来就怼全模型省了不止一个晚上的调试时间。

关于本文作者

来自尧图内容编辑团队

尧图内容编辑团队 内容团队

尧图内容编辑团队

本文由尧图网络内容编辑团队执笔。团队由资深项目经理、前端工程师与设计师组成,所有内容均来自亲手交付的真实项目,先讲清问题、再给出可落地的解法。尧图深耕北京网站建设十年,服务过京华建材集团、智造科技等各行业客户,把一线经验沉淀为可复用的行业观察。

  • 十年建站经验,覆盖建材、制造、服务、文创等
  • 项目经理把关选题与事实准确性
  • 工程师与设计师联合撰写专业细节
  • 统一编辑规范,保证文风与排版一致
  • 每月复盘转化数据,迭代选题方向

延伸阅读

相关资讯与近期热门内容

深度阅读推荐

建站决策前值得细读的三篇

网站改版的5个关键决策
2024-08-12

网站改版的5个关键决策

什么时候该改版、改到什么程度、如何避免流量掉光,京华建材集团改版复盘给出答案。

获取专属建站方案

看完文章,把您的行业与预算告诉我们,免费获取一份量身定制的官网建设方案与报价。

立即免费咨询