source: git/modules/openmath/objects.py @ 913156

spielwiese
Last change on this file since 913156 was 913156, checked in by Michael Brickenstein <bricken@…>, 18 years ago
*bricken: initial version git-svn-id: file:///usr/local/Singular/svn/trunk@8995 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 8.9 KB
Line 
1"""Implementation of openmath basic objects"""
2from omexceptions import UnsupportedOperationError
3from  omexceptions import OutOfScopeError, EvaluationFailedError
4from exceptions import NotImplementedError
5from copy import copy
6from xml.sax.xmlreader import AttributesImpl as attr
7from itertools import izip
8import base64
9
10raiseException=True
11#TODO: OMOBJ, OME, OMATTR
12#from cd import *
13try:
14    import psyco
15    def optimize(f):
16        psyco.bind(f)
17except:
18    def optimize(f):
19        pass
20
21class OMCD(object):
22    def __init__(self, name, base="http://www.openmath.org/cd"):
23        self.name = name
24        self.base = base
25    def  __eq__(self, other):
26        try:
27            return (self.name == other.name) and (self.base == other.base)
28        except:
29            return False
30    def __hash__(self):
31        return hash((self.name,self.base))
32
33
34       
35class OMCDImplementation(object):
36    def __init__(self, cd):
37        object.__setattr__(self,"cd",cd)
38    def support(self,symbol):
39        setattr(self,symbol,OMS(symbol, self.cd))
40    def __setattr__(self, name,value):
41        "FIXME: implements this later safer against name conflicts"
42        if callable(value) and (not isinstance(value, ImplementedSymbol)):
43            object.__setattr__(self, name, ImplementedSymbol(OMS(name,self.cd), value))
44        else:
45            object.__setattr__(self,name,value)
46
47class OMS(object):
48    def __init__(self,name,cd = None):
49        #super(OMSymbol,self).__init__()
50        self.cd = cd
51        self.name = name
52    def __eq__(self, other):
53        try:
54            return bool(other.name == self.name and self.cd == other.cd)
55        except:
56            return False
57    def __str__(self):
58        return "OMS(" + self.name + ", " + self.cd.name + ")"
59    def __repr__(self):
60        return str(self)
61    def __hash__(self):#
62        return hash((self.name,self.cd.__hash__()))
63    def evaluate(self,context):
64        return context.evaluateSymbol(self)
65    XMLtag="OMS"
66    def getXMLAttributes(self):
67        #return [XMLAttribute("name", self.name),\
68        #         XMLAttribute("cdbase", self.cd.base),\
69        #         XMLAttribute("cd", self.cd.name)]
70        return {"name":self.name, "cdbase":self.cd.base, "cd": self.cd.name}
71    def setXMLAttributes(self):
72        raise UnsupportedOperationError
73
74
75class ImplementedSymbol(OMS):
76    def __init__(self,symbol, func):
77        super(ImplementedSymbol,self).__init__(symbol.name, symbol.cd)
78        self.implementation = func
79    def __str__(self):
80        return "ImplementedOMS("+self.name+", " + self.cd.name +")"
81    def __call__(self, context, *args):
82        try:
83            erg=self.implementation(*args)
84        except KeyError:
85             raise EvaluationFailedError
86        return context.package(erg)
87
88cdFns1 = OMCD("fns1")
89lambdasym = OMS("lambda", cdFns1)
90
91def islambda(sym):
92    "return True, iff sym is the lambda binder"
93    return lambdasym == sym
94   
95class OMBIND(object):
96    """hopefully fixed possible problems: reevaluation writes new scope,
97       if it isn't
98       meant so, references do not work correctly because of scopes
99       solve this by first evaluation to bounded OMBinding"""
100    def __init__(self, binder, variables, block):
101        #super(OMBinding, self).__init__()
102        self.block = block
103        self.binder = binder
104        self.variables = variables
105        self.bounded = False
106    def evaluate(self, context):
107        "evaluate the OMbinding in context"
108        assert islambda(self.binder)
109        if not self.bounded:
110            mycopy = copy(self)
111            mycopy.scope = context.scopeFromCurrentScope()
112            mycopy.bounded = True
113            return mycopy
114        else:
115            return self
116    def bind(self, args):
117        "bind arguments to values"
118        #print args, self.variables
119        assert len(args) == len(self.variables)
120        varBindings = dict(izip([i.name for i in self.variables], args))
121        self.scope.push(varBindings)
122    def unbind(self):
123        "unbind the arguments"
124        self.scope.pop()
125
126    def calcErg(self, context):
127        "do the actual computation"
128        return context.evaluateInScope(self.block, self.scope)
129    def __call__(self, context, *args):
130        assert self.bounded
131        self.bind(args)
132        erg = self.calcErg(context)
133        self.unbind()
134        #print "__call__ erg is", erg
135        return erg   
136       
137    XMLtag = "OMBIND"
138    def getChildren(self):
139        "get children for (XML) representation"
140        return [self.binder]+self.variables+[self.block]
141             
142       
143
144class OMOBJ(object):
145    def __init__(self, children):
146        #super(OMObject, self).__init__()
147        self.children = children
148    def getChildren(self):
149        return self.__children
150    def setChildren(self ,children):
151        self.__children=children
152    XMLtag = "OMOBJ"
153    def evaluate(self, context):
154        return OMObject([context.evaluate(c) for c in self.children])
155class OMV(object):
156    def __init__(self,name):
157        #super(OMVar, self).__init__()
158        self.name = name
159    def evaluate(self, context):
160        try:
161            return context[self.name]
162        except OutOfScopeError:
163            return self
164    def __str__(self):
165        return "OMV(" + self.name +")"
166    def __repr__(self):
167        return str(self)
168    XMLtag="OMV"
169class OMA(object):
170    def __init__(self, func, args):
171        #super(OMApply, self).__init__()
172        self.func = func
173        self.args = args
174       
175    def evaluate(self, context):
176        efunc = context.evaluate(self.func)
177        eargs = [context.evaluate(a) for a in self.args]
178        if callable(efunc):
179            if raiseException:
180                return context.apply(efunc,eargs)
181            else:
182                try:
183                    return context.apply(efunc, eargs)
184                except EvaluationFailedError, NotImplementedError:
185                    return OMA(efunc, eargs)
186                #return self
187        else:
188            #print efunc
189            return OMA(efunc, eargs)
190    def __str__ (self):
191        return "OMA"+"("+str(self.func)+str(self.args)
192    def __repr__ (self):
193        return "OMA"+"("+str(self.func)+str(self.args)
194    XMLtag="OMA"
195       
196
197# class OMB(SimpleValue):
198#     def __init__(self, value):
199#         #super(OMByteArray,self).__init__(value)
200#         self.value=value
201#     def __str__(self):
202#         return "OMByteArray(" + repr(self.value) + ")"
203#     def parse(self, value):
204#         return value
205#     XMLtag = "OMB"
206#     def getBody(self):
207#         return base64.encodestring(self.value)
208class OMRef(object):
209    def __init__(self, ref):
210        self.ref=ref
211    def evaluate(self, context):
212        return context.evaluate(self.ref)
213    def XMLEncode(self, context):
214        "FIXME: maybe it should also be able to encode as reference"
215        return context.XMLEncodeObject(self.ref)
216
217class OMATTR(object):
218    def __init__(self, *args):
219        #super(OMAttribution,self).__init__()
220        self.attr = list(args[:-1])
221        self.value = args[-1]
222    def getChildren(self):
223        #print type(self.attr)
224        #print type(self.value)
225        return self.attr+[self.value]
226    def evaluate(self, context):
227        value = copy(self.value)
228        value.attributes = copy(value.attributes)
229        for attribute in self.attr:
230            attribute_evaluated=context.evaluate(attribute)
231            value.attributes[attribute_evaluated.key] = attribute_evaluated.value
232        return value
233    XMLtag = "OMATTR"
234if __name__ == '__main__':
235    print OMV("x")
236    print OMA(OMV("x"),[OMV("y"),1])
237 
238
239    #from binding import OMBinding, lambdasym
240
241   
242    context["x"] = 1
243
244    x = OMV("x")
245
246    y = OMV("y")
247
248    print context.evaluate(x)
249    print context.evaluateVariable(x)
250    print context.evaluate(y)
251    import cd.arith1 as arith1
252    context.addCDImplementation(arith1.implementation)
253    print OMA(arith1.implementation.plus, [1,2])
254    print context.evaluate(OMA(arith1.implementation.plus, [1,2]))
255    application = OMA(OMS("plus", arith1.content), [1,2])
256   
257    print context.evaluate(application)
258    firstArg=OMBinding(lambdasym,[OMVar("x"), OMVar("y")], OMVar("x"))
259    #print context.evaluate(firstArg)
260    application = OMApply(firstArg, [x,y])
261    print context.evaluate(application)
262    application = OMApply(firstArg, [y,x])
263    print context.evaluate(application)
264   
265    #print type(context.lookupImplementation(arith1.plussym))
266    #application=OMApply(arith1.plussym,[x])
267    #application=OMApply(arith1.plussym,[x,x])
268    application = OMApply(OMS("plus", arith1.content), [x, x])
269   
270    print context.evaluate(application)
271    application = OMApply(OMS("plus", arith1.content), [x, x, x])
272   
273    print context.evaluate(application)
274    i =  OMint(22482489)
275    print i.body
276    print i.XMLEncode(context)
277    print context.XMLEncodeObject(OMS("plus", arith1.content))
278    #i.body="dshj"
279   
280#optimize(OMObjectBase.__init__)
281#optimize(OMObjectBase.XMLPreEncode)
282#optimize(SimpleValue.__init__)
283#optimize(OMint.__init__)
284#optimize(OMApply.__init__)
Note: See TracBrowser for help on using the repository browser.