Package pypower :: Module int2ext
[hide private]
[frames] | no frames]

Source Code for Module pypower.int2ext

  1  # Copyright (C) 1996-2011 Power System Engineering Research Center (PSERC) 
  2  # Copyright (C) 2011 Richard Lincoln 
  3  # 
  4  # PYPOWER is free software: you can redistribute it and/or modify 
  5  # it under the terms of the GNU General Public License as published 
  6  # by the Free Software Foundation, either version 3 of the License, 
  7  # or (at your option) any later version. 
  8  # 
  9  # PYPOWER is distributed in the hope that it will be useful, 
 10  # but WITHOUT ANY WARRANTY; without even the implied warranty of 
 11  # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 
 12  # GNU General Public License for more details. 
 13  # 
 14  # You should have received a copy of the GNU General Public License 
 15  # along with PYPOWER. If not, see <http://www.gnu.org/licenses/>. 
 16   
 17  """Converts internal to external bus numbering. 
 18  """ 
 19   
 20  import sys 
 21   
 22  from copy import deepcopy 
 23   
 24  from numpy import arange, concatenate 
 25   
 26  from idx_bus import BUS_I 
 27  from idx_gen import GEN_BUS 
 28  from idx_brch import F_BUS, T_BUS 
 29  from idx_area import PRICE_REF_BUS 
 30   
 31  from pypower.get_reorder import get_reorder 
 32  from pypower.set_reorder import set_reorder 
 33  from pypower.run_userfcn import run_userfcn 
 34   
 35   
36 -def int2ext(ppc, val_or_field=None, oldval=None, ordering=None, dim=0):
37 """Converts internal to external bus numbering. 38 39 This function performs several different tasks, depending on the 40 arguments passed. 41 42 1. C{ppc = int2ext(ppc)} 43 44 If the input is a single PYPOWER case dict, then it restores all 45 buses, generators and branches that were removed because of being 46 isolated or off-line, and reverts to the original generator ordering 47 and original bus numbering. This requires that the 'order' key 48 created by L{ext2int} be in place. 49 50 Example:: 51 ppc = int2ext(ppc) 52 53 2. C{val = int2ext(ppc, val, oldval, ordering)} 54 55 C{val = int2ext(ppc, val, oldval, ordering, dim)} 56 57 C{ppc = int2ext(ppc, field, ordering)} 58 59 C{ppc = int2ext(ppc, field, ordering, dim)} 60 61 For a case dict using internal indexing, this function can be 62 used to convert other data structures as well by passing in 2 to 4 63 extra parameters in addition to the case dict. If the values passed 64 in the 2nd argument (C{val}) is a column vector, it will be converted 65 according to the ordering specified by the 4th argument (C{ordering}, 66 described below). If C{val} is an n-dimensional matrix, then the 67 optional 5th argument (C{dim}, default = 0) can be used to specify 68 which dimension to reorder. The 3rd argument (C{oldval}) is used to 69 initialize the return value before converting C{val} to external 70 indexing. In particular, any data corresponding to off-line gens 71 or branches or isolated buses or any connected gens or branches 72 will be taken from C{oldval}, with C{val} supplying the rest of the 73 returned data. 74 75 If the 2nd argument is a string or list of strings, it 76 specifies a field in the case dict whose value should be 77 converted as described above. In this case, the corresponding 78 C{oldval} is taken from where it was stored by L{ext2int} in 79 ppc["order"]["ext"] and the updated case dict is returned. 80 If C{field} is a list of strings, they specify nested fields. 81 82 The C{ordering} argument is used to indicate whether the data 83 corresponds to bus-, gen- or branch-ordered data. It can be one 84 of the following three strings: 'bus', 'gen' or 'branch'. For 85 data structures with multiple blocks of data, ordered by bus, 86 gen or branch, they can be converted with a single call by 87 specifying C{ordering} as a list of strings. 88 89 Any extra elements, rows, columns, etc. beyond those indicated 90 in C{ordering}, are not disturbed. 91 92 @see: L{ext2int} 93 94 @author: Ray Zimmerman (PSERC Cornell) 95 @author: Richard Lincoln 96 """ 97 ppc = deepcopy(ppc) 98 if val_or_field is None: # nargin == 1 99 if 'order' not in ppc: 100 sys.stderr.write('int2ext: ppc does not have the "order" field ' 101 'require for conversion back to external numbering.\n') 102 o = ppc["order"] 103 104 if o["state"] == 'i': 105 ## execute userfcn callbacks for 'int2ext' stage 106 if 'userfcn' in ppc: 107 ppc = run_userfcn(ppc["userfcn"], 'int2ext', ppc) 108 109 ## save data matrices with internal ordering & restore originals 110 o["int"] = {} 111 o["int"]["bus"] = ppc["bus"].copy() 112 o["int"]["branch"] = ppc["branch"].copy() 113 o["int"]["gen"] = ppc["gen"].copy() 114 ppc["bus"] = o["ext"]["bus"].copy() 115 ppc["branch"] = o["ext"]["branch"].copy() 116 ppc["gen"] = o["ext"]["gen"].copy() 117 if 'gencost' in ppc: 118 o["int"]["gencost"] = ppc["gencost"].copy() 119 ppc["gencost"] = o["ext"]["gencost"].copy() 120 if 'areas' in ppc: 121 o["int"]["areas"] = ppc["areas"].copy() 122 ppc["areas"] = o["ext"]["areas"].copy() 123 if 'A' in ppc: 124 o["int"]["A"] = ppc["A"].copy() 125 ppc["A"] = o["ext"]["A"].copy() 126 if 'N' in ppc: 127 o["int"]["N"] = ppc["N"].copy() 128 ppc["N"] = o["ext"]["N"].copy() 129 130 ## update data (in bus, branch and gen only) 131 ppc["bus"][o["bus"]["status"]["on"], :] = \ 132 o["int"]["bus"] 133 ppc["branch"][o["branch"]["status"]["on"], :] = \ 134 o["int"]["branch"] 135 ppc["gen"][o["gen"]["status"]["on"], :] = \ 136 o["int"]["gen"][o["gen"]["i2e"], :] 137 if 'areas' in ppc: 138 ppc["areas"][o["areas"]["status"]["on"], :] = \ 139 o["int"]["areas"] 140 141 ## revert to original bus numbers 142 ppc["bus"][o["bus"]["status"]["on"], BUS_I] = \ 143 o["bus"]["i2e"] \ 144 [ ppc["bus"][o["bus"]["status"]["on"], BUS_I].astype(int) ] 145 ppc["branch"][o["branch"]["status"]["on"], F_BUS] = \ 146 o["bus"]["i2e"][ ppc["branch"] \ 147 [o["branch"]["status"]["on"], F_BUS].astype(int) ] 148 ppc["branch"][o["branch"]["status"]["on"], T_BUS] = \ 149 o["bus"]["i2e"][ ppc["branch"] \ 150 [o["branch"]["status"]["on"], T_BUS].astype(int) ] 151 ppc["gen"][o["gen"]["status"]["on"], GEN_BUS] = \ 152 o["bus"]["i2e"][ ppc["gen"] \ 153 [o["gen"]["status"]["on"], GEN_BUS].astype(int) ] 154 if 'areas' in ppc: 155 ppc["areas"][o["areas"]["status"]["on"], PRICE_REF_BUS] = \ 156 o["bus"]["i2e"][ ppc["areas"] \ 157 [o["areas"]["status"]["on"], PRICE_REF_BUS].astype(int) ] 158 159 if 'ext' in o: del o['ext'] 160 o["state"] = 'e' 161 ppc["order"] = o 162 else: 163 sys.stderr.write('int2ext: ppc claims it is already using ' 164 'external numbering.\n') 165 else: ## convert extra data 166 if isinstance(val_or_field, str) or isinstance(val_or_field, list): 167 ## field (key) 168 field = val_or_field 169 if 'int' not in ppc['order']: 170 ppc['order']['int'] = {} 171 172 if isinstance(field, str): 173 key = '["%s"]' % field 174 else: # nested dicts 175 key = '["%s"]' % '"]["'.join(field) 176 177 v_int = ppc["order"]["int"] 178 for fld in field: 179 if fld not in v_int: 180 v_int[fld] = {} 181 v_int = v_int[fld] 182 183 exec 'ppc["order"]["int"]%s = ppc%s.copy()' % (key, key) 184 exec 'ppc%s = int2ext(ppc, ppc%s, ppc["order"]["ext"]%s, ordering, dim)' % (key, key, key) 185 186 else: 187 ## value 188 val = val_or_field.copy() 189 o = ppc["order"] 190 if isinstance(ordering, str): ## single set 191 if ordering == 'gen': 192 v = get_reorder(val, o[ordering]["i2e"], dim) 193 else: 194 v = val 195 val = set_reorder(oldval, v, o[ordering]["status"]["on"], dim) 196 else: ## multiple sets 197 be = 0 ## base, external indexing 198 bi = 0 ## base, internal indexing 199 new_v = [] 200 for ord in ordering: 201 ne = o["ext"][ord].shape[0] 202 ni = ppc[ord].shape[0] 203 v = get_reorder(val, bi + arange(ni), dim) 204 oldv = get_reorder(oldval, be + arange(ne), dim) 205 new_v.append( int2ext(ppc, v, oldv, ord, dim) ) 206 be = be + ne 207 bi = bi + ni 208 ni = val.shape[dim] 209 if ni > bi: ## the rest 210 v = get_reorder(val, arange(bi, ni), dim) 211 new_v.append(v) 212 val = concatenate(new_v, dim) 213 return val 214 215 return ppc
216 217
218 -def int2ext1(i2e, bus, gen, branch, areas):
219 """Converts from the consecutive internal bus numbers back to the originals 220 using the mapping provided by the I2E vector returned from C{ext2int}. 221 222 @see: L{ext2int} 223 @see: U{http://www.pserc.cornell.edu/matpower/} 224 """ 225 bus[:, BUS_I] = i2e[ bus[:, BUS_I].astype(int) ] 226 gen[:, GEN_BUS] = i2e[ gen[:, GEN_BUS].astype(int) ] 227 branch[:, F_BUS] = i2e[ branch[:, F_BUS].astype(int) ] 228 branch[:, T_BUS] = i2e[ branch[:, T_BUS].astype(int) ] 229 230 if areas != None and len(areas) > 0: 231 areas[:, PRICE_REF_BUS] = i2e[ areas[:, PRICE_REF_BUS].astype(int) ] 232 return bus, gen, branch, areas 233 234 return bus, gen, branch
235