Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Improvements in the aggregates support and Part21 importer as well
  • Loading branch information
tpaviot committed Feb 22, 2012
commit d56795946c7b39fecf8bdcb5c91c190874f1e0fe
8 changes: 7 additions & 1 deletion src/fedex_python/python/SCL/AggregationDataTypes.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,12 @@ def __init__( self , bound_1 , bound_2 , base_type , UNIQUE = False, OPTIONAL=F
list_size = bound_2 - bound_1 + 1
self._container = list_size*[None]

def bound_1(self):
return self._bound_1

def bound_2(self):
return self._bound_2

def __getitem__(self, index):
if index<self._bound_1:
raise IndexError("ARRAY index out of bound (lower bound is %i, passed %i)"%(self._bound_1,index))
Expand Down Expand Up @@ -122,7 +128,7 @@ def __setitem__(self, index, value):

class LIST(list, BaseAggregate):
"""A list data type has as its domain sequences of like elements. The optional lower and upper
bounds, which are integer-valued expressions, dfine the minimum and maximum number of
bounds, which are integer-valued expressions, define the minimum and maximum number of
elements that can be held in the collection defined by a list data type.
A list data type
definition may optionally specify that a list value cannot contain duplicate elements.
Expand Down
93 changes: 14 additions & 79 deletions src/fedex_python/python/SCL/Part21.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

import re
import Utils

INSTANCE_DEFINITION_RE = re.compile("#(\d+)[^\S\n]?=[^\S\n]?(.*?)\((.*)\)[^\S\n]?;[\\r]?$")

Expand Down Expand Up @@ -119,32 +120,6 @@ def get_schema_name(self):
def get_number_of_instances(self):
return len(self._instances_definition.keys())

def parse_attributes(self, attr_str):
"""
This method takes a string an returns a list of attributes (but without any mapping).
For instance:
input = "'',(#11,#15,#19,#23,#27),#31"
output = ['',(#11,#15,#19,#23,#27),'#31']
"""
aggr_scope_level = 0
attrs = []
current_attr = ''
previous_ch = ''
for ch in attr_str:
if ch == ',' and aggr_scope_level == 0:
attrs.append(current_attr)
current_attr = ''
else:
if ch == '(':
aggr_scope_level +=1
elif ch == ')':
aggr_scope_level -= 1
current_attr += ch
previous_ch = ch
# finally add the last attr when exiting loop
attrs.append(current_attr)
return attrs

def parse_file(self):
init_time = time.time()
print "Parsing file %s..."%self._filename,
Expand All @@ -155,8 +130,8 @@ def parse_file(self):
break
# there may be a multline definition. In this case, we read lines untill we found
# a ;
while (not line.endswith(";\r\n")): #its a multiline
line = line.replace("\r\n","") + fp.readline()
#while (not line.endswith(";\r\n")): #its a multiline
# line = line.replace("\r\n","") + fp.readline()
# parse line
match_instance_definition = INSTANCE_DEFINITION_RE.search(line) # id,name,attrs
if match_instance_definition:
Expand All @@ -167,7 +142,7 @@ def parse_file(self):
# fill number of ancestors dict
self._number_of_ancestors[number_of_ancestors].append(instance_int_id)
# parse attributes string
entity_attrs_list = self.parse_attributes(entity_attrs)
entity_attrs_list, str_len = Utils.process_nested_parent_str(entity_attrs)
# then finally append this instance to the disct instance
self._instances_definition[instance_int_id] = (entity_name,entity_attrs_list)
else: #does not match with entity instance definition, parse the header
Expand All @@ -185,21 +160,23 @@ class EntityInstancesFactory(object):
20: ('CARTESIAN_POINT', ["''", '(5.,125.,20.)'])
will result in:
p = ARRAY(1,3,REAL)
p.[1]=REAL(5)
p.[1] = REAL(5)
p.[2] = REAL(125)
p.[3] = REAL(20)
new_instance = cartesian_point(STRING(''),p)
'''
def __init__(self, schema_name, instance_definition):
# First try to import the schema module
pass

class Part21Population(object):
def __init__(self, part21_loader):
""" Take a part21_loader a tries to create entities
"""
self._part21_loader = part21_loader
self._aggregate_scope = []
self._aggr_scope = False
self.create_entity_instances()

def create_entity_instances(self):
""" Starts entity instances creation
Expand All @@ -210,63 +187,21 @@ def create_entity_instances(self):

def create_entity_instance(self, instance_id):
instance_definition = self._part21_loader._instances_definition[instance_id]
print "Instance definition to process",instance_definition
# first find class name
class_name = instance_definition[0].lower()
print "Class name:%s"%class_name
object_ = globals()[class_name]
# then attributes
#print object_.__doc__
instance_attributes = instance_definition[1]
#print instance_attributes
# find attributes
attributes = instance_attributes.split(",")
instance_attributes = []
#print attributes
for attr in attributes:
if attr[0]=="(":#new aggregate_scope
#print "new aggregate scope"
self._aggr_scope = True
at = self.map_express_to_python(attr[1:])
#self._aggregate_scope.append(at)
elif attr[-1]==")":
#print "end aggregate scope"
at = self.map_express_to_python(attr[:-1])
self._aggregate_scope.append(at)
self._aggr_scope = False
else:
at = self.map_express_to_python(attr)
if self._aggr_scope:
self._aggregate_scope.append(at)
if len(self._aggregate_scope)>0 and not self._aggr_scope:
instance_attributes.append(self._aggregate_scope)
self._aggregate_scope = []
elif len(self._aggregate_scope)>0 and self._aggr_scope:
pass
else:
instance_attributes.append(at)
print "instance_attributes:",instance_attributes
a = object_(*instance_attributes)


def map_express_to_python(self,attr):
""" Map EXPRESS to python"""
if attr in ["$","''"]: #optional argument
return None
elif attr.startswith('#'): #entity_id
return attr[1:]
else:
return map_string_to_num(attr)

if __name__ == "__main__":
import time
import sys
#sys.path.append("..")
#from config_control_design import *
#p21loader = Part21Loader("as1-oc-214.stp")
#file = Part21Loader("as1-tu-203.stp")
#file = Part21Loader("HAYON.stp")
p21loader = Part21Parser("as1.stp")
print p21loader._instances_definition
#print "Creating instances"
#p21population = Part21Population(p21loader)
#p21population.create_entity_instances()
#t2 = time.time()
#print "Creating instances took: %s s \n" % ((t2-t1))
from config_control_design import *
p21loader = Part21Parser("gasket1.p21")
print "Creating instances"
p21population = Part21Population(p21loader)
19 changes: 16 additions & 3 deletions src/fedex_python/python/SCL/TypeChecker.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,17 @@

from ConstructedDataTypes import ENUMERATION, SELECT

RAISE_EXCEPTION_IF_TYPE_DOES_NOT_MATCH = False

def cast_python_list_to_aggregate(lst, aggregate):
""" This function casts a python list to an aggregate type. For instance:
[1.,2.,3.]-> ARRAY(1,3,REAL)"""
aggregate_lower_bound = aggregate.bound_1()
aggregate_upper_bound = aggregate.bound_2()
for idx in range(aggregate_lower_bound,aggregate_upper_bound+1):
aggregate[idx] = lst[idx-aggregate_lower_bound]
return aggregate

def check_type(instance, expected_type):
""" This function checks wether an object is an instance of a given class
returns False or True
Expand All @@ -46,8 +57,10 @@ def check_type(instance, expected_type):
else:
type_match = isinstance(instance,expected_type)
if not type_match:
raise TypeError('Type of argument number_of_sides must be %s (you passed %s)'%(expected_type,type(instance)))
if RAISE_EXCEPTION_IF_TYPE_DOES_NOT_MATCH:
raise TypeError('Type of argument number_of_sides must be %s (you passed %s)'%(expected_type,type(instance)))
else:
print "WARNING: expected '%s' but passed a '%s', casting from python value to EXPRESS type"%(expected_type, type(instance))
return False
else:
return True


35 changes: 0 additions & 35 deletions src/fedex_python/python/SCL/as1.stp

This file was deleted.

52 changes: 36 additions & 16 deletions src/fedex_python/python/SCL/essa_par.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,36 +19,56 @@ def process_nested_parent_str(attr_str):
current_param += ch
return params

idx = 0
def process_nested_parent_str2(attr_str):
def process_nested_parent_str2(attr_str,idx=0):
'''
The first letter should be a parenthesis
input string: "(1,4,(5,6),7)"
output: ['1','4',['5','6'],'7']
'''
global idx
acc=0
print 'Entering function with string %s and index %i'%(attr_str,idx)
#print 'Entering function with string %s'%(attr_str)
params = []
current_param = ''
for i,ch in enumerate(attr_str):
idx += 1
acc +=1
k = 0
while (k<len(attr_str)):
#print 'k in this function:%i'%k
ch = attr_str[k]
k += 1
if ch==',':
#print "Add param:",current_param
params.append(current_param)
current_param = ''
elif ch=='(':
nv = attr_str[idx:]
print "params",params
print "Str passed to the function:%s (idx=%i)"%(nv,idx)
current_param = process_nested_parent_str2(nv)
nv = attr_str[k:]
#print "Up one level parenthesis:%s"%(nv)
current_param, progress = process_nested_parent_str2(nv)
#print "Adding the list returned from nested",current_param
params.append(current_param)
current_param = ''
k += progress+1
elif ch==')':
#print "Down one level parenthesis: %i caracters parsed"%k
params.append(current_param)
idx -= acc+1
return params
#print "Current params:",params#k -= acc-2
return params,k
else:
current_param += ch
#print "Ch:",ch
#print "k:",k

#raw_input("")
#idx += 1

params.append(current_param)
return params
return params,k
#print process_nested_parent_str2('1,2,3,4,5,6')
print process_nested_parent_str2("'A','B',('C','D'),'E'")
#idx=0
#print process_nested_parent_str2("'A','B','C'")
print process_nested_parent_str2("'A'")[0]
print process_nested_parent_str2("30.0,0.0,5.0")[0]
print process_nested_parent_str2("(Thomas)")[0]
print process_nested_parent_str2("Thomas, Paviot, ouais")[0]
print process_nested_parent_str2("1,2,(3,4,5),6,7,8")[0]
print process_nested_parent_str2("(#9149,#9166),#9142,.T.")[0]



10 changes: 9 additions & 1 deletion src/fedex_python/python/SCL_unittest.py
Original file line number Diff line number Diff line change
Expand Up @@ -243,6 +243,14 @@ class P:

def test_check_enum_type(self):
enum = ENUMERATION(["my","string"])


#
# Cast from list to aggregates
#
class CastTypeChecker(unittest.TestCase):
def test_cast_list_to_array(self):
a = [1.,2.,3.]
b = cast_python_list_to_aggregate(a,ARRAY(1,3,REAL))

unittest.main()

Loading