多時(shí)段SOCP最優(yōu)潮流:基于MATLAB+YALMIP+CPLEX建模)
簡(jiǎn)介基于二階錐規(guī)劃的主動(dòng)配電網(wǎng)最優(yōu)潮流求解程序包面向電力系統(tǒng)專業(yè)研究生、配電網(wǎng)規(guī)劃與運(yùn)行研究人員以及具備一定MATLAB/CPLEX基礎(chǔ)的學(xué)習(xí)者。資源以IEEE33節(jié)點(diǎn)配電網(wǎng)為算例實(shí)現(xiàn)含風(fēng)電Wind、并聯(lián)電容器CB、靜止無功發(fā)生器SVG、有載調(diào)壓變壓器OLTC及儲(chǔ)能系統(tǒng)ESS的多時(shí)段24h協(xié)同優(yōu)化可幫助讀者掌握主動(dòng)配電網(wǎng)最優(yōu)潮流的建模方法與二階錐松弛求解技巧。程序包共17個(gè)文件壓縮包5.51MB。其中2個(gè)m文件為MATLAB主體程序提供骨灰級(jí)注釋便于逐行理解12個(gè)log文件為CPLEX求解過程記錄便于對(duì)照分析迭代與收斂情況png為配電網(wǎng)結(jié)構(gòu)示意圖pptx為潮流計(jì)算原理說明另有參考文獻(xiàn)zip可供延伸學(xué)習(xí)。這套程序包目前已有835人學(xué)習(xí)下載注釋詳盡、案例完整尤其適合初學(xué)者循代碼逐步搭建主動(dòng)配電網(wǎng)優(yōu)化框架并快速遷移至自己的研究場(chǎng)景。1. SOCP 這塊硬骨頭CPLEX 怎么啃下來分布式光伏、風(fēng)電大量接入 10kV 饋線后潮流方程從線性代數(shù)問題變成非凸優(yōu)化問題傳統(tǒng)的牛拉法只能做潮流計(jì)算沒法直接做“運(yùn)行點(diǎn)尋優(yōu)”。二階錐規(guī)劃SOCP是當(dāng)前主動(dòng)配電網(wǎng)最優(yōu)潮流里工程化程度最高的松弛手段。這套基于 MATLAB 的代碼把 24h 多時(shí)段、風(fēng)電機(jī)組Wind、電容器組CB、靜止無功發(fā)生器SVG、有載調(diào)壓變壓器OLTC和儲(chǔ)能ESS全部拉進(jìn)一個(gè) CPLEX 可解的錐優(yōu)化模型在 IEEE33 節(jié)點(diǎn)系統(tǒng)上做完整的最優(yōu)潮流分析注釋細(xì)到每個(gè)變量和每行約束都有說明。比較適合做配電網(wǎng)課題、正在入門凸優(yōu)化應(yīng)用、或想把非凸最優(yōu)潮流模型換成可求解 SOCP 的工程師。2. 從 DistFlow 到二階錐松弛非凸潮流怎么變成 CPLEX 能啃的模型2.1 輻射網(wǎng)下的 DistFlow 方程配電網(wǎng)最優(yōu)潮流不像輸電網(wǎng)那樣適合用節(jié)點(diǎn)導(dǎo)納矩陣直接寫因?yàn)?10kV 饋線大多是輻射狀結(jié)構(gòu)支路功率方向明確用支路潮流方程寫起來更直觀這就是 DistFlow 模型。記支路ij首端有功功率為P_ij、無功功率為Q_ij母線電壓幅值平方為V_i支路電流幅值平方為I_ij那么 in 每個(gè)時(shí)段t節(jié)點(diǎn)j的功率平衡可以寫成P_ij(t) - sum(P_jk(t)) - R_ij * I_ij(t) P_load_j(t) - P_gen_j(t) Q_ij(t) - sum(Q_jk(t)) - X_ij * I_ij(t) Q_load_j(t) - Q_gen_j(t)其中sum(P_jk(t))表示以j為首端的所有下游支路功率之和。電壓遞推關(guān)系則是V_j(t) V_i(t) - 2 * (R_ij * P_ij(t) X_ij * Q_ij(t)) (R_ij^2 X_ij^2) * I_ij(t)這三個(gè)等式只刻畫了潮流守恒真正讓模型變難的是最后一條I_ij(t) * V_i(t) P_ij(t)^2 Q_ij(t)^2。這個(gè)約束里既有電壓平方、電流平方又有支路功率的二次項(xiàng)整體是非凸的CPLEX 這類求解器沒法直接吃進(jìn)去。項(xiàng)目里面對(duì)這個(gè)等式做了二階錐松弛把“等號(hào)”改成“不小于”再變換成標(biāo)準(zhǔn)錐形式。2.2 為什么要松弛成錐而不是線性化把I_ij (P_ij^2 Q_ij^2) / V_i展開時(shí)可以寫成矩陣范數(shù)形式|| [2*P_ij; 2*Q_ij; I_ij - V_i] ||_2 I_ij V_i這個(gè)錐約束在數(shù)學(xué)上是凸的。對(duì)輻射狀配電網(wǎng)只要電壓幅值有合理上下界、目標(biāo)函數(shù)是網(wǎng)損最小松弛后的最優(yōu)解往往會(huì)落在原非凸問題的可行域邊界上也就是說松弛是精確的。實(shí)際調(diào)試時(shí)你會(huì)發(fā)現(xiàn)CPLEX 日志里每個(gè)支路電流約束基本都是緊的幾乎沒有“錐內(nèi)點(diǎn)”的浪費(fèi)。這里還有個(gè)常見誤用有人為了省事直接把I_ij設(shè)成常數(shù)或者把P_ij^2Q_ij^2做一階泰勒展開。前者適合配電網(wǎng)規(guī)劃估算但做 24h 運(yùn)行優(yōu)化時(shí)會(huì)低估網(wǎng)損后者在運(yùn)行點(diǎn)附近小擾動(dòng)下勉強(qiáng)可用遇到 OLTC 抽頭切換或 ESS 大功率充放就容易失真。這也是為什么在 IEEE33 節(jié)點(diǎn)上做多時(shí)段潮流優(yōu)化SOCP 比線性潮流更穩(wěn)妥。2.3 在 YALMIP 中寫下第一個(gè)錐約束項(xiàng)目里大量使用 YALMIP 建模錐約束不要手寫norm而是直接用cone函數(shù)CPLEX 識(shí)別更高效模型也更干凈。以支路ij為例% 支路電流平方 I_ij電壓平方 V_i支路功率 P_ij、Q_ij for ij 1:n_branch for t 1:24 idx_i br_from(ij); % 首端節(jié)點(diǎn)編號(hào) idx_j br_to(ij); % 末端節(jié)點(diǎn)編號(hào) V_i V_sq(idx_i, t); % 首端電壓幅值平方 L I_sq(ij, t); % 支路電流幅值平方 P P_branch(ij, t); Q Q_branch(ij, t); % || [2P; 2Q; L - V] ||_2 L V Constraints [Constraints, cone([2*P; 2*Q; L - V_i], L V_i)]; end endcone的第一個(gè)入?yún)⑹欠较蛳蛄康诙€(gè)入?yún)⑹欠稊?shù)的上界標(biāo)量整體表達(dá)的是||向量||_2 標(biāo)量。注意向量里第二項(xiàng)是L - V_i不是L V_i這在抄模型時(shí)非常容易寫反。如果寫反求解結(jié)果會(huì)變得很奇怪電壓曲線在某幾個(gè)節(jié)點(diǎn)上突然偏低但約束檢查又提示 infeasible。參數(shù)br_from和br_to可以直接從 IEEE33 初始數(shù)據(jù)生成也可以用[1:32;2:33]這種簡(jiǎn)單矩陣手工構(gòu)造本質(zhì)上是告訴 YALMIP 哪些節(jié)點(diǎn)之間允許有潮流。對(duì)比項(xiàng)DistFlow 原始形式SOCP 松弛形式適用網(wǎng)絡(luò)輻射狀配電網(wǎng)輻射狀配電網(wǎng)核心變量支路功率、電壓、電流平方同樣變量多一個(gè)錐約束約束性質(zhì)非線性等式非凸凸錐約束求解器支持需要 IPOPT 等非線性求解器CPLEX、MOSEK、Gurobi 原生支持3. 多時(shí)段元件建模Wind/CB/SVG/OLTC/ESS 的錐約束怎么進(jìn)模型3.1 Wind 的預(yù)測(cè)功率邊界與棄風(fēng)懲罰風(fēng)電機(jī)組在最優(yōu)潮流里通常不是簡(jiǎn)單設(shè)成恒定有功注入而是給一個(gè)預(yù)測(cè)出力上限實(shí)際出力由優(yōu)化器決定。這么做是為了兼顧棄風(fēng)當(dāng)線路電壓越過上限或儲(chǔ)能 SOC 接近滿時(shí)調(diào)度可以主動(dòng)壓低風(fēng)力出力。代碼里一般寫成% n_wind 臺(tái)風(fēng)電機(jī)組T 為 24 小時(shí) P_wind_max forecast_wind; % 24h 預(yù)測(cè)曲線維度 n_wind * T P_wind sdpvar(n_wind, T); % 實(shí)際調(diào)度出力連續(xù)變量 % 出力下限 0上限不超過預(yù)測(cè) Constraints [Constraints, 0 P_wind P_wind_max];變量定義要放在一個(gè)Constraints序列里不斷追加。forecast_wind在代碼里可能是從 Excel 或.mat文件讀取也可能在 m 文件里直接寫成 24 個(gè)數(shù)的數(shù)組。注意風(fēng)電場(chǎng)接入節(jié)點(diǎn)通常是無功支撐較弱的末端如果只約束有功不約束無功模型會(huì)從線路末端吸取大量無功導(dǎo)致 CPLEX 求解時(shí)間上升最好給風(fēng)機(jī)加Q_wind的容量約束例如-0.2 * P_wind Q_wind 0.2 * P_wind。3.2 CB 離散投切與 SVG 連續(xù)無功電容器組和 SVG 都是無功補(bǔ)償設(shè)備區(qū)別在 CB 是離散投切SVG 是連續(xù)調(diào)節(jié)。CB 建模時(shí)用binvar表示每組投切狀態(tài)再乘以單組無功容量得到總無功注入n_cb_group 5; % 5 組電容器 q_cb_single 0.1; % 每組 0.1 Mvar標(biāo)幺化后處理 u_cb binvar(n_cb_group, 24); % 投切狀態(tài)1 表示投入 Q_cb q_cb_single * sum(u_cb, 1); % 24 個(gè)時(shí)段的 CB 總無功 % 防止頻繁投切一天最大動(dòng)作次數(shù)限制 for g 1:n_cb_group Constraints [Constraints, sum(abs(diff(u_cb(g,:)))) 4]; end這里的sum(abs(diff(...)))是在統(tǒng)計(jì)相鄰時(shí)段投切狀態(tài)變化次數(shù)。diff對(duì)二進(jìn)制變量做差分結(jié)果可能是-1、0、1取絕對(duì)值再求和就是動(dòng)作次數(shù)。如果不加這個(gè)約束CPLEX 求解出來的 CB 策略看著很漂亮但實(shí)際沒法執(zhí)行因?yàn)槊堪胄r(shí)切一次電容器會(huì)嚴(yán)重縮短開關(guān)壽命。SVG 相對(duì)簡(jiǎn)單直接用連續(xù)變量并限制上下限Q_svg sdpvar(n_svg, 24); Constraints [Constraints, -Q_svg_max Q_svg Q_svg_max];兩者在目標(biāo)網(wǎng)損中的權(quán)重完全不同CB 基本是離散投切納入目標(biāo)沒有成本項(xiàng)容易和 OLTC 一起形成“整點(diǎn)切一刀”的鋸齒策略SVG 可連續(xù)調(diào)節(jié)通常也會(huì)給一個(gè)小權(quán)重避免高頻抖動(dòng)。3.3 OLTC 抽頭如何避免變比平方的非線性有載調(diào)壓變壓器通過改變變比k_t來調(diào)節(jié)電壓。直接寫V_secondary k_t^2 * V_primary會(huì)產(chǎn)生k_t^2和非線性乘積破化 SOCP 結(jié)構(gòu)。常見做法是把每個(gè)離散檔位對(duì)應(yīng)的k^2拆成固定數(shù)值然后用二進(jìn)制整數(shù)選擇tap_pos intvar(n_tap, 24); % 整數(shù)變量檔位位置 % 假設(shè) 9 檔tap_pos 范圍 -4 到 4 Constraints [Constraints, -4 tap_pos 4]; % 通過重復(fù)矩陣或者表查映射把 tap_pos 換成變比平方 k2_table [0.975^2 0.98^2 0.985^2 0.99^2 1^2 1.01^2 1.015^2 1.02^2 1.025^2]; k2 sdpvar(n_tap, 24); % 輔助連續(xù)變量 for t 1:24 for r 1:n_tap % 用 implies 方式填值實(shí)際工程中常用查找表 大 M end end嚴(yán)格說這里需要把整數(shù)變量與連續(xù)變量耦合代碼里通常會(huì)用一個(gè)表格矩陣做索引或者用一列二進(jìn)制變量對(duì)每個(gè)檔位獨(dú)熱編碼。CPLEX 支持 MISOCP因此 OLTC 離散檔位不會(huì)破壞整體模型結(jié)構(gòu)但會(huì)顯著增加分支定界節(jié)點(diǎn)數(shù)量。調(diào)參時(shí)優(yōu)先改善的就是這個(gè)部件如果 24h 模型求解太慢先放寬抽頭動(dòng)作次數(shù)約束比調(diào)求解器參數(shù)更有效。3.4 ESS 的 SOC 遞推是 24h 模型的時(shí)間耦合核心ESS 是唯一讓不同小時(shí)之間產(chǎn)生耦合的元件。其余 Wind、CB、SVG 在時(shí)間維度上都是獨(dú)立斷面只是參數(shù)滾動(dòng)更新ESS 的荷電狀態(tài)SOC(t1)依賴SOC(t)這一條約束讓整個(gè)模型變成真正的多時(shí)段問題。代碼里通常用以下方式建模% dim: n_ess * (T1)多出一列存初始 SOC E_soc sdpvar(n_ess, 25); P_ch sdpvar(n_ess, 24); % 充電功率0 P_dis sdpvar(n_ess, 24); % 放電功率0 dt 1; % 時(shí)段間隔 1h也可以寫成 1 的標(biāo)幺值 for t 1:24 % 充電效率和放電效率分開考慮 Constraints [Constraints, E_soc(:,t1) E_soc(:,t) ... eta_ch * P_ch(:,t) - P_dis(:,t) / eta_dis]; Constraints [Constraints, 0 P_ch(:,t) P_ch_max]; Constraints [Constraints, 0 P_dis(:,t) P_dis_max]; Constraints [Constraints, E_min E_soc(:,t) E_max]; end Constraints [Constraints, E_soc(:,1) E_soc(:,25)]; % 24h 循環(huán)調(diào)度eta_ch與eta_dis通常取 0.9 到 0.95不要用同一個(gè)混著算否則充電到放電之間會(huì)產(chǎn)生虛擬能量增益CPLEX 會(huì)利用這個(gè)漏洞“憑空發(fā)電”得到很小的網(wǎng)損但物理上不可能。E_soc(:,1) E_soc(:,25)是日循環(huán)邊界條件如果做跨天調(diào)度可以改成和前一天終端 SOC 綁定。功率上限建議用額定功率但有些代碼里會(huì)默認(rèn) 0.5MW標(biāo)幺化后要仔細(xì)換算。元件決策變量類型典型約束多時(shí)段耦合Wind連續(xù)有功/無功0 P 預(yù)測(cè)上限無CB二進(jìn)制投切動(dòng)作次數(shù)限制較弱SVG連續(xù)無功-Qmax Q Qmax無OLTC整數(shù)抽頭檔位范圍、動(dòng)作次數(shù)較弱ESS連續(xù)充放電功率SOC 更新、功率上下限強(qiáng)4. MATLABYALMIPCPLEX 鏈路從 IEEE33 數(shù)據(jù)到 24h 求解4.1 IEEE33 數(shù)據(jù)組織和標(biāo)幺值選擇項(xiàng)目里的IEEE33BW.m和IEEE33_2.m就是入口腳本。打開后最前面通常是一堆基礎(chǔ)數(shù)據(jù)33 個(gè)節(jié)點(diǎn)、32 條支路的電阻電抗、每個(gè)節(jié)點(diǎn)的有功無功負(fù)荷以及各臺(tái)設(shè)備的接入母線編號(hào)。這些數(shù)據(jù)必須轉(zhuǎn)成標(biāo)幺值否則 SOCP 迭代時(shí)數(shù)值范圍為差 6 個(gè)量級(jí)CPLEX 還沒開始分支定界就已經(jīng)先報(bào)數(shù)值警告。baseMVA 10; % 功率基準(zhǔn) 10MW視具體系統(tǒng)調(diào)整 baseKV 12.66; % 電壓基準(zhǔn) 12.66kVIEEE33 基準(zhǔn)值 % 負(fù)荷標(biāo)幺化 load_p_pu load_p_mw / baseMVA; load_q_pu load_q_mvar / baseMVA;baseMVA的選取和網(wǎng)絡(luò)電壓等級(jí)相關(guān)IEEE33 基準(zhǔn)負(fù)荷約 3.7MW用baseMVA10會(huì)讓大部分變量落在 0.01 到 1 之間數(shù)值條件較好。如果直接用 MW 做單位支路功率和網(wǎng)損差 3 個(gè)數(shù)量級(jí)CPLEX 求解器內(nèi)部的尺度化步驟會(huì)花掉大量時(shí)間。項(xiàng)目日志里的clone0.log到clone11.log就是不同參數(shù)組合下的 CPLEX 運(yùn)行日志通過對(duì)比這些日志可以清楚看到標(biāo)幺值對(duì)迭代次數(shù)和求解時(shí)間的影響。4.2 目標(biāo)函數(shù)和 CPLEX 參數(shù)設(shè)置目標(biāo)函數(shù)常見組合是網(wǎng)損最小、棄風(fēng)懲罰、抽頭動(dòng)作懲罰三部分加權(quán)% 網(wǎng)損所有支路電阻 * 電流平方 * dt loss sum(sum(R_branch .* I_sq)) * dt; % 棄風(fēng)懲罰預(yù)測(cè)值減實(shí)際出力 curtailment sum(P_wind_max - P_wind); Objective loss penalty_curtail * curtailment;實(shí)際代碼里可能只有前兩項(xiàng)也可能額外加上 CB 動(dòng)作次數(shù)懲罰。penalty_curtail不宜設(shè)得太大否則會(huì)把網(wǎng)損優(yōu)化的空間完全壓掉導(dǎo)致儲(chǔ)能不充不放一直維持 SOC 邊界。比較合理的做法是先單獨(dú)跑一次不棄風(fēng)情況下的網(wǎng)損下限再把懲罰系數(shù)按網(wǎng)損的 3 到 5 倍設(shè)置。求解器參數(shù)在sdpsettings里傳入ops sdpsettings(solver, cplex, ... verbose, 2, ... cplex.mip.tolerances.mipgap, 1e-4, ... cplex.timelimit, 3600, ... savesolveroutput, 1); sol optimize(Constraints, Objective, ops);cplex.mip.tolerances.mipgap控制最優(yōu)性間隙10kV 配電網(wǎng)下網(wǎng)損通常在 0.05 到 0.2MW 之間設(shè)成1e-4已經(jīng)足夠如果繼續(xù)設(shè)成1e-6CPLEX 會(huì)陷入長(zhǎng)時(shí)間分支定界而收益只是網(wǎng)損多準(zhǔn)確幾個(gè)小數(shù)點(diǎn)。timelimit是硬性保護(hù)多時(shí)段含 OLTC、CB 的 MISOCP 模型很容易超過 30 分鐘。savesolveroutput為 1 時(shí)會(huì)保留 CPLEX 原始日志到 YALMIP 結(jié)果對(duì)象里排錯(cuò)時(shí)可以直接看sol.solveroutput.info。4.3 求解完成后的結(jié)果對(duì)象怎么讀取optimize返回后不要立刻value()所有變量先看sol.info和sol.solvertimeif sol.problem 0 fprintf(求解成功用時(shí) %.2f s\n, sol.solvertime); else disp(sol.info); endsol.problem 0表示求解正常完成1表示 infeasible2表示 unbounded9表示 NaN 值。如果sol.problem是 0 但后面value(V_sq)里出現(xiàn) NaN通常不是求解器問題而是 YALMIP 變量沒有全部進(jìn)入約束集合某個(gè)孤立變量沒有被任何表達(dá)式引用value之后是空。這時(shí)候去檢查代碼里是否有某個(gè)sdpvar變量定義了卻沒進(jìn)入Constraints。CPLEX 參數(shù)作用項(xiàng)目中的建議值cplex.mip.tolerances.mipgap分支定界最優(yōu)化間隙1e-4cplex.timelimit求解時(shí)間上限3600 秒cplex.threads并行線程數(shù)4 或 8cplex.mip.display求解日志顯示頻率2cplex.mip.limits.nodes最大節(jié)點(diǎn)數(shù)1e6 或留空5. 求解失敗時(shí)CPLEX 日志和 check 函數(shù)怎么定位問題5.1 先看sol.info再看求解狀態(tài)遇到Infeasible時(shí)很多人第一反應(yīng)是擴(kuò)大 CPLEX 容差這是錯(cuò)誤方向。infeasible只說明約束集合本身沒有交點(diǎn)和數(shù)值容差關(guān)系不大。項(xiàng)目日志里如果出現(xiàn)infeasible優(yōu)先檢查 OLTC 的抽頭變量和 CB 的投切變量是否作用到母線電壓上。比如 CB 只是定義出了Q_cb但沒有寫進(jìn)節(jié)點(diǎn)無功平衡方程那這個(gè)變量孤立存在不會(huì)導(dǎo)致 infeasible反而是寫進(jìn)平衡方程但上下限沖突更容易觸發(fā)。在實(shí)際項(xiàng)目中的排查順序是先注釋掉 ESS 的 SOC 遞推約束改成單時(shí)段斷面分別求解看每個(gè)時(shí)段是否可行。如果單時(shí)段可行、24h 不可行說明 SOC 初值或容量邊界設(shè)置不合理。再把 OLTC 抽頭范圍從-4:4擴(kuò)大到-8:8看是否依然 infeasible。若可行說明電壓約束和變比范圍沖突。最后檢查潮流方程里的I_ij松弛是否寫漏了節(jié)點(diǎn)編號(hào)特別是br_from和br_to從 1 開始索引還是從 0 開始。MATLAB 的索引從 1 開始如果原始數(shù)據(jù)來自 Python 習(xí)慣很容易錯(cuò)位。5.2 用check(Constraints)檢查約束緊度YALMIP 的check函數(shù)會(huì)返回每條約束的殘差這是驗(yàn)證松弛平坦度和模型準(zhǔn)確性最快的方法。代碼片段如下% 求解結(jié)束后檢查所有約束 residual check(Constraints); [max_res, idx] max(abs(residual)); if max_res 1e-5 fprintf(最大誤差出現(xiàn)在第 %d 條約束\n, idx); Constraints(idx) end注意 YALMIP 的check返回值在約束滿足時(shí)為負(fù)數(shù)或 0這個(gè)負(fù)數(shù)值是松弛不等式左側(cè)減右側(cè)的差。通常max_res在1e-7到1e-5之間。如果某個(gè) SOC 約束的殘差達(dá)到1e-2問題大概率不是求解精度而是cone的參數(shù)順序?qū)懛?。比如把cone([P;Q], L)寫成cone(L, [P;Q])YALMIP 會(huì)把它解釋成L norm([P;Q])這個(gè)約束完全變了形。建議在代碼里加一條調(diào)試命令% 輸出錐約束的數(shù)量對(duì)比與 n_branch*24 是否一致 fprintf(錐約束數(shù)量: %d\n, n_branch * 24);5.3 CPLEX 參數(shù)里的幾個(gè)“救命開關(guān)”如果模型可行但求解時(shí)間極長(zhǎng)或者日志里大量出現(xiàn)Numerical difficulties需要調(diào)整 CPLEX 的線性求解器行為。常見做法是ops sdpsettings(ops, cplex.lpmethod, 4); % barrier 方法 ops sdpsettings(ops, cplex.mip.strategy.search, 1); % 深度優(yōu)先 ops sdpsettings(ops, cplex.mip.stagnation.nodes, 50000);cplex.lpmethod設(shè)為 4 是 use barrier對(duì) SOCP 的根節(jié)點(diǎn)求解通常比默認(rèn)單純形更好。mip.strategy.search設(shè)為 1 是深度優(yōu)先適合中等規(guī)模但整數(shù)變量集中的模型。stagnation.nodes用來檢測(cè)目標(biāo)值長(zhǎng)時(shí)間不變的停滯達(dá)到閾值后 CPLEX 會(huì)自動(dòng)加全局切開平面。還有一類問題表現(xiàn)為求解結(jié)果可用但某兩個(gè)時(shí)段間 CB 投切完全相反這通常是目標(biāo)函數(shù)缺少對(duì)動(dòng)作次數(shù)的懲罰導(dǎo)致所有無功方案網(wǎng)損相同CPLEX 隨機(jī)選了一個(gè)最優(yōu)頂點(diǎn)。這時(shí)候調(diào)整目標(biāo)權(quán)重比調(diào)求解參數(shù)重要。可以給動(dòng)作懲罰設(shè)一個(gè)很小的正數(shù)只要大于數(shù)值噪聲就能穩(wěn)定輸出平滑策略。日志特征真實(shí)含義項(xiàng)目里優(yōu)先動(dòng)作Infeasible約束無交集檢查 ESS SOC 和 OLTC 檔位邊界Unbounded目標(biāo)無下界檢查風(fēng)機(jī)無功和網(wǎng)損表達(dá)式方向Numerical difficulties數(shù)值剛度大調(diào)整lpmethod和標(biāo)幺值Node limit exceeded分支定界節(jié)點(diǎn)爆炸放寬 mipgap 或抽頭檔位Integer optimal求到最優(yōu)整數(shù)解讀value前先看剩余間隙6. 24h 結(jié)果的工程化校驗(yàn)從 v2、I2 再到物理可信度6.1 從優(yōu)化變量回到傳統(tǒng)潮流結(jié)果SOCP 求解得到的是電壓平方、電流平方和支路功率直接畫電壓曲線時(shí)很多人會(huì)犯一個(gè)錯(cuò)誤用sqrt(value(V_sq))得到幅值卻沒乘以母線基準(zhǔn)電壓。IEEE33 的基準(zhǔn)電壓是 12.66kV標(biāo)幺化后電壓平方落在 0.950. 到 1.05、之間換算成實(shí)際電壓要乘回baseKV。代碼里可以這樣寫V_pu sqrt(value(V_sq)); % 標(biāo)幺電壓維度 n_bus*24 V_kv V_pu .* 12.66; % 實(shí)際電壓 kV bus_10_charge V_pu(10,:); % 挑一個(gè)末端節(jié)點(diǎn)觀察 figure stairs(1:24, bus_10_charge)觀察第 10 號(hào)節(jié)點(diǎn)在夜間和午間的電壓波動(dòng)。風(fēng)電機(jī)組高發(fā)時(shí)段如果電壓升高超過 1.03pu說明無功支撐或變壓器檔位調(diào)整不足以完全抑制電壓抬升。這時(shí)候 CB 和 SVG 的出力會(huì)體現(xiàn)為無功注入而 OLTC 的檔位變化可以在value(tap_pos)上看到明顯的整點(diǎn)跳變。要注意SOCP 模型對(duì)電壓平方做松弛輸出的V_sq理論上是滿足網(wǎng)損最小的最優(yōu)值但不一定滿足該節(jié)點(diǎn)單相電壓的實(shí)際諧波和三相平衡約束做工程推廣時(shí)還需要回到三相潮流進(jìn)一步校驗(yàn)。6.2 一個(gè)馬上可以驗(yàn)證的擴(kuò)展儲(chǔ)能 SOC 下界靈敏度這套代碼最值得動(dòng)手改的地方是 ESS 的E_min。把 SOC 下界從 0.1 改成 0.3重新求解然后對(duì)比網(wǎng)損和棄風(fēng)量E_min_list [0.1 0.2 0.3 0.4]; for k 1:length(E_min_list) E_min E_min_list(k); % 重復(fù)上一輪建模和求解 optimize(Constraints, Objective, ops); loss_result(k) value(loss); wind_curtail_result(k) value(curtailment); end這個(gè)靈敏度分析可以很容易判斷儲(chǔ)能容量是否還有擴(kuò)容空間。如果 SOC 下界從 0.1 提到 0.3 后網(wǎng)損只增加 0.5%說明儲(chǔ)能多數(shù)時(shí)段處于高 SOC 區(qū)域容量冗余較充足如果網(wǎng)損增加超過 5%則說明儲(chǔ)能深度充放對(duì)削峰填谷影響很大此時(shí)加強(qiáng)對(duì)充放電功率的時(shí)序約束比單純?cè)黾尤萘扛鼊澦?。另有一個(gè)小技巧把P_ch和P_dis的上下限從固定值改成P_ch_max * u_ess和P_dis_max * (1-u_ess)引入一個(gè)充電放電互斥的二進(jìn)制變量u_ess可以避免求解結(jié)果出現(xiàn)同一儲(chǔ)能同時(shí)充電和放電的“套利”假象。雖然目標(biāo)函數(shù)本身會(huì)抑制這種浪費(fèi)但在無網(wǎng)損懲罰或雙峰電價(jià)場(chǎng)景下不加互斥約束時(shí) CPLEX 經(jīng)常給出同時(shí)充放的病態(tài)解。本文還有配套的精品資源點(diǎn)擊獲取