[pypy-svn] rev 671 - in pypy/trunk/src/pypy: . interpreter interpreter/test module/test objspace/std objspace/std/test
arigo at codespeak.net
arigo at codespeak.net
Thu May 29 15:31:37 CEST 2003
Author: arigo
Date: Thu May 29 15:31:36 2003
New Revision: 671
Added:
pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py (contents, props changed)
pypy/trunk/src/pypy/objspace/std/typeobject.py (contents, props changed)
pypy/trunk/src/pypy/objspace/std/userobject.py
- copied, changed from rev 620, pypy/trunk/src/pypy/objspace/std/usertype.py
Removed:
pypy/trunk/src/pypy/objspace/std/usertype.py
Modified:
pypy/trunk/src/pypy/interpreter/baseobjspace.py
pypy/trunk/src/pypy/interpreter/test/s1.py (props changed)
pypy/trunk/src/pypy/interpreter/testsupport.py (props changed)
pypy/trunk/src/pypy/module/test/test_apply.py (props changed)
pypy/trunk/src/pypy/objspace/std/boolobject.py
pypy/trunk/src/pypy/objspace/std/cpythonobject.py
pypy/trunk/src/pypy/objspace/std/default.py (contents, props changed)
pypy/trunk/src/pypy/objspace/std/floatobject.py
pypy/trunk/src/pypy/objspace/std/intobject.py
pypy/trunk/src/pypy/objspace/std/multimethod.py
pypy/trunk/src/pypy/objspace/std/noneobject.py
pypy/trunk/src/pypy/objspace/std/objspace.py
pypy/trunk/src/pypy/objspace/std/rarray.py (props changed)
pypy/trunk/src/pypy/objspace/std/test/test_multimethod.py
pypy/trunk/src/pypy/objspace/std/test/test_stdobjspace.py (props changed)
pypy/trunk/src/pypy/objspace/std/test/test_stringobject.py (props changed)
pypy/trunk/src/pypy/testwice.py (props changed)
Log:
multimethods and basic type system coexist now
Modified: pypy/trunk/src/pypy/interpreter/baseobjspace.py
==============================================================================
--- pypy/trunk/src/pypy/interpreter/baseobjspace.py (original)
+++ pypy/trunk/src/pypy/interpreter/baseobjspace.py Thu May 29 15:31:36 2003
@@ -163,65 +163,65 @@
## as 'space.op.xxx()' instead of directly 'space.xxx()'.
ObjSpace.MethodTable = [
-# method name # symbol # number of arguments
- ('id', 'id', 1),
- ('type', 'type', 1),
- ('issubtype', 'issubtype', 2), # not for old-style classes
- ('repr', 'repr', 1),
- ('str', 'str', 1),
- ('len', 'len', 1),
- ('hash', 'hash', 1),
- ('getattr', 'getattr', 2),
- ('setattr', 'setattr', 3),
- ('delattr', 'delattr', 2),
- ('getitem', 'getitem', 2),
- ('setitem', 'setitem', 3),
- ('delitem', 'delitem', 2),
- ('pos', 'pos', 1),
- ('neg', 'neg', 1),
- ('not_', 'not', 1),
- ('abs' , 'abs', 1),
- ('hex', 'hex', 1),
- ('oct', 'oct', 1),
- ('ord', 'ord', 1),
- ('invert', '~', 1),
- ('add', '+', 2),
- ('sub', '-', 2),
- ('mul', '*', 2),
- ('truediv', '/', 2),
- ('floordiv', '//', 2),
- ('div', 'div', 2),
- ('mod', '%', 2),
- ('divmod', 'divmod', 2),
- ('pow', '**', 3),
- ('lshift', '<<', 2),
- ('rshift', '>>', 2),
- ('and_', '&', 2),
- ('or_', '|', 2),
- ('xor', '^', 2),
- ('inplace_add', '+=', 2),
- ('inplace_sub', '-=', 2),
- ('inplace_mul', '*=', 2),
- ('inplace_truediv', '/=', 2),
- ('inplace_floordiv','//=', 2),
- ('inplace_div', 'div=', 2),
- ('inplace_mod', '%=', 2),
- ('inplace_pow', '**=', 2),
- ('inplace_lshift', '<<=', 2),
- ('inplace_rshift', '>>=', 2),
- ('inplace_and', '&=', 2),
- ('inplace_or', '|=', 2),
- ('inplace_xor', '^=', 2),
- ('lt', '<', 2),
- ('le', '<=', 2),
- ('eq', '==', 2),
- ('ne', '!=', 2),
- ('gt', '>', 2),
- ('ge', '>=', 2),
- ('contains', 'contains', 2),
- ('iter', 'iter', 1),
- ('next', 'next', 1), # iterator interface
- ('call', 'call', 3),
+# method name # symbol # number of arguments # special method name(s)
+ ('id', 'id', 1, []),
+ ('type', 'type', 1, []),
+ ('issubtype', 'issubtype', 2, []), # not for old-style classes
+ ('repr', 'repr', 1, ['__repr__']),
+ ('str', 'str', 1, ['__str__']),
+ ('len', 'len', 1, ['__len__']),
+ ('hash', 'hash', 1, ['__hash__']),
+ ('getattr', 'getattr', 2, ['__getattribute__']),
+ ('setattr', 'setattr', 3, ['__setattr__']),
+ ('delattr', 'delattr', 2, ['__delattr__']),
+ ('getitem', 'getitem', 2, ['__getitem__']),
+ ('setitem', 'setitem', 3, ['__setitem__']),
+ ('delitem', 'delitem', 2, ['__delitem__']),
+ ('pos', 'pos', 1, ['__pos__']),
+ ('neg', 'neg', 1, ['__neg__']),
+ ('not_', 'not', 1, []),
+ ('abs' , 'abs', 1, ['__abs__']),
+ ('hex', 'hex', 1, ['__hex__']),
+ ('oct', 'oct', 1, ['__oct__']),
+ ('ord', 'ord', 1, []),
+ ('invert', '~', 1, ['__invert__']),
+ ('add', '+', 2, ['__add__', '__radd__']),
+ ('sub', '-', 2, ['__sub__', '__rsub__']),
+ ('mul', '*', 2, ['__mul__', '__rmul__']),
+ ('truediv', '/', 2, ['__truediv__', '__rtruediv__']),
+ ('floordiv', '//', 2, ['__floordiv__', '__rfloordiv__']),
+ ('div', 'div', 2, ['__div__', '__rdiv__']),
+ ('mod', '%', 2, ['__mod__', '__rmod__']),
+ ('divmod', 'divmod', 2, ['__divmod__', '__rdivmod__']),
+ ('pow', '**', 3, ['__pow__', '__rpow__']),
+ ('lshift', '<<', 2, ['__lshift__', '__rlshift__']),
+ ('rshift', '>>', 2, ['__rshift__', '__rrshift__']),
+ ('and_', '&', 2, ['__and__', '__rand__']),
+ ('or_', '|', 2, ['__or__', '__ror__']),
+ ('xor', '^', 2, ['__xor__', '__rxor__']),
+ ('inplace_add', '+=', 2, ['__iadd__']),
+ ('inplace_sub', '-=', 2, ['__isub__']),
+ ('inplace_mul', '*=', 2, ['__imul__']),
+ ('inplace_truediv', '/=', 2, ['__itruediv__']),
+ ('inplace_floordiv','//=', 2, ['__ifloordiv__']),
+ ('inplace_div', 'div=', 2, ['__idiv__']),
+ ('inplace_mod', '%=', 2, ['__imod__']),
+ ('inplace_pow', '**=', 2, ['__ipow__']),
+ ('inplace_lshift', '<<=', 2, ['__ilshift__']),
+ ('inplace_rshift', '>>=', 2, ['__irshift__']),
+ ('inplace_and', '&=', 2, ['__iand__']),
+ ('inplace_or', '|=', 2, ['__ior__']),
+ ('inplace_xor', '^=', 2, ['__ixor__']),
+ ('lt', '<', 2, ['__lt__', '__gt__']),
+ ('le', '<=', 2, ['__le__', '__ge__']),
+ ('eq', '==', 2, ['__eq__', '__eq__']),
+ ('ne', '!=', 2, ['__ne__', '__ne__']),
+ ('gt', '>', 2, ['__gt__', '__lt__']),
+ ('ge', '>=', 2, ['__ge__', '__le__']),
+ ('contains', 'contains', 2, ['__contains__']),
+ ('iter', 'iter', 1, ['__iter__']),
+ ('next', 'next', 1, ['next']), # iterator interface
+ ('call', 'call', 3, ['__call__']),
]
ObjSpace.BuiltinModuleTable = [
Modified: pypy/trunk/src/pypy/objspace/std/boolobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/boolobject.py (original)
+++ pypy/trunk/src/pypy/objspace/std/boolobject.py Thu May 29 15:31:36 2003
@@ -3,6 +3,7 @@
class W_BoolObject(W_Object):
delegate_once = {}
+ statictypename = 'bool'
def __init__(w_self, space, boolval):# please pass in a real bool, not an int
W_Object.__init__(w_self, space)
Modified: pypy/trunk/src/pypy/objspace/std/cpythonobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/cpythonobject.py (original)
+++ pypy/trunk/src/pypy/objspace/std/cpythonobject.py Thu May 29 15:31:36 2003
@@ -123,7 +123,7 @@
'iter': iter,
}
-for _name, _symbol, _arity in ObjSpace.MethodTable:
+for _name, _symbol, _arity, _specialnames in ObjSpace.MethodTable:
f = MethodImplementation.get(_name)
if f:
if _arity == 1:
Modified: pypy/trunk/src/pypy/objspace/std/default.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/default.py (original)
+++ pypy/trunk/src/pypy/objspace/std/default.py Thu May 29 15:31:36 2003
@@ -71,7 +71,7 @@
# in-place operators fall back to their non-in-place counterpart
-for _name, _symbol, _arity in ObjSpace.MethodTable:
+for _name, _symbol, _arity, _specialnames in ObjSpace.MethodTable:
if _name.startswith('inplace_'):
def default_inplace(space, w_1, w_2, baseop=_name[8:]):
op = getattr(space, baseop)
Modified: pypy/trunk/src/pypy/objspace/std/floatobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/floatobject.py (original)
+++ pypy/trunk/src/pypy/objspace/std/floatobject.py Thu May 29 15:31:36 2003
@@ -7,25 +7,40 @@
##############################################################
import math
+import intobject
applicationfile = StdObjSpace.AppFile(__name__)
class W_FloatObject(W_Object):
"""This is a reimplementation of the CPython "PyFloatObject"
it is assumed that the constructor takes a real Python float as
- an argument"""
+ an argument"""
+
+ delegate_once = {}
+ statictypename = 'float'
def __init__(w_self, space, floatval):
W_Object.__init__(w_self, space)
w_self.floatval = floatval
+# int-to-float delegation
+def int_to_float(space, w_intobj):
+ return W_FloatObject(space, float(w_intobj.intval))
+intobject.W_IntObject.delegate_once[W_FloatObject] = int_to_float
+
+
def float_float(space,w_value):
if w_value.__class__ == W_FloatObject:
return w_value
else:
return W_FloatObject(space, w_value.floatval)
-StdObjSpace.float.register(float_float, W_FloatObject)
+#?StdObjSpace.float.register(float_float, W_FloatObject)
+
+def float_unwrap(space, w_float):
+ return w_float.floatval
+
+StdObjSpace.unwrap.register(float_unwrap, W_FloatObject)
def float_repr(space, w_float):
## %reimplement%
@@ -41,17 +56,41 @@
StdObjSpace.str.register(float_str, W_FloatObject)
-def float_float_compare(space, w_float1, w_float2):
- x = w_float1.floatval
- y = w_float2.floatval
- if x < y:
- return space.wrap(-1)
- elif x > y:
- return space.wrap(1)
- else:
- return space.wrap(0)
-
-StdObjSpace.cmp.register(float_float_compare, W_FloatObject, W_FloatObject)
+def float_float_lt(space, w_float1, w_float2):
+ i = w_float1.floatval
+ j = w_float2.floatval
+ return space.newbool( i < j )
+StdObjSpace.lt.register(float_float_lt, W_FloatObject, W_FloatObject)
+
+def float_float_le(space, w_float1, w_float2):
+ i = w_float1.floatval
+ j = w_float2.floatval
+ return space.newbool( i <= j )
+StdObjSpace.le.register(float_float_le, W_FloatObject, W_FloatObject)
+
+def float_float_eq(space, w_float1, w_float2):
+ i = w_float1.floatval
+ j = w_float2.floatval
+ return space.newbool( i == j )
+StdObjSpace.eq.register(float_float_eq, W_FloatObject, W_FloatObject)
+
+def float_float_ne(space, w_float1, w_float2):
+ i = w_float1.floatval
+ j = w_float2.floatval
+ return space.newbool( i != j )
+StdObjSpace.ne.register(float_float_ne, W_FloatObject, W_FloatObject)
+
+def float_float_gt(space, w_float1, w_float2):
+ i = w_float1.floatval
+ j = w_float2.floatval
+ return space.newbool( i > j )
+StdObjSpace.gt.register(float_float_gt, W_FloatObject, W_FloatObject)
+
+def float_float_ge(space, w_float1, w_float2):
+ i = w_float1.floatval
+ j = w_float2.floatval
+ return space.newbool( i >= j )
+StdObjSpace.ge.register(float_float_ge, W_FloatObject, W_FloatObject)
def float_hash(space,w_value):
## %reimplement%
@@ -188,7 +227,7 @@
def float_nonzero(space, w_float):
return w_float.floatval != 0.0
-StdObjSpace.nonzero.register(float_nonzero, W_FloatObject)
+StdObjSpace.is_true.register(float_nonzero, W_FloatObject)
######## coersion must be done later
later = """
Modified: pypy/trunk/src/pypy/objspace/std/intobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/intobject.py (original)
+++ pypy/trunk/src/pypy/objspace/std/intobject.py Thu May 29 15:31:36 2003
@@ -23,6 +23,7 @@
class W_IntObject(W_Object):
delegate_once = {}
+ statictypename = 'int'
def __init__(w_self, space, intval):
W_Object.__init__(w_self, space)
Modified: pypy/trunk/src/pypy/objspace/std/multimethod.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/multimethod.py (original)
+++ pypy/trunk/src/pypy/objspace/std/multimethod.py Thu May 29 15:31:36 2003
@@ -6,15 +6,17 @@
class W_ANY:
"Placeholder to allow dispatch on any value."
+ statictype = None
class MultiMethod(object):
- def __init__(self, operatorsymbol, arity):
+ def __init__(self, operatorsymbol, arity, specialnames):
"MultiMethod dispatching on the first 'arity' arguments."
self.arity = arity
self.operatorsymbol = operatorsymbol
self.dispatch_table = {}
+ self.specialnames = specialnames # list like ['__xxx__', '__rxxx__']
def register(self, function, *types):
# W_ANY can be used as a placeholder to dispatch on any value.
@@ -61,6 +63,16 @@
currentdelegators + (delegator,),
result)
+ def slicetable(self, position, statictype):
+ m = MultiMethod(self.operatorsymbol, self.arity, self.specialnames)
+ for key, value in self.dispatch_table.iteritems():
+ if key[position].statictype == statictype:
+ m.dispatch_table[key] = value
+ return m
+
+ def is_empty(self):
+ return not self.dispatch_table
+
class BoundMultiMethod:
@@ -73,8 +85,26 @@
raise TypeError, ("multimethod needs at least %d arguments" %
self.multimethod.arity)
dispatchargs = args[:self.multimethod.arity]
- extraargs = args[self.multimethod.arity:]
initialtypes = tuple([a.__class__ for a in dispatchargs])
+ try:
+ return self.perform_call(args, initialtypes)
+ except FailedToImplement, e:
+ if e.args:
+ raise OperationError(*e.args)
+ else:
+ if len(initialtypes) <= 1:
+ plural = ""
+ else:
+ plural = "s"
+ typenames = [t.__name__ for t in initialtypes]
+ message = "unsupported operand type%s for %s: %s" % (
+ plural, self.multimethod.operatorsymbol,
+ ', '.join(typenames))
+ w_value = self.space.wrap(message)
+ raise OperationError(self.space.w_TypeError, w_value)
+
+ def perform_call(self, args, initialtypes):
+ extraargs = args[self.multimethod.arity:]
choicelist = self.multimethod.buildchoices(initialtypes)
firstfailure = None
for delegators, function in choicelist:
@@ -90,19 +120,14 @@
# we got FailedToImplement, record the first such error
if firstfailure is None:
firstfailure = e
- if firstfailure is None:
- if len(initialtypes) <= 1:
- plural = ""
- else:
- plural = "s"
- typenames = [t.__name__ for t in initialtypes]
- message = "unsupported operand type%s for %s: %s" % (
- plural, self.multimethod.operatorsymbol,
- ', '.join(typenames))
- w_value = self.space.wrap(message)
- raise OperationError(self.space.w_TypeError, w_value)
- else:
- raise OperationError(*e.args)
+ raise firstfailure or FailedToImplement()
+
+ def slicetable(self, position, statictype):
+ return BoundMultiMethod(self.space,
+ self.multimethod.slicetable(position, statictype))
+
+ def is_empty(self):
+ return self.multimethod.is_empty()
class error(Exception):
Modified: pypy/trunk/src/pypy/objspace/std/noneobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/noneobject.py (original)
+++ pypy/trunk/src/pypy/objspace/std/noneobject.py Thu May 29 15:31:36 2003
@@ -3,6 +3,7 @@
class W_NoneObject(W_Object):
delegate_once = {}
+ statictypename = 'NoneType'
def none_unwrap(space, w_none):
Modified: pypy/trunk/src/pypy/objspace/std/objspace.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/objspace.py (original)
+++ pypy/trunk/src/pypy/objspace/std/objspace.py Thu May 29 15:31:36 2003
@@ -10,9 +10,14 @@
class W_Object:
"Parent base class for wrapped objects."
+ statictype = None
+
def __init__(w_self, space):
w_self.space = space
+ def get_builtin_impl_class(w_self):
+ return w_self.__class__
+
##################################################################
@@ -26,24 +31,45 @@
pass
AppFile.LOCAL_PATH = [PACKAGE_PATH]
+ BUILTIN_TYPES = {
+ 'W_NoneObject': 'noneobject',
+ 'W_BoolObject': 'boolobject',
+ 'W_IntObject': 'intobject',
+ 'W_FloatObject': 'floatobject',
+ #'W_ListObject': 'listobject',
+ }
+ TYPE_CACHE = {}
+
def initialize(self):
from noneobject import W_NoneObject
from boolobject import W_BoolObject
from cpythonobject import W_CPythonObject
+ from typeobject import W_TypeObject, make_type_by_name
self.w_None = W_NoneObject(self)
self.w_False = W_BoolObject(self, False)
self.w_True = W_BoolObject(self, True)
+ self.w_NotImplemented = self.wrap(NotImplemented) # XXX do me
# hack in the exception classes
import __builtin__, types
newstuff = {"False": self.w_False,
"True" : self.w_True,
"None" : self.w_None,
+ "NotImplemented": self.w_NotImplemented,
}
for n, c in __builtin__.__dict__.iteritems():
if isinstance(c, types.ClassType) and issubclass(c, Exception):
w_c = W_CPythonObject(self, c)
setattr(self, 'w_' + c.__name__, w_c)
newstuff[c.__name__] = w_c
+ # make the types
+ for classname, modulename in self.BUILTIN_TYPES.iteritems():
+ mod = __import__(modulename, globals(), locals(), [classname])
+ cls = getattr(mod, classname)
+ w_type = make_type_by_name(self, cls.statictypename)
+ w_type.setup_builtin_type(cls)
+ setattr(self, 'w_' + cls.statictypename, w_type)
+ newstuff[cls.statictypename] = w_type
+
self.make_builtins()
self.make_sys()
# insert these into the newly-made builtins
@@ -71,9 +97,9 @@
items_w = [(self.wrap(k), self.wrap(v)) for (k, v) in x.iteritems()]
import dictobject
return dictobject.W_DictObject(self, items_w)
- #if isinstance(x, float):
- # import floatobject
- # return floatobject.W_FloatObject(self, x)
+ if isinstance(x, float):
+ import floatobject
+ return floatobject.W_FloatObject(self, x)
if isinstance(x, tuple):
wrappeditems = [self.wrap(item) for item in x]
import tupleobject
@@ -124,8 +150,9 @@
return stringobject.W_StringObject(self, ''.join(chars))
# special multimethods
- unwrap = MultiMethod('unwrap', 1) # returns an unwrapped object
- is_true = MultiMethod('nonzero', 1) # returns an unwrapped bool
+ unwrap = MultiMethod('unwrap', 1, []) # returns an unwrapped object
+ is_true = MultiMethod('nonzero', 1, []) # returns an unwrapped bool
+ # XXX do something about __nonzero__ !
## # handling of the common fall-back cases
## def compare_any_any(self, w_1, w_2, operation):
@@ -141,8 +168,8 @@
# add all regular multimethods to StdObjSpace
-for _name, _symbol, _arity in ObjSpace.MethodTable:
- setattr(StdObjSpace, _name, MultiMethod(_symbol, _arity))
+for _name, _symbol, _arity, _specialnames in ObjSpace.MethodTable:
+ setattr(StdObjSpace, _name, MultiMethod(_symbol, _arity, _specialnames))
# default implementations of some multimethods for all objects
# that don't explicitely override them or that raise FailedToImplement
Modified: pypy/trunk/src/pypy/objspace/std/test/test_multimethod.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/test/test_multimethod.py (original)
+++ pypy/trunk/src/pypy/objspace/std/test/test_multimethod.py Thu May 29 15:31:36 2003
@@ -44,7 +44,7 @@
return "add_int_any", y1, o2
class FakeObjSpace:
- add = MultiMethod('+', 2)
+ add = MultiMethod('+', 2, [])
add.register(add_x_x, X, X)
add.register(add_x_y, X, Y)
add.register(add_y_y, Y, Y)
Added: pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py
==============================================================================
--- (empty file)
+++ pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py Thu May 29 15:31:36 2003
@@ -0,0 +1,59 @@
+import unittest, sys
+import testsupport
+from pypy.interpreter import unittest_w
+from pypy.objspace.std import typeobject as tobj
+from pypy.objspace.std.objspace import *
+
+
+class TestPyMultimethodCode(unittest_w.TestCase_w):
+
+ def setUp(self):
+ self.space = StdObjSpace()
+
+ def tearDown(self):
+ pass
+
+ def test_int_sub(self):
+ w = self.space.wrap
+ for i in range(2):
+ meth = tobj.PyMultimethodCode(self.space.sub, i, self.space.w_int)
+ self.assertEqual(meth.multimethod.is_empty(), False)
+ # test int.__sub__ and int.__rsub__
+ self.assertEqual_w(meth.eval_code(self.space, None,
+ w({'x1': 5, 'x2': 7})),
+ w(-2))
+ self.assertEqual_w(meth.eval_code(self.space, None,
+ w({'x1': 5, 'x2': 7.1})),
+ self.space.w_NotImplemented)
+ self.assertEqual_w(meth.eval_code(self.space, None,
+ w({'x1': 5.5, 'x2': 7})),
+ self.space.w_NotImplemented)
+
+ def test_empty_inplace_add(self):
+ for i in range(2):
+ meth = tobj.PyMultimethodCode(self.space.inplace_add, i,
+ self.space.w_int)
+ self.assertEqual(meth.multimethod.is_empty(), True)
+
+ def test_float_sub(self):
+ w = self.space.wrap
+ for i in range(2):
+ meth = tobj.PyMultimethodCode(self.space.sub, i, self.space.w_float)
+ self.assertEqual(meth.multimethod.is_empty(), False)
+ # test float.__sub__ and float.__rsub__
+
+ # some of these tests are pointless for Python because
+ # float.__(r)sub__ should not accept an int as first argument
+ self.assertEqual_w(meth.eval_code(self.space, None,
+ w({'x1': 5, 'x2': 7})),
+ w(-2.0))
+ self.assertEqual_w(meth.eval_code(self.space, None,
+ w({'x1': 5, 'x2': 7.5})),
+ w(-2.5))
+ self.assertEqual_w(meth.eval_code(self.space, None,
+ w({'x1': 5.5, 'x2': 7})),
+ w(-1.5))
+
+
+if __name__ == '__main__':
+ unittest.main()
Added: pypy/trunk/src/pypy/objspace/std/typeobject.py
==============================================================================
--- (empty file)
+++ pypy/trunk/src/pypy/objspace/std/typeobject.py Thu May 29 15:31:36 2003
@@ -0,0 +1,62 @@
+from pypy.interpreter import pycode
+from pypy.objspace.std.objspace import *
+
+
+class W_TypeObject(W_Object):
+ delegate_once = {}
+ statictypename = 'type'
+
+ def __init__(w_self, space, w_tpname):
+ W_Object.__init__(w_self, space)
+ w_self.w_tpname = w_tpname
+ w_self.builtin_implementations = []
+ w_self.multimethods = [value for key, value in space.__dict__.iteritems()
+ if isinstance(value, MultiMethod)]
+
+ def setup_builtin_type(w_self, implementation):
+ implementation.statictype = w_self
+ w_self.builtin_implementations.append(implementation)
+
+
+def make_type_by_name(space, tpname):
+ try:
+ w_type = space.TYPE_CACHE[tpname]
+ except KeyError:
+ w_type = space.TYPE_CACHE[tpname] = W_TypeObject(space,
+ space.wrap(tpname))
+ return w_type
+
+
+class PyMultimethodCode(pycode.PyBaseCode):
+
+ def __init__(self, multimethod, bound_position=None, w_type=None):
+ pycode.PyBaseCode.__init__(self)
+ argnames = ['x%d'%(i+1) for i in range(multimethod.multimethod.arity)]
+ if w_type is not None:
+ multimethod = multimethod.slicetable(bound_position, w_type)
+ argnames.insert(0, argnames.pop(bound_position))
+ self.multimethod = multimethod
+ self.co_name = multimethod.multimethod.operatorsymbol
+ self.co_flags = 0
+ self.co_varnames = tuple(argnames)
+ self.co_argcount = multimethod.multimethod.arity
+
+ def eval_code(self, space, w_globals, w_locals):
+ """Call the multimethod, ignoring all implementations that do not
+ have exactly the expected type at the bound_position."""
+ multimethod = self.multimethod
+ dispatchargs = []
+ initialtypes = []
+ for i in range(multimethod.multimethod.arity):
+ w_arg = space.getitem(w_locals, space.wrap('x%d'%(i+1)))
+ dispatchargs.append(w_arg)
+ initialtypes.append(w_arg.get_builtin_impl_class())
+ dispatchargs = tuple(dispatchargs)
+ initialtypes = tuple(initialtypes)
+ try:
+ return multimethod.perform_call(dispatchargs, initialtypes)
+ except FailedToImplement, e:
+ if e.args:
+ raise OperationError(*e.args)
+ else:
+ return space.w_NotImplemented
Copied: pypy/trunk/src/pypy/objspace/std/userobject.py (from rev 620, pypy/trunk/src/pypy/objspace/std/usertype.py)
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/usertype.py (original)
+++ pypy/trunk/src/pypy/objspace/std/userobject.py Thu May 29 15:31:36 2003
@@ -1,5 +1,6 @@
+from pypy.objspace.std.objspace import *
-class W_UserType:
- def __init__(self):
- pass
+class W_UserObject(W_Object):
+ pass
+
Deleted: pypy/trunk/src/pypy/objspace/std/usertype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/usertype.py Thu May 29 15:31:36 2003
+++ (empty file)
@@ -1,5 +0,0 @@
-
-
-class W_UserType:
- def __init__(self):
- pass
More information about the Pypy-commit
mailing list