Commit 56304494 authored by Robert Bradshaw's avatar Robert Bradshaw

Handle for-from ranges with unsigned targets and near-zero endpoints.

parent 122904c4
...@@ -6201,12 +6201,24 @@ class ForFromStatNode(LoopNode, StatNode): ...@@ -6201,12 +6201,24 @@ class ForFromStatNode(LoopNode, StatNode):
loopvar_name = code.funcstate.allocate_temp(self.target.type, False) loopvar_name = code.funcstate.allocate_temp(self.target.type, False)
else: else:
loopvar_name = self.loopvar_node.result() loopvar_name = self.loopvar_node.result()
code.putln( if self.target.type.is_int and not self.target.type.signed and self.relation2[0] == '>':
"for (%s = %s%s; %s %s %s; %s%s) {" % ( # Handle the case where the endpoint of an unsigned int iteration
loopvar_name, # is within step of 0.
self.bound1.result(), offset, if not self.step:
loopvar_name, self.relation2, self.bound2.result(), step = 1
loopvar_name, incop)) code.putln(
"for (%s = %s%s + %s; %s %s %s + %s; ) { %s%s;" % (
loopvar_name,
self.bound1.result(), offset, step,
loopvar_name, self.relation2, self.bound2.result(), step,
loopvar_name, incop))
else:
code.putln(
"for (%s = %s%s; %s %s %s; %s%s) {" % (
loopvar_name,
self.bound1.result(), offset,
loopvar_name, self.relation2, self.bound2.result(),
loopvar_name, incop))
if self.py_loopvar_node: if self.py_loopvar_node:
self.py_loopvar_node.generate_evaluation_code(code) self.py_loopvar_node.generate_evaluation_code(code)
self.target.generate_assignment_code(self.py_loopvar_node, code) self.target.generate_assignment_code(self.py_loopvar_node, code)
......
...@@ -759,3 +759,39 @@ def reversed_bytes_slice_step_only(bytes s): ...@@ -759,3 +759,39 @@ def reversed_bytes_slice_step_only(bytes s):
for c in reversed(s[::-1]): for c in reversed(s[::-1]):
result.append(c) result.append(c)
return result return result
@cython.test_assert_path_exists('//ForFromStatNode')
def reversed_unsigned(int a, int b):
"""
>>> reversed_unsigned(0, 5)
[4, 3, 2, 1, 0]
>>> reversed_unsigned(1, 5)
[4, 3, 2, 1]
>>> reversed_unsigned(1, 1)
[]
"""
cdef unsigned int i
return [i for i in reversed(range(a, b))]
@cython.test_assert_path_exists('//ForFromStatNode')
def reversed_unsigned_by_3(int a, int b):
"""
>>> reversed_unsigned_by_3(0, 5)
[3, 0]
>>> reversed_unsigned_by_3(0, 7)
[6, 3, 0]
"""
cdef unsigned int i
return [i for i in reversed(range(a, b, 3))]
@cython.test_assert_path_exists('//ForFromStatNode')
def range_unsigned_by_neg_3(int a, int b):
"""
>>> range_unsigned_by_neg_3(-1, 6)
[6, 3, 0]
>>> range_unsigned_by_neg_3(0, 7)
[7, 4, 1]
"""
cdef unsigned int i
return [i for i in range(b, a, -3)]
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment