[pypy-svn] r26714 - in pypy/dist/pypy: annotation annotation/test rpython/lltypesystem rpython/test
arigo at codespeak.net
arigo at codespeak.net
Wed May 3 11:02:50 CEST 2006
Author: arigo
Date: Wed May 3 11:02:48 2006
New Revision: 26714
Modified:
pypy/dist/pypy/annotation/annrpython.py
pypy/dist/pypy/annotation/test/test_annrpython.py
pypy/dist/pypy/annotation/unaryop.py
pypy/dist/pypy/rpython/lltypesystem/rdict.py
pypy/dist/pypy/rpython/test/test_remptydict.py
Log:
(pedronis, arigo) Support for iterating over empty lists and dicts.
Modified: pypy/dist/pypy/annotation/annrpython.py
==============================================================================
--- pypy/dist/pypy/annotation/annrpython.py (original)
+++ pypy/dist/pypy/annotation/annrpython.py Wed May 3 11:02:48 2006
@@ -488,11 +488,12 @@
exits = [link for link in block.exits
if link.exitcase is not None]
- elif e.op.opname in ('simple_call', 'call_args'):
+ elif e.op.opname in ('simple_call', 'call_args', 'next'):
# XXX warning, keep the name of the call operations in sync
# with the flow object space. These are the operations for
# which it is fine to always raise an exception. We then
# swallow the BlockedInference and that's it.
+ # About 'next': see test_annotate_iter_empty_container().
return
else:
Modified: pypy/dist/pypy/annotation/test/test_annrpython.py
==============================================================================
--- pypy/dist/pypy/annotation/test/test_annrpython.py (original)
+++ pypy/dist/pypy/annotation/test/test_annrpython.py Wed May 3 11:02:48 2006
@@ -1975,6 +1975,23 @@
assert s.__class__ == annmodel.SomeObject
assert s.knowntype == type
+ def test_annotate_iter_empty_container(self):
+ def f():
+ n = 0
+ d = {}
+ for x in []: n += x
+ for y in d: n += y
+ for z in d.iterkeys(): n += z
+ for s in d.itervalues(): n += s
+ for t, u in d.items(): n += t * u
+ for t, u in d.iteritems(): n += t * u
+ return n
+
+ a = self.RPythonAnnotator()
+ s = a.build_types(f, [])
+ assert s.is_constant()
+ assert s.const == 0
+
def g(n):
return [0,1,2,n]
Modified: pypy/dist/pypy/annotation/unaryop.py
==============================================================================
--- pypy/dist/pypy/annotation/unaryop.py (original)
+++ pypy/dist/pypy/annotation/unaryop.py Wed May 3 11:02:48 2006
@@ -7,7 +7,7 @@
SomeDict, SomeUnicodeCodePoint, SomeTuple, SomeImpossibleValue, \
SomeInstance, SomeBuiltin, SomeFloat, SomeIterator, SomePBC, \
SomeExternalObject, SomeTypedAddressAccess, SomeAddress, \
- SomeCTypesObject,\
+ SomeCTypesObject, s_ImpossibleValue, \
unionof, set, missing_operation, add_knowntypedata
from pypy.annotation.bookkeeper import getbookkeeper
from pypy.annotation import builtin
@@ -317,8 +317,13 @@
elif variant == 'values':
return dct.dictdef.read_value()
elif variant == 'items':
- return SomeTuple((dct.dictdef.read_key(),
- dct.dictdef.read_value()))
+ s_key = dct.dictdef.read_key()
+ s_value = dct.dictdef.read_value()
+ if (isinstance(s_key, SomeImpossibleValue) or
+ isinstance(s_value, SomeImpossibleValue)):
+ return s_ImpossibleValue
+ else:
+ return SomeTuple((s_key, s_value))
else:
raise ValueError
@@ -342,8 +347,7 @@
return getbookkeeper().newlist(dct.dictdef.read_value())
def method_items(dct):
- return getbookkeeper().newlist(SomeTuple((dct.dictdef.read_key(),
- dct.dictdef.read_value())))
+ return getbookkeeper().newlist(dct.getanyitem('items'))
def method_iterkeys(dct):
return SomeIterator(dct, 'keys')
@@ -388,7 +392,7 @@
def method_join(str, s_list):
getbookkeeper().count("str_join", str)
s_item = s_list.listdef.read_item()
- if s_item == SomeImpossibleValue():
+ if isinstance(s_item, SomeImpossibleValue):
return immutablevalue("")
return SomeString()
Modified: pypy/dist/pypy/rpython/lltypesystem/rdict.py
==============================================================================
--- pypy/dist/pypy/rpython/lltypesystem/rdict.py (original)
+++ pypy/dist/pypy/rpython/lltypesystem/rdict.py Wed May 3 11:02:48 2006
@@ -614,7 +614,9 @@
index = index + 1
if entry.valid():
iter.index = index
- if func is dum_items:
+ if RETURNTYPE is lltype.Void:
+ return None
+ elif func is dum_items:
r = lltype.malloc(RETURNTYPE.TO)
r.item0 = recast(RETURNTYPE.TO.item0, entry.key)
r.item1 = recast(RETURNTYPE.TO.item1, entry.value)
@@ -707,15 +709,16 @@
entry = entries[i]
if entry.valid():
ELEM = lltype.typeOf(items).TO.OF
- if func is dum_items:
- r = lltype.malloc(ELEM.TO)
- r.item0 = recast(ELEM.TO.item0, entry.key)
- r.item1 = recast(ELEM.TO.item1, entry.value)
- items[p] = r
- elif func is dum_keys:
- items[p] = recast(ELEM, entry.key)
- elif func is dum_values:
- items[p] = recast(ELEM, entry.value)
+ if ELEM is not lltype.Void:
+ if func is dum_items:
+ r = lltype.malloc(ELEM.TO)
+ r.item0 = recast(ELEM.TO.item0, entry.key)
+ r.item1 = recast(ELEM.TO.item1, entry.value)
+ items[p] = r
+ elif func is dum_keys:
+ items[p] = recast(ELEM, entry.key)
+ elif func is dum_values:
+ items[p] = recast(ELEM, entry.value)
p += 1
i += 1
return res
Modified: pypy/dist/pypy/rpython/test/test_remptydict.py
==============================================================================
--- pypy/dist/pypy/rpython/test/test_remptydict.py (original)
+++ pypy/dist/pypy/rpython/test/test_remptydict.py Wed May 3 11:02:48 2006
@@ -11,3 +11,17 @@
return bool(a.d1) or bool(a.d2)
res = interpret(func, [])
assert res is False
+
+def test_iterate_over_empty_dict():
+ def f():
+ n = 0
+ d = {}
+ for x in []: n += x
+ for y in d: n += y
+ for z in d.iterkeys(): n += z
+ for s in d.itervalues(): n += s
+ for t, u in d.items(): n += t * u
+ for t, u in d.iteritems(): n += t * u
+ return n
+ res = interpret(f, [])
+ assert res == 0
More information about the Pypy-commit
mailing list