ARTICLE DETAIL

资讯详情

深耕编程入门与网站建设的一线实战洞察。

光伏储能双层优化配置配电网选址定容的Matlab实现

光伏储能双层优化配置配电网选址定容的Matlab实现 分布式能源选址与定容这事儿我这两年用Matlab做了不少算例从最初的盲试到后来能一小时跑完一套完整方案中间踩过的坑比代码行数还多。今天就把这套光伏、储能双层优化配置接入配电网的研究思路和Matlab实现经验完整拆开聊从模型怎么搭、代码怎么写到结果怎么解读一次性讲透。这套东西解决的核心问题就是两个光伏和储能装在哪、装多大。别小看这两个问题装错了位置光伏午间出力高峰可能直接把节点电压顶到越限储能容量选大了投资收不回来选小了削峰填谷根本不起作用。我在实际算例里见过不少方案网损确实降了但电压越限问题反而更严重典型的捡了芝麻丢西瓜。所以做选址定容不能只看单一指标。这套研究用双层优化把规划层的投资决策和运行层的调度策略解耦开上层决定装什么下层负责算清楚装完之后系统怎么运行、成本是多少再把运行结果反馈回上层作为方案评价依据。这种结构非常贴合电力系统里先规划、后运行的实际决策流程也是目前这个方向用得最多的建模方式。无论你是刚接触分布式能源规划的研究生还是在做配电网项目的工程师这篇文章都会把从建模到落地的关键环节讲清楚。模型目标函数怎么设、约束条件容易漏掉哪些、粒子群参数怎么调、内层求解器报错怎么处理这些常规论文里不会写细的东西我在下文里都给你交代明白。1. 为什么选址定容这么关键光伏储能在配电网里会惹什么麻烦1.1 光伏接入带来的电压抬升与消纳难题光伏发电有一个天然特性就是它的出力曲线和负荷曲线往往错位。午间光伏出力达到峰值的时候恰恰是居民和商用负荷的低谷期工厂还没到换班高峰空调负荷也还没起来。这时候多余的电只能顺着馈线往回送也就是业内常说的反向潮流。反向潮流一出现节点电压就会被抬高。这个抬升幅度在接入点附近最明显因为电流往回走线路压降的极性反转了。分布式光伏渗透率高的馈线末端节点电压在午间时段容易逼近甚至超过上限这在光伏资源好的地区尤其常见。电压越限的后果不只是电能质量不合格严重了会导致用户设备损坏、逆变器保护动作频繁启停甚至是馈线保护误动。光伏的另一个问题就是出力波动。云层飘过出力可能在半分钟内掉一半这种短时功率波动对配电网的调压和无功控制设备是很大考验。我做仿真的时候看到过一条馈线一分钟内电压波动超过3%这已经超过国标对电压变动的限值了。如果这些问题不在规划阶段就考虑进去等到实际运行出问题再来补救成本要高得多。1.2 储能的价值与选址定容的决策困境储能在配电网里的角色简单说就是搬运工加缓冲池。光伏出力高峰时把电存起来负荷高峰时再放出去既避免了午间电压抬升又能在晚高峰提供支撑。同时储能还能平抑出力波动让光伏并网点的功率曲线平滑很多。理论上讲储能是光伏接入配电网的最佳搭档。但储能的成本摆在那电池本体、PCS变流器、土地、运维加起来一套MWh级的储能系统投资不小。这就带来了决策困境储能不是装得越多越好装多了利用率上不去投资回收周期长得吓人也不是哪儿都能装装在不合适的位置线损降低效果差削峰填谷作用也发挥不出来。光伏的选址也是类似的逻辑光照资源好但设备老旧、容量紧张的馈线段未必比光照稍差但网架结构合理的节点更适合。这类问题看起来是选几个坐标、定几个容量本质上是在投资成本、系统安全、运行经济性三者之间找平衡点。纯靠经验拍脑袋选节点跑几个潮流算例看看结果很难保证方案是全局最优的。1.3 双层优化为什么比单层更贴合这个问题选址定容问题最直观的做法是搭一个混合整数非线性规划模型把所有投资决策变量和运行决策变量放一起求解。理论上没问题但这个模型里既有0-1整数变量装不装、连续变量容量多少、功率多少又有潮流方程这种强非线性约束再加上储能的时间耦合约束SOC的时序递推求解难度非常大。我用商业求解器试过直接求解单层模型中等规模算例跑几个小时还经常找不到可行解工程上根本没法用。双层优化把问题拆成了两层上层做投资决策下层做运行模拟。上层每次确定一组选址定容方案后下层就在这个方案下求解最优运行策略再把运行指标反馈给上层。这样每一层的问题规模都小了很多下层潮流和调度问题用成熟求解器就能快速求解上层用智能算法去搜索方案空间。更重要的一点是这种结构非常贴近实际决策流程——先定规划方案再做运行调度决策逻辑清晰也方便工程人员理解每个方案为什么优、为什么劣。2. 双层优化模型搭建上层定方案、下层算运行2.1 上层规划模型的目标函数与决策变量上层模型回答的问题是在哪些节点装、装多大容量。决策变量包括光伏的安装节点和装机容量以及储能的安装节点、额定功率和额定容量。这里有一个实际问题光伏和储能是否必须绑定安装在同一节点从我做的算例经验来看光伏和储能同点位安装的方案实施起来更简单征地、并网、运维都方便但未必是运行最优的。允许光伏和储能分别在适合的节点安装会给上层优化更大的搜索空间最终方案的综合经济性往往更好。不过要注意解绑后问题的组合爆炸特性会更明显对上层搜索算法的要求也更高。上层目标函数我通常设定为年综合费用最小或者年净收益最大。年综合费用包含几个部分一是光伏和储能的年化投资成本把总投资按寿命周期折成等年值二是年运行维护费用按装机容量的比例估算三是系统年运行费用这部分来自下层反馈包括向上级电网购电的费用和网损费用。如果算例设置了分时电价购电费用就要按峰平谷三个时段分别计算这也更符合实际。约束条件方面第一是投资预算约束总投资的现值不能超过给定预算上限。第二是各节点安装容量上下限约束比如单个光伏接入点的容量不能超过该节点变压器容量的某个比例。第三是安装节点数约束很多工程案例中会对分布式电源的总接入点数有限制因为每增加一个接入点就多一套并网设备。第四是渗透率约束分布式电源总装机容量占系统峰值负荷的比例不能超过设定值这个约束在消纳能力不足的地区尤其重要。2.2 下层运行调度模型的核心约束下层模型在每个上层方案下求解典型日的运行策略。目标函数是系统日运行成本最小化主要构成是向上级电网的购电成本加上网损成本。如果是夏季和冬季多个典型日分别计算就把每个典型日的运行成本加权汇总后反馈给上层。下层决策变量是每个时段的光伏实际出力和储能充放电功率。光伏出力在光照充足时通常全额消纳但如果出现电压越限风险也可以做弃光处理弃光惩罚系数设置得比较高就行。储能运行策略是典型的时间耦合问题需要满足前后时段的SOC递推关系充电效率、放电效率和自放电率都要考虑进去。潮流约束是下层模型的核心。在配电网计算中我一般用DistFlow分支潮流方程这个模型在处理辐射状配电网时精度足够且求解速度快。节点电压需要维持在允许范围内IEEE 33节点算例中我习惯设为0.95到1.05pu。线路传输功率不能超过载流量限制购买电力的联络线功率也要有限制。储能运行约束要特别注意除了SOC递推外还要保证一个调度周期结束后SOC回到初始值不然储能就在一个周期内偷偷赚能量结果没有实际意义。充放电功率不能同时为正值和负值如果有0-1变量能处理就直接处理如果没有通过大M法或者二进制变量方式也能解决。我在YALMIP里实现时习惯用二进制变量把充放电状态显式建模清晰不易出错代价是求解时间略长。2.3 上下层迭代求解的实现逻辑上下层求解的衔接方式常见的有两种路线。第一种是把下层模型通过KKT条件转换为上层模型的约束形成单层数学规划问题再求解。好处是用数学优化方法处理有最优性保证坏处是KKT转换要求下层是凸问题而且补松弛条件会引入大量非线性项最后模型复杂度依然很高。第二种是我更常用的方法上层用启发式算法比如粒子群下层用数值求解器精确求解上下层通过迭代实现嵌套。每次上层生成一组粒子的位置也就是一组选址定容方案然后逐一送入下层求解器计算运行成本把结果返回给上层更新粒子的适应度值。虽然计算量相比单层模型大不少但每一层的求解器都很成熟稳定性好出了问题也好排查。这里有个实操细节上下层之间的数据传递要定义好接口和单位。上层传给下层的是光伏安装节点序号、光伏容量、储能安装节点序号、储能功率和容量这些静态参数。下层返回的是典型日总运行成本、网损电量、弃光电量、最大电压偏移这些运行指标。如果单位不一致比如上层用kW下层用MW计算出来的数据可能就是天文数字或者接近零这个坑我在初版代码里踩过调试了半天才发现是单位问题。3. Matlab代码实现从IEEE 33节点算例到可复用框架3.1 算例系统与基础数据准备我用的测试系统是标准的IEEE 33节点配电网基准电压12.66kV系统总负荷大约3.7MW加2.3Mvar。这个系统的拓扑结构很规范节点和支路参数在很多论文里都能查到方便结果对比验证。关键是这个网络有33个节点、32条支路规模不大不小既能体现电压分布问题的复杂性又不会让内层求解器算得太慢。想研究更大规模的系统比如IEEE 69节点或123节点代码逻辑完全不用改只换数据文件就行。基础数据要准备这么几类。第一是线路参数每条支路的电阻电抗和最大载流量第二是节点负荷参数典型日的负荷曲线我在算例里取的是24个时段的标幺值曲线峰谷比大约1.5到2.0之间第三是光伏出力曲线夏季典型日取早6点到晚7点有出力午间12点到14点达到峰值峰值利用小时数我按全年1200小时倒推第四是分时电价数据我这里设定峰时段1.2元/kWh、平时段0.75元/kWh、谷时段0.4元/kWh储能就是在谷时充电、峰时放电来套利的。一种常见的做法是把光伏和储能的物理参数做在独立文件中。光伏逆变器功率因数设定为0.95储能系统充放电效率设为0.95SOC运行范围取10%到90%储能寿命按10年计光伏寿命按20年计。投资单价方面光伏按每千瓦3500元估算储能电池按每千瓦时1200元PCS按每千瓦500元这些参数可以根据自己所在地区的市场情况调整模型结构不用动。3.2 Matlab代码结构怎么组织才算顺手写这个代码初期我走过弯路把所有功能堆在几个大脚本里结果改一个参数要翻半天出了问题也不知道是建模错误还是求解器设置不对。后来重构之后我按功能拆成了三个模块数据模块、模型模块、求解模块。数据模块负责读取系统参数和规划参数模型模块负责构建上层和下层的目标函数及约束求解模块负责粒子群搜索和调用内层求解器。数据模块用结构体把参数组织起来比如sysData存线路和负荷数据planData存光伏储能成本及约束参数priceData存分时电价。这样在模型模块里引用参数就不用全局变量函数传参传入结构体就可以代码清晰很多。模型模块我拆成了两个函数buildUpperModel.m负责生成上层优化所需的适应度函数buildLowerModel.m负责构建内层YALMIP模型并求解。上下层迭代的主循环放在主程序main_double_layer.m里流程是初始化粒子群参数、生成初始粒子群、循环计算每个粒子的适应度调用下层求解器、更新粒子速度和位置、判断收敛条件、输出最优解。整个流程行数不长但逻辑一定要理清楚特别是粒子群的边界处理光伏容量和储能容量如果超出边界要拉回到边界内并重新计算适应度不然搜出来的结果可能是不可行的。3.3 上层粒子群的参数设置与实现细节粒子群算法在这个问题里的表现很大程度上取决于参数设置。我第一次跑的时候直接用了个默认参数组合种群规模30迭代次数100惯性权重0.8学习因子都是2.0结果收敛很慢而且多次运行结果差异大稳定性不好。调参之后我固定下来一套效果不错的参数。种群规模50迭代次数150惯性权重从0.9线性递减到0.4这个策略的好处是前期探索能力强后期限于局部搜索不容易错过最优区域。学习因子c1和c2都取2.0但速度上限设为变量范围的一半防止粒子飞出去太远导致适应度计算畸形。粒子编码方式我选择的是混合编码。前段是光伏安装节点编号后段是光伏容量值再后段是储能安装节点编号最后是储能功率和容量。节点编号用整数编码容量用实数编码。速度更新的时候整数部分用取整的方式处理实数部分用标准PSO公式。这种处理方式在实现时稍显麻烦但比把所有变量都变成实数的效果要好因为节点编号就是离散的整数硬用连续变量去逼近反而会引入无意义的中间值。有个容易踩的坑是粒子群初始化。节点编号不能随机生成重复值不然一个节点被选了两次实际上就是少了一个可用节点。我初始化时用randperm从可选节点集合里无放回抽取容量变量则用均匀分布随机生成。另外初始种群生成后建议做一次可行性检查把不满足投资预算约束的粒子直接重新生成比在迭代过程中靠惩罚函数去拉回要好得多。3.4 内层YALMIP模型的构建与求解器配置下层模型用YALMIP建模求解器我推荐用gurobi对混合整数二阶锥规划的支持非常好求解速度快。如果没有gurobi的license用cplex、mosek效果也不错。如果这些商业求解器都没有退而求其次用开源的cbc或ipopt也能算但在混合整数变量的处理上速度会慢很多。我不建议在YALMIP默认求解器状态下直接跑很多时候求解器选不对模型规模稍大就卡死。YALMIP建模的下层模型核心代码逻辑大概是这样定义优化变量包括各节点电压幅值、支路功率、光伏出力、储能充放电功率、SOC状态以及充放电状态的二进制变量。然后按刚才说的约束逐条添加用optimize命令求解。这里我强烈建议把求解器细节打开optimize的第三个参数设成solvesdp设置或者直接用options sdpsettings(solver,gurobi,verbose,0)把冗余输出关掉。我在调试阶段会把verbose打开看求解状态但批量跑粒子群时一定关掉不然终端刷屏刷到你怀疑人生。内层模型还有一个细节是时段间耦合。储能SOC是跨时段的变量不能把24个时段拆开单独求解必须整体建模。这意味着内层模型的变量数量是24倍的单时段变量规模对求解器来说压力还是有的。我在33节点算例上单次内层求解时间大约在0.5到1.5秒之间粒子群50个粒子150次迭代理论上总计算量不小。实际跑的时候可以并行化处理用parfor把每个粒子的适应度计算分散到多核上整体耗时可以从两个多小时压缩到半小时以内这个优化非常值得做。内层模型构建时的潮流约束我建议用二阶锥松弛处理。DistFlow方程本身有凸性配电网辐射状的特性让二阶锥松弛在很多标准算例下是紧的也就是说松弛后的解和原问题解误差很小。用二阶锥的好处是模型是凸的求解器可以在多项式时间内求解稳定性大大提高。做结果验证时可以检查松弛间隙来判断松弛是否紧如果间隙大需要增加约束来收紧模型。4. 结果分析怎么看方案评价的关键指标与典型结果4.1 选址定容结果与经济性判断跑完程序后最关心的自然是结果。我在33节点算例里得到的一个典型方案是光伏安装在第18节点线路末端附近和第25节点容量分别为500kW和300kW储能安装在第18节点和第30节点功率容量分别是200kW/400kWh和300kW/600kWh。这个规律其实符合配电网规划的基本逻辑——电压偏低的末端节点恰恰是光伏和储能最能发挥作用的位置因为就地支撑能直接改善电压分布。判定经济性要看几个关键指标。第一是年化总投资成本假设光伏总投资280万元储能总投资216万元寿命期内折算到每年的成本大约是34万元和33万元左右。第二是年运行费用的变化如果没有光伏储能系统年购电费用大约在520万元网损折算约30万元加了分布式光伏储能之后购电费用降到450万元网损降到20万元左右加上储能的峰谷套利收益大约10万元。综合起来年净收益大约70万元左右投资回收期能控制到6到7年。但要注意不同光伏和储能容量配比下经济性差异很大。我做过一组对比实验储能容量从200kWh增加到800kWh时投资成本快速上升而运行收益的边际增加在600kWh之后就明显变缓。这说明储能的最佳容量范围有个甜点区容量超出某个阈值后边际效益下降不单纯是越大越好。这也是为什么选址定容问题不能简化成经验估计必须做优化搜索的原因。4.2 电压分布与网损改善效果验证方案效果验证最直观的方法是画出24小时的节点电压分布图。我在对比实验里的数据很典型未接入光伏储能前18号节点晚高峰时段电压低到0.938pu已经低于0.95pu的下限午间时段因为光伏出力反送25号节点电压又能抬到1.06pu左右属于一头低一头高的双重越限状态。接入优化方案后情况明显改善了。午间光伏出力就地消纳剩余部分充入储能25号节点电压稳定在1.03pu以内晚高峰时段储能放电18号节点电压回升到0.96pu以上。全天各节点电压都保持在0.95到1.05pu的安全范围内电压合格率从优化前的78%提升到接近100%。网损方面系统日网损电量从原来的1320kWh降到约880kWh降幅超过30%损耗改善效果非常明显。这些数据也可以用表格固化下来作为论文里的结果支撑。一般我会整理一个对比表分别列出无分布式电源、光伏单独接入、光伏储能接入三种情况下的电压极值、网损率、购电费用、DG渗透率等指标这样评审老师看起来一目了然自己核对结果时也方便。5. 常见问题与排查技巧实录5.1 内层求解器报不可行怎么查这是我在调试阶段最常遇到的情况。内层模型报infeasible problem说明给定方案下运行约束无法满足。最常见的触发原因是电压约束设得太紧特别是线路末端节点在某些恶劣的运行方式下电压已经不可能回到安全区间。排查方法是先把电压约束放松到0.90到1.10pu范围跑一遍如果这样能求解成功基本可以确定问题出在约束范围上。第二个常见原因是储能SOC约束矛盾。比如SOC范围设置成了10%到90%但调度周期结束又要求SOC回到初始值如果初始值设置得太高或充放电效率太低储能在一天内放不完也充不满就可能出现无解。这时把SOC初值设成50%或调整结束SOC的允许偏差范围通常问题就解决了。第三个原因是求解器数值问题。DistFlow方程里如果电阻值太小或导纳值太大数值矩阵会出现病态也会导致求解器误判不可行。排查办法是检查数据文件里有没有异常值线路阻抗如果是标幺值系统看看基准值是不是设置对了。我在处理一个69节点算例数据时发现有一条支路的电阻被人为填成了0.00001欧姆显然不对修正后模型就正常了。5.2 粒子群收敛太慢或者陷入局部最优粒子群在这个问题里最典型的症状是迭代到四五十代后适应度就不再下降但你知道这个结果并不是全局最优因为稍微改变几个安装节点成本就能降不少。这种问题通常是粒子多样性不足造成的。解决思路有两个方向。第一是调大惯性权重的初始值让粒子在前期有更强的探索能力减少过早收敛到局部最优的概率。我原来用的是0.8到0.4线性递减改成0.95到0.35线性递减之后虽然收敛速度慢了十几代但最终结果明显更优。第二是引入变异操作。每次迭代结束后随机选一小部分粒子对节点编号做重新随机化相当于强制注入新信息防止整个种群陷入同一个局部区域。还有一种情况是适应度函数计算有误导致伪最优。我遇到过一次适应度计算时把储能投资成本的单位弄错了导致算法永远在往储能容量偏小的方向搜索。排查这类问题的方法很直接取一个已知可行方案手算一遍适应度值和程序算出来的对比如果对不上就逐步排查目标函数里每一项的单位和符号。5.3 运行时间太长怎么办粒子群嵌套潮流计算天然耗时我在早期的串行版本算过50个粒子150次迭代跑了近三个小时调试体验非常差。优化方向有三个层次。第一层是选择更快的潮流求解方式。如果只是需要计算电压分布和网损可以不用YALMIP搭完整的优化模型直接用Matpower或者手写牛顿拉夫逊法算潮流这样单次计算耗时能降到几十毫秒。但这种方式没法显式模拟储能的最优调度策略储能充放电曲线只能按固定规则比如谷充峰放来给定精度会打折扣。第二层是并行化。用parfor替换for循环让每个粒子的适应度计算分配到不同的工作线程上。我实测下来六核机器能提速四倍多。需要注意的是parfor循环内不要共享数据每个粒子的适应度计算必须完全独立结果保存用单元格数组或者按索引写入。第三层是减少不必要的计算。粒子群每次更新位置后只有部分粒子发生了变化但早期版本我每次都对所有粒子重新计算适应度浪费了大量算力。优化后可以只重算变化过的粒子对未变化的粒子沿用历史适应度值。这个方法在问题规模大的时候效果尤其显著。5.4 YALMIP求解器设置和数值稳定性细节最后提几个YALMIP使用上的小坑。一个是全局默认精度设置sdpsettings(gurobi, struct(MIPGap, 1e-4))求解器类型中的MIPGap参数要设置好。如果不设求解器可能默认追求精确解收敛很慢设成1e-3甚至5e-3对分布式能源规划问题来说精度足够速度能快不少。另一个是模型导出和调试技巧。如果内层模型经常报错可以用save函数把YALMIP模型保存成文件再用export命令导出成LP或MPS格式放到求解器官方工具里进一步分析。这个办法排查约束错误非常管用能直接看到求解器视角下的模型长什么样比自己对着代码猜快得多。数值稳定性方面建议统一用标幺值而不是有名值。有名值下线路阻抗、电压、功率的数量级差太多求解器在迭代过程中容易出现数值问题。用标幺值后所有变量量纲统一求解稳定而且后面换成更大的系统也方便比较。这是我吃过亏之后才养成的习惯现在建模都会先做归算。最后再分享一个小经验。做这个课题最忌讳一上来就把模型加得很复杂什么三相不平衡、各种时序场景全塞进去最后根本跑不动。我的建议是先跑通一个最简单的版本——单典型日、光伏储能同点位、粒子群50代——哪怕是结果差强人意至少整条链路是通的。确认无误了再逐步增加细节从单日扩展为四季典型日从同点位扩展到独立选址从固定电价升级成分时电价每一步都验证一次结果的合理性。这种迭代方式看着慢实际上是最快的路子。做完了之后回头看整个框架很干净加约束、换数据、迁移到别的系统都不费劲。
返回列表