OPF_LEGACY_USER_COST_FCN Evaluates legacy user costs and derivatives. [F, DF, D2F] = OPF_LEGACY_USER_COST_FCN(X, CP) Evaluates the legacy user-defined costs and derivatives. Inputs: X : cell array with vectors of optimization variables CP : legacy user-defined cost parameter struct such as returned by @OPT_MODEL/GET_COST_PARAMS Outputs: F : sum of generator polynomial costs DF : (optional) gradient (column vector) of polynomial costs D2F : (optional) Hessian of polynomial costs Examples: f = opf_legacy_user_cost_fcn(x, cp); [f, df] = opf_legacy_user_cost_fcn(x, cp); [f, df, d2f] = opf_legacy_user_cost_fcn(x, cp);
0001 function [f, df, d2f] = opf_legacy_user_cost_fcn(x, cp) 0002 %OPF_LEGACY_USER_COST_FCN Evaluates legacy user costs and derivatives. 0003 % [F, DF, D2F] = OPF_LEGACY_USER_COST_FCN(X, CP) 0004 % 0005 % Evaluates the legacy user-defined costs and derivatives. 0006 % 0007 % Inputs: 0008 % X : cell array with vectors of optimization variables 0009 % CP : legacy user-defined cost parameter struct such as returned by 0010 % @OPT_MODEL/GET_COST_PARAMS 0011 % 0012 % Outputs: 0013 % F : sum of generator polynomial costs 0014 % DF : (optional) gradient (column vector) of polynomial costs 0015 % D2F : (optional) Hessian of polynomial costs 0016 % 0017 % Examples: 0018 % f = opf_legacy_user_cost_fcn(x, cp); 0019 % [f, df] = opf_legacy_user_cost_fcn(x, cp); 0020 % [f, df, d2f] = opf_legacy_user_cost_fcn(x, cp); 0021 0022 % MATPOWER 0023 % Copyright (c) 1996-2017, Power Systems Engineering Research Center (PSERC) 0024 % by Carlos E. Murillo-Sanchez, PSERC Cornell & Universidad Nacional de Colombia 0025 % and Ray Zimmerman, PSERC Cornell 0026 % 0027 % This file is part of MATPOWER. 0028 % Covered by the 3-clause BSD License (see LICENSE file for details). 0029 % See https://matpower.org for more info. 0030 0031 %%----- initialize ----- 0032 %% unpack data 0033 [N, Cw, H, dd, rh, kk, mm] = ... 0034 deal(cp.N, cp.Cw, cp.H, cp.dd, cp.rh, cp.kk, cp.mm); 0035 nx = length(x); 0036 0037 if isempty(N) 0038 f = 0; 0039 df = zeros(nx, 1); 0040 d2f = sparse(nx, nx); 0041 else 0042 nw = size(N, 1); 0043 r = N * x - rh; %% Nx - rhat 0044 iLT = find(r < -kk); %% below dead zone 0045 iEQ = find(r == 0 & kk == 0); %% dead zone doesn't exist 0046 iGT = find(r > kk); %% above dead zone 0047 iND = [iLT; iEQ; iGT]; %% rows that are Not in the Dead region 0048 iL = find(dd == 1); %% rows using linear function 0049 iQ = find(dd == 2); %% rows using quadratic function 0050 LL = sparse(iL, iL, 1, nw, nw); 0051 QQ = sparse(iQ, iQ, 1, nw, nw); 0052 kbar = sparse(iND, iND, [ ones(length(iLT), 1); 0053 zeros(length(iEQ), 1); 0054 -ones(length(iGT), 1)], nw, nw) * kk; 0055 rr = r + kbar; %% apply non-dead zone shift 0056 M = sparse(iND, iND, mm(iND), nw, nw); %% dead zone or scale 0057 diagrr = sparse(1:nw, 1:nw, rr, nw, nw); 0058 0059 %% linear rows multiplied by rr(i), quadratic rows by rr(i)^2 0060 w = M * (LL + QQ * diagrr) * rr; 0061 0062 f = (w' * H * w) / 2 + Cw' * w; 0063 0064 %%----- evaluate cost gradient ----- 0065 if nargout > 1 0066 HwC = H * w + Cw; 0067 AA = N' * M * (LL + 2 * QQ * diagrr); 0068 df = AA * HwC; 0069 0070 %% numerical check 0071 if 0 %% 1 to check, 0 to skip check 0072 ddff = zeros(size(df)); 0073 step = 1e-7; 0074 tol = 1e-3; 0075 for k = 1:length(x) 0076 xx = x; 0077 xx(k) = xx(k) + step; 0078 ddff(k) = (nlp_costfcn(om, xx) - f) / step; 0079 end 0080 if max(abs(ddff - df)) > tol 0081 idx = find(abs(ddff - df) == max(abs(ddff - df))); 0082 fprintf('\nMismatch in gradient\n'); 0083 fprintf('idx df(num) df diff\n'); 0084 fprintf('%4d%16g%16g%16g\n', [ 1:length(df); ddff'; df'; abs(ddff - df)' ]); 0085 fprintf('MAX\n'); 0086 fprintf('%4d%16g%16g%16g\n', [ idx'; ddff(idx)'; df(idx)'; abs(ddff(idx) - df(idx))' ]); 0087 fprintf('\n'); 0088 end 0089 end %% numeric check 0090 0091 %% ---- evaluate cost Hessian ----- 0092 if nargout > 2 0093 d2f = AA * H * AA' + 2 * N' * M * QQ * sparse(1:nw, 1:nw, HwC, nw, nw) * N; 0094 end 0095 end 0096 end