]>
Commit | Line | Data |
---|---|---|
4710c53d | 1 | # Python test set -- built-in functions\r |
2 | \r | |
3 | import test.test_support, unittest\r | |
4 | import sys\r | |
5 | import pickle\r | |
6 | import itertools\r | |
7 | \r | |
8 | import warnings\r | |
9 | warnings.filterwarnings("ignore", "integer argument expected",\r | |
10 | DeprecationWarning, "unittest")\r | |
11 | \r | |
12 | # pure Python implementations (3 args only), for comparison\r | |
13 | def pyrange(start, stop, step):\r | |
14 | if (start - stop) // step < 0:\r | |
15 | # replace stop with next element in the sequence of integers\r | |
16 | # that are congruent to start modulo step.\r | |
17 | stop += (start - stop) % step\r | |
18 | while start != stop:\r | |
19 | yield start\r | |
20 | start += step\r | |
21 | \r | |
22 | def pyrange_reversed(start, stop, step):\r | |
23 | stop += (start - stop) % step\r | |
24 | return pyrange(stop - step, start - step, -step)\r | |
25 | \r | |
26 | \r | |
27 | class XrangeTest(unittest.TestCase):\r | |
28 | def assert_iterators_equal(self, xs, ys, test_id, limit=None):\r | |
29 | # check that an iterator xs matches the expected results ys,\r | |
30 | # up to a given limit.\r | |
31 | if limit is not None:\r | |
32 | xs = itertools.islice(xs, limit)\r | |
33 | ys = itertools.islice(ys, limit)\r | |
34 | sentinel = object()\r | |
35 | pairs = itertools.izip_longest(xs, ys, fillvalue=sentinel)\r | |
36 | for i, (x, y) in enumerate(pairs):\r | |
37 | if x == y:\r | |
38 | continue\r | |
39 | elif x == sentinel:\r | |
40 | self.fail('{}: iterator ended unexpectedly '\r | |
41 | 'at position {}; expected {}'.format(test_id, i, y))\r | |
42 | elif y == sentinel:\r | |
43 | self.fail('{}: unexpected excess element {} at '\r | |
44 | 'position {}'.format(test_id, x, i))\r | |
45 | else:\r | |
46 | self.fail('{}: wrong element at position {};'\r | |
47 | 'expected {}, got {}'.format(test_id, i, y, x))\r | |
48 | \r | |
49 | def test_xrange(self):\r | |
50 | self.assertEqual(list(xrange(3)), [0, 1, 2])\r | |
51 | self.assertEqual(list(xrange(1, 5)), [1, 2, 3, 4])\r | |
52 | self.assertEqual(list(xrange(0)), [])\r | |
53 | self.assertEqual(list(xrange(-3)), [])\r | |
54 | self.assertEqual(list(xrange(1, 10, 3)), [1, 4, 7])\r | |
55 | self.assertEqual(list(xrange(5, -5, -3)), [5, 2, -1, -4])\r | |
56 | \r | |
57 | a = 10\r | |
58 | b = 100\r | |
59 | c = 50\r | |
60 | \r | |
61 | self.assertEqual(list(xrange(a, a+2)), [a, a+1])\r | |
62 | self.assertEqual(list(xrange(a+2, a, -1L)), [a+2, a+1])\r | |
63 | self.assertEqual(list(xrange(a+4, a, -2)), [a+4, a+2])\r | |
64 | \r | |
65 | seq = list(xrange(a, b, c))\r | |
66 | self.assertIn(a, seq)\r | |
67 | self.assertNotIn(b, seq)\r | |
68 | self.assertEqual(len(seq), 2)\r | |
69 | \r | |
70 | seq = list(xrange(b, a, -c))\r | |
71 | self.assertIn(b, seq)\r | |
72 | self.assertNotIn(a, seq)\r | |
73 | self.assertEqual(len(seq), 2)\r | |
74 | \r | |
75 | seq = list(xrange(-a, -b, -c))\r | |
76 | self.assertIn(-a, seq)\r | |
77 | self.assertNotIn(-b, seq)\r | |
78 | self.assertEqual(len(seq), 2)\r | |
79 | \r | |
80 | self.assertRaises(TypeError, xrange)\r | |
81 | self.assertRaises(TypeError, xrange, 1, 2, 3, 4)\r | |
82 | self.assertRaises(ValueError, xrange, 1, 2, 0)\r | |
83 | \r | |
84 | self.assertRaises(OverflowError, xrange, 10**100, 10**101, 10**101)\r | |
85 | \r | |
86 | self.assertRaises(TypeError, xrange, 0, "spam")\r | |
87 | self.assertRaises(TypeError, xrange, 0, 42, "spam")\r | |
88 | \r | |
89 | self.assertEqual(len(xrange(0, sys.maxint, sys.maxint-1)), 2)\r | |
90 | \r | |
91 | self.assertRaises(OverflowError, xrange, -sys.maxint, sys.maxint)\r | |
92 | self.assertRaises(OverflowError, xrange, 0, 2*sys.maxint)\r | |
93 | \r | |
94 | r = xrange(-sys.maxint, sys.maxint, 2)\r | |
95 | self.assertEqual(len(r), sys.maxint)\r | |
96 | self.assertRaises(OverflowError, xrange, -sys.maxint-1, sys.maxint, 2)\r | |
97 | \r | |
98 | def test_pickling(self):\r | |
99 | testcases = [(13,), (0, 11), (-22, 10), (20, 3, -1),\r | |
100 | (13, 21, 3), (-2, 2, 2)]\r | |
101 | for proto in range(pickle.HIGHEST_PROTOCOL + 1):\r | |
102 | for t in testcases:\r | |
103 | r = xrange(*t)\r | |
104 | self.assertEqual(list(pickle.loads(pickle.dumps(r, proto))),\r | |
105 | list(r))\r | |
106 | \r | |
107 | def test_range_iterators(self):\r | |
108 | # see issue 7298\r | |
109 | limits = [base + jiggle\r | |
110 | for M in (2**32, 2**64)\r | |
111 | for base in (-M, -M//2, 0, M//2, M)\r | |
112 | for jiggle in (-2, -1, 0, 1, 2)]\r | |
113 | test_ranges = [(start, end, step)\r | |
114 | for start in limits\r | |
115 | for end in limits\r | |
116 | for step in (-2**63, -2**31, -2, -1, 1, 2)]\r | |
117 | \r | |
118 | for start, end, step in test_ranges:\r | |
119 | try:\r | |
120 | iter1 = xrange(start, end, step)\r | |
121 | except OverflowError:\r | |
122 | pass\r | |
123 | else:\r | |
124 | iter2 = pyrange(start, end, step)\r | |
125 | test_id = "xrange({}, {}, {})".format(start, end, step)\r | |
126 | # check first 100 entries\r | |
127 | self.assert_iterators_equal(iter1, iter2, test_id, limit=100)\r | |
128 | \r | |
129 | try:\r | |
130 | iter1 = reversed(xrange(start, end, step))\r | |
131 | except OverflowError:\r | |
132 | pass\r | |
133 | else:\r | |
134 | iter2 = pyrange_reversed(start, end, step)\r | |
135 | test_id = "reversed(xrange({}, {}, {}))".format(start, end, step)\r | |
136 | self.assert_iterators_equal(iter1, iter2, test_id, limit=100)\r | |
137 | \r | |
138 | \r | |
139 | def test_main():\r | |
140 | test.test_support.run_unittest(XrangeTest)\r | |
141 | \r | |
142 | if __name__ == "__main__":\r | |
143 | test_main()\r |