source: coopr.pysp/trunk/coopr/pysp/phutils.py @ 2320

Last change on this file since 2320 was 2320, checked in by jwatson, 11 years ago

A *very* early commit of a Pyro-based PH solver server - some of it functions, much of it doesn't. Committing to checkpoint.

File size: 7.2 KB
Line 
1#  _________________________________________________________________________
2#
3#  Coopr: A COmmon Optimization Python Repository
4#  Copyright (c) 2008 Sandia Corporation.
5#  This software is distributed under the BSD License.
6#  Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
7#  the U.S. Government retains certain rights in this software.
8#  For more information, see the Coopr README.txt file.
9#  _________________________________________________________________________
10
11import string
12import traceback
13import os
14
15#
16# a simple utility function to pretty-print an index tuple into a [x,y] form string.
17#
18
19def indexToString(index):
20
21   # if the input type is a string or an int, then this isn't a tuple!
22   if isinstance(index, str) or isinstance(index, int):
23      return "["+str(index)+"]"
24
25   result = "["
26   for i in range(0,len(index)):
27      result += str(index[i])
28      if i != len(index) - 1:
29         result += ","
30   result += "]"
31   return result
32
33#
34# a simple utility to determine if a variable name contains an index specification.
35# in other words, is the reference to a complete variable (e.g., "foo") - which may
36# or may not be indexed - or a specific index or set of indices (e.g., "foo[1]" or
37# or "foo[1,*]".
38#
39
40def isVariableNameIndexed(variable_name):
41
42   left_bracket_count = variable_name.count('[')
43   right_bracket_count = variable_name.count(']')
44
45   if (left_bracket_count == 1) and (right_bracket_count == 1):
46      return True
47   elif (left_bracket_count == 1) or (right_bracket_count == 1):
48      raise ValueError, "Illegally formed variable name="+variable_name+"; if indexed, variable names must contain matching left and right brackets"
49   else:
50      return False
51
52#
53# takes a string indexed of the form "('foo', 'bar')" and returns a proper tuple ('foo','bar')
54#
55
56def tupleizeIndexString(index_string):
57
58   index_string=index_string.lstrip('(')
59   index_string=index_string.rstrip(')')
60   pieces = index_string.split(',')
61   return_index = ()
62   for piece in pieces:
63      piece = string.strip(piece)
64      piece = piece.lstrip('\'')
65      piece = piece.rstrip('\'')
66      transformed_component = None
67      try:
68         transformed_component = int(piece)
69      except ValueError:
70         transformed_component = piece
71      return_index = return_index + (transformed_component,)
72
73   # IMPT: if the tuple is a singleton, return the element itself.
74   if len(return_index) == 1:
75      return return_index[0]
76   else:
77      return return_index     
78
79#
80# related to above, extract the index from the variable name.
81# will throw an exception if the variable name isn't indexed.
82# the returned variable name is a string, while the returned
83# index is a tuple. integer values are converted to integers
84# if the conversion works!
85#
86
87def extractVariableNameAndIndex(variable_name):
88
89   if isVariableNameIndexed(variable_name) is False:
90      raise ValueError, "Non-indexed variable name passed to function extractVariableNameAndIndex()"
91
92   pieces = variable_name.split('[')
93   name = string.strip(pieces[0])
94   full_index = pieces[1].rstrip(']')
95
96   # even nested tuples in pyomo are "flattened" into
97   # one-dimensional tuples. to accomplish flattening
98   # replace all parens in the string with commas and
99   # proceed with the split.
100   full_index=string.translate(full_index, None, "()")
101   indices = full_index.split(',')
102
103   return_index = ()
104   
105   for index in indices:
106
107      # unlikely, but strip white-space from the string.
108      index=string.strip(index)
109
110      # if the tuple contains nested tuples, then the nested
111      # tuples have single quotes - "'" characters - around
112      # strings. remove these, as otherwise you have an
113      # illegal index.
114      index=string.translate(index, None, "\'")
115
116      # if the index is an integer, make it one!
117      transformed_index = None
118      try:
119         transformed_index = int(index)
120      except ValueError:
121         transformed_index = index                 
122      return_index = return_index + (transformed_index,)
123
124   # IMPT: if the tuple is a singleton, return the element itself.
125   if len(return_index) == 1:
126      return name, return_index[0]
127   else:
128      return name, return_index
129
130#
131# determine if the input index is an instance of the template,
132# which may or may not contain wildcards.
133#
134
135def indexMatchesTemplate(index, index_template):
136
137   # if the input index is not a tuple, make it one.
138   # ditto with the index template. one-dimensional
139   # indices in pyomo are not tuples, but anything
140   # else is.
141
142   if type(index) != tuple:
143      index = (index,)
144   if type(index_template) != tuple:
145      index_template = (index_template,)
146
147   if len(index) != len(index_template):
148      return False
149
150   for i in range(0,len(index_template)):
151      if index_template[i] == '*':
152         # anything matches
153         pass
154      else:
155         if index_template[i] != index[i]:
156            return False
157
158   return True
159
160#
161# given a variable (the real object, not the name) and an index,
162# "shotgun" the index and see which variable indices match the
163# input index. the cardinality could be > 1 if slices are
164# specified, e.g., [*,1].
165#
166
167def extractVariableIndices(variable, index_template):
168
169   result = []
170
171   for index in variable._index:
172
173      if indexMatchesTemplate(index, index_template) is True:
174         result.append(index)
175
176   return result
177
178#
179# construct a scenario instance!
180#
181def construct_scenario_instance(scenario_tree_instance,
182                                scenario_data_directory_name,
183                                scenario_name,
184                                reference_model,
185                                verbose):
186
187   if verbose is True:
188      if scenario_tree_instance._scenario_based_data == 1:
189         print "Scenario-based instance initialization enabled"
190      else:
191         print "Node-based instance initialization enabled"
192   
193   scenario = scenario_tree_instance.get_scenario(scenario_name)
194   scenario_instance = None
195
196   if verbose is True:
197      print "Creating instance for scenario=" + scenario._name
198
199   try:
200      if scenario_tree_instance._scenario_based_data == 1:
201         scenario_data_filename = scenario_data_directory_name + os.sep + scenario._name + ".dat"
202         if verbose is True:
203            print "Data for scenario=" + scenario._name + " loads from file=" + scenario_data_filename
204         scenario_instance = reference_model.create(scenario_data_filename)
205      else:
206         scenario_instance = reference_model.clone()
207         scenario_data = ModelData()
208         current_node = scenario._leaf_node
209         while current_node is not None:
210            node_data_filename = scenario_data_directory_name + os.sep + current_node._name + ".dat"
211            if verbose is True:
212               print "Node data for scenario=" + scenario._name + " partially loading from file=" + node_data_filename
213            scenario_data.add(node_data_filename)
214            current_node = current_node._parent
215         scenario_data.read(model=scenario_instance)
216         scenario_instance._load_model_data(scenario_data)
217         scenario_instance.presolve()
218   except:
219      print "Encountered exception in model instance creation - traceback:"
220      traceback.print_exc()
221      raise RuntimeError, "Failed to create model instance for scenario=" + scenario._name
222
223   return scenario_instance
Note: See TracBrowser for help on using the repository browser.