MAKEAPQ Construct linear constraints for generator capability curves. [APQH, UBPQH, APQL, UBPQL, DATA] = MAKEAPQ(BASEMVA, GEN) Constructs the parameters for the following linear constraints implementing trapezoidal generator capability curves, where Pg and Qg are the real and reactive generator injections. APQH * [Pg; Qg] <= UBPQH APQL * [Pg; Qg] <= UBPQL DATA constains additional information as shown below. Example: [Apqh, ubpqh, Apql, ubpql, data] = makeApq(baseMVA, gen); data.h [QC1MAX-QC2MAX, PC2-PC1] data.l [QC2MIN-QC1MIN, PC1-PC2] data.ipqh indices of gens with general PQ cap curves (upper) data.ipql indices of gens with general PQ cap curves (lower)
0001 function [Apqh, ubpqh, Apql, ubpql, data] = makeApq(baseMVA, gen) 0002 %MAKEAPQ Construct linear constraints for generator capability curves. 0003 % [APQH, UBPQH, APQL, UBPQL, DATA] = MAKEAPQ(BASEMVA, GEN) 0004 % 0005 % Constructs the parameters for the following linear constraints 0006 % implementing trapezoidal generator capability curves, where 0007 % Pg and Qg are the real and reactive generator injections. 0008 % 0009 % APQH * [Pg; Qg] <= UBPQH 0010 % APQL * [Pg; Qg] <= UBPQL 0011 % 0012 % DATA constains additional information as shown below. 0013 % 0014 % Example: 0015 % [Apqh, ubpqh, Apql, ubpql, data] = makeApq(baseMVA, gen); 0016 % 0017 % data.h [QC1MAX-QC2MAX, PC2-PC1] 0018 % data.l [QC2MIN-QC1MIN, PC1-PC2] 0019 % data.ipqh indices of gens with general PQ cap curves (upper) 0020 % data.ipql indices of gens with general PQ cap curves (lower) 0021 0022 % MATPOWER 0023 % $Id: makeApq.m,v 1.7 2010/04/26 19:45:25 ray Exp $ 0024 % by Ray Zimmerman, PSERC Cornell 0025 % and Carlos E. Murillo-Sanchez, PSERC Cornell & Universidad Autonoma de Manizales 0026 % Copyright (c) 1996-2010 by Power System Engineering Research Center (PSERC) 0027 % 0028 % This file is part of MATPOWER. 0029 % See http://www.pserc.cornell.edu/matpower/ for more info. 0030 % 0031 % MATPOWER is free software: you can redistribute it and/or modify 0032 % it under the terms of the GNU General Public License as published 0033 % by the Free Software Foundation, either version 3 of the License, 0034 % or (at your option) any later version. 0035 % 0036 % MATPOWER is distributed in the hope that it will be useful, 0037 % but WITHOUT ANY WARRANTY; without even the implied warranty of 0038 % MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 0039 % GNU General Public License for more details. 0040 % 0041 % You should have received a copy of the GNU General Public License 0042 % along with MATPOWER. If not, see <http://www.gnu.org/licenses/>. 0043 % 0044 % Additional permission under GNU GPL version 3 section 7 0045 % 0046 % If you modify MATPOWER, or any covered work, to interface with 0047 % other modules (such as MATLAB code and MEX-files) available in a 0048 % MATLAB(R) or comparable environment containing parts covered 0049 % under other licensing terms, the licensors of MATPOWER grant 0050 % you additional permission to convey the resulting work. 0051 0052 %% define named indices into data matrices 0053 [GEN_BUS, PG, QG, QMAX, QMIN, VG, MBASE, GEN_STATUS, PMAX, PMIN, ... 0054 MU_PMAX, MU_PMIN, MU_QMAX, MU_QMIN, PC1, PC2, QC1MIN, QC1MAX, ... 0055 QC2MIN, QC2MAX, RAMP_AGC, RAMP_10, RAMP_30, RAMP_Q, APF] = idx_gen; 0056 0057 %% data dimensions 0058 ng = size(gen, 1); %% number of dispatchable injections 0059 0060 %% which generators require additional linear constraints 0061 %% (in addition to simple box constraints) on (Pg,Qg) to correctly 0062 %% model their PQ capability curves 0063 ipqh = find( hasPQcap(gen, 'U') ); 0064 ipql = find( hasPQcap(gen, 'L') ); 0065 npqh = size(ipqh, 1); %% number of general PQ capability curves (upper) 0066 npql = size(ipql, 1); %% number of general PQ capability curves (lower) 0067 0068 %% make Apqh if there is a need to add general PQ capability curves; 0069 %% use normalized coefficient rows so multipliers have right scaling 0070 %% in $$/pu 0071 if npqh > 0 0072 data.h = [gen(ipqh,QC1MAX)-gen(ipqh,QC2MAX), gen(ipqh,PC2)-gen(ipqh,PC1)]; 0073 ubpqh = data.h(:, 1) .* gen(ipqh,PC1) + data.h(:, 2) .* gen(ipqh,QC1MAX); 0074 for i=1:npqh, 0075 tmp = norm(data.h(i,:)); 0076 data.h(i,:) = data.h(i, :) / tmp; 0077 ubpqh(i) = ubpqh(i) / tmp; 0078 end 0079 Apqh = sparse([1:npqh, 1:npqh]', [ipqh; ipqh+ng], ... 0080 data.h(:), npqh, 2*ng); 0081 ubpqh = ubpqh / baseMVA; 0082 else 0083 data.h = []; 0084 Apqh = sparse(0, 2*ng); 0085 ubpqh = []; 0086 end 0087 0088 %% similarly Apql 0089 if npql > 0 0090 data.l = [gen(ipql,QC2MIN)-gen(ipql,QC1MIN), gen(ipql,PC1)-gen(ipql,PC2)]; 0091 ubpql= data.l(:, 1) .* gen(ipql,PC1) + data.l(:, 2) .* gen(ipql,QC1MIN) ; 0092 for i=1:npql, 0093 tmp = norm(data.l(i, : )); 0094 data.l(i, :) = data.l(i, :) / tmp; 0095 ubpql(i) = ubpql(i) / tmp; 0096 end 0097 Apql = sparse([1:npql, 1:npql]', [ipql; ipql+ng], ... 0098 data.l(:), npql, 2*ng); 0099 ubpql = ubpql / baseMVA; 0100 else 0101 data.l = []; 0102 Apql = sparse(0, 2*ng); 0103 ubpql = []; 0104 end 0105 0106 data.ipql = ipql; 0107 data.ipqh = ipqh;