0001 function om = add_costs(om, name, idx, varargin)
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049
0050
0051
0052
0053
0054
0055
0056
0057
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068
0069
0070
0071
0072
0073
0074 if iscell(idx)
0075 if ~isempty(varargin)
0076
0077
0078
0079
0080 s1 = struct('type', {'.', '()'}, 'subs', {name, idx});
0081 s2 = s1;
0082 s2(2).type = '{}';
0083
0084
0085 if subsref(om.cost.idx.i1, s1) ~= 0
0086 str = '%d'; for m = 2:length(idx), str = [str ',%d']; end
0087 nname = sprintf(['%s(' str, ')'], name, idx{:});
0088 error('@opt_model/add_costs: cost set named ''%s'' already exists', nname);
0089 end
0090
0091 cp = varargin{1};
0092 args = varargin(2:end);
0093 else
0094
0095 if isfield(om.cost.idx.N, name)
0096 error('@opt_model/add_costs: cost set named ''%s'' already exists', name);
0097 end
0098
0099 cp = [];
0100 args = {};
0101 end
0102 else
0103
0104 if isfield(om.cost.idx.N, name)
0105 error('@opt_model/add_costs: cost set named ''%s'' already exists', name);
0106 end
0107
0108 cp = idx;
0109 args = varargin;
0110 idx = {};
0111 end
0112
0113 if isempty(cp)
0114
0115 if length(idx) == 1
0116 idx = {idx{:}, 1};
0117 end
0118
0119
0120 om.cost.idx.i1.(name) = zeros(idx{:});
0121 om.cost.idx.iN.(name) = zeros(idx{:});
0122 om.cost.idx.N.(name) = zeros(idx{:});
0123 om.cost.data.N.(name) = cell(idx{:});
0124 om.cost.data.Cw.(name) = cell(idx{:});
0125 om.cost.data.vs.(name) = cell(idx{:});
0126 else
0127 if isempty(args)
0128 varsets = {};
0129 else
0130 varsets = args{1};
0131 end
0132 if ~isempty(varsets) && iscell(varsets)
0133 empty_cells = cell(1, length(varsets));
0134 [empty_cells{:}] = deal({});
0135 varsets = struct('name', varsets, 'idx', empty_cells);
0136 end
0137 if isfield(cp, 'N')
0138 [nw, nx] = size(cp.N);
0139 else
0140 nw = length(cp.Cw);
0141 nx = nw;
0142 cp.N = speye(nw, nx);
0143 end
0144
0145
0146 if isempty(varsets)
0147 nv = om.var.N;
0148 else
0149 nv = 0;
0150 s = struct('type', {'.', '()'}, 'subs', {'', 1});
0151 for k = 1:length(varsets)
0152
0153
0154
0155 s(1).subs = varsets(k).name;
0156 s(2).subs = varsets(k).idx;
0157 nv = nv + subsref(om.var.idx.N, s);
0158 end
0159 end
0160 if nx ~= nv
0161 if nw == 0
0162 cp.N = sparse(nw, nx);
0163 else
0164 error('@opt_model/add_costs: number of columns in N (%d x %d) does not match\nnumber of variables (%d)\n', nw, nx, nv);
0165 end
0166 end
0167 if size(cp.Cw, 1) ~= nw
0168 error('@opt_model/add_costs: number of rows of Cw (%d x %d) and N (%d x %d) must match\n', size(cp.Cw), nw, nx);
0169 end
0170 if isfield(cp, 'H') && (size(cp.H, 1) ~= nw || size(cp.H, 2) ~= nw)
0171 error('@opt_model/add_costs: both dimensions of H (%d x %d) must match the number of rows in N (%d x %d)\n', size(cp.H), nw, nx);
0172 end
0173 if isfield(cp, 'dd') && size(cp.dd, 1) ~= nw
0174 error('@opt_model/add_costs: number of rows of dd (%d x %d) and N (%d x %d) must match\n', size(cp.dd), nw, nx);
0175 end
0176 if isfield(cp, 'rh') && size(cp.rh, 1) ~= nw
0177 error('@opt_model/add_costs: number of rows of rh (%d x %d) and N (%d x %d) must match\n', size(cp.rh), nw, nx);
0178 end
0179 if isfield(cp, 'kk') && size(cp.kk, 1) ~= nw
0180 error('@opt_model/add_costs: number of rows of kk (%d x %d) and N (%d x %d) must match\n', size(cp.kk), nw, nx);
0181 end
0182 if isfield(cp, 'mm') && size(cp.mm, 1) ~= nw
0183 error('@opt_model/add_costs: number of rows of mm (%d x %d) and N (%d x %d) must match\n', size(cp.mm), nw, nx);
0184 end
0185
0186 if isempty(idx)
0187
0188 om.cost.idx.i1.(name) = om.cost.N + 1;
0189 om.cost.idx.iN.(name) = om.cost.N + nw;
0190 om.cost.idx.N.(name) = nw;
0191 om.cost.data.N.(name) = cp.N;
0192 om.cost.data.Cw.(name) = cp.Cw;
0193 om.cost.data.vs.(name) = varsets;
0194 if isfield(cp, 'H')
0195 om.cost.data.H.(name) = cp.H;
0196 end
0197 if isfield(cp, 'dd')
0198 om.cost.data.dd.(name) = cp.dd;
0199 end
0200 if isfield(cp, 'rh')
0201 om.cost.data.rh.(name) = cp.rh;
0202 end
0203 if isfield(cp, 'kk')
0204 om.cost.data.kk.(name) = cp.kk;
0205 end
0206 if isfield(cp, 'mm')
0207 om.cost.data.mm.(name) = cp.mm;
0208 end
0209
0210
0211 om.cost.N = om.cost.idx.iN.(name);
0212 om.cost.NS = om.cost.NS + 1;
0213
0214
0215 om.cost.order(om.cost.NS).name = name;
0216 om.cost.order(om.cost.NS).idx = {};
0217 else
0218
0219 om.cost.idx.i1 = subsasgn(om.cost.idx.i1, s1, om.cost.N + 1);
0220 om.cost.idx.iN = subsasgn(om.cost.idx.iN, s1, om.cost.N + nw);
0221 om.cost.idx.N = subsasgn(om.cost.idx.N, s1, nw);
0222
0223 om.cost.data.N = subsasgn(om.cost.data.N, s2, cp.N);
0224 om.cost.data.Cw = subsasgn(om.cost.data.Cw, s2, cp.Cw);
0225 om.cost.data.vs = subsasgn(om.cost.data.vs, s2, varsets);
0226 if isfield(cp, 'H')
0227 om.cost.data.H = subsasgn(om.cost.data.H, s2, cp.H);
0228 end
0229 if isfield(cp, 'dd')
0230 om.cost.data.dd = subsasgn(om.cost.data.dd, s2, cp.dd);
0231 end
0232 if isfield(cp, 'rh')
0233 om.cost.data.rh = subsasgn(om.cost.data.rh, s2, cp.rh);
0234 end
0235 if isfield(cp, 'kk')
0236 om.cost.data.kk = subsasgn(om.cost.data.kk, s2, cp.kk);
0237 end
0238 if isfield(cp, 'mm')
0239 om.cost.data.mm = subsasgn(om.cost.data.mm, s2, cp.mm);
0240 end
0241
0242
0243 om.cost.N = subsref(om.cost.idx.iN, s1);
0244 om.cost.NS = om.cost.NS + 1;
0245
0246
0247 om.cost.order(om.cost.NS).name = name;
0248 om.cost.order(om.cost.NS).idx = idx;
0249 end
0250 end