Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(425)

Unified Diff: third_party/google-endpoints/future/types/newrange.py

Issue 2666783008: Add google-endpoints to third_party/. (Closed)
Patch Set: Created 3 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: third_party/google-endpoints/future/types/newrange.py
diff --git a/third_party/google-endpoints/future/types/newrange.py b/third_party/google-endpoints/future/types/newrange.py
new file mode 100644
index 0000000000000000000000000000000000000000..c190ba9e3da07df0b60c89ce5f85603b7ada0eec
--- /dev/null
+++ b/third_party/google-endpoints/future/types/newrange.py
@@ -0,0 +1,159 @@
+"""
+Nearly identical to xrange.py, by Dan Crosta, from
+
+ https://github.com/dcrosta/xrange.git
+
+This is included here in the ``future`` package rather than pointed to as
+a dependency because there is no package for ``xrange`` on PyPI. It is
+also tweaked to appear like a regular Python 3 ``range`` object rather
+than a Python 2 xrange.
+
+From Dan Crosta's README:
+
+ "A pure-Python implementation of Python 2.7's xrange built-in, with
+ some features backported from the Python 3.x range built-in (which
+ replaced xrange) in that version."
+
+ Read more at
+ https://late.am/post/2012/06/18/what-the-heck-is-an-xrange
+"""
+from __future__ import absolute_import
+
+from collections import Sequence, Iterator
+from itertools import islice
+
+from future.backports.misc import count # with step parameter on Py2.6
+# For backward compatibility with python-future versions < 0.14.4:
+_count = count
+
+
+class newrange(Sequence):
+ """
+ Pure-Python backport of Python 3's range object. See `the CPython
+ documentation for details:
+ <http://docs.python.org/py3k/library/functions.html#range>`_
+ """
+
+ def __init__(self, *args):
+ if len(args) == 1:
+ start, stop, step = 0, args[0], 1
+ elif len(args) == 2:
+ start, stop, step = args[0], args[1], 1
+ elif len(args) == 3:
+ start, stop, step = args
+ else:
+ raise TypeError('range() requires 1-3 int arguments')
+
+ try:
+ start, stop, step = int(start), int(stop), int(step)
+ except ValueError:
+ raise TypeError('an integer is required')
+
+ if step == 0:
+ raise ValueError('range() arg 3 must not be zero')
+ elif step < 0:
+ stop = min(stop, start)
+ else:
+ stop = max(stop, start)
+
+ self._start = start
+ self._stop = stop
+ self._step = step
+ self._len = (stop - start) // step + bool((stop - start) % step)
+
+ @property
+ def start(self):
+ return self._start
+
+ @property
+ def stop(self):
+ return self._stop
+
+ @property
+ def step(self):
+ return self._step
+
+ def __repr__(self):
+ if self._step == 1:
+ return 'range(%d, %d)' % (self._start, self._stop)
+ return 'range(%d, %d, %d)' % (self._start, self._stop, self._step)
+
+ def __eq__(self, other):
+ return (isinstance(other, newrange) and
+ (self._len == 0 == other._len or
+ (self._start, self._step, self._len) ==
+ (other._start, other._step, self._len)))
+
+ def __len__(self):
+ return self._len
+
+ def index(self, value):
+ """Return the 0-based position of integer `value` in
+ the sequence this range represents."""
+ diff = value - self._start
+ quotient, remainder = divmod(diff, self._step)
+ if remainder == 0 and 0 <= quotient < self._len:
+ return abs(quotient)
+ raise ValueError('%r is not in range' % value)
+
+ def count(self, value):
+ """Return the number of ocurrences of integer `value`
+ in the sequence this range represents."""
+ # a value can occur exactly zero or one times
+ return int(value in self)
+
+ def __contains__(self, value):
+ """Return ``True`` if the integer `value` occurs in
+ the sequence this range represents."""
+ try:
+ self.index(value)
+ return True
+ except ValueError:
+ return False
+
+ def __reversed__(self):
+ return iter(self[::-1])
+
+ def __getitem__(self, index):
+ """Return the element at position ``index`` in the sequence
+ this range represents, or raise :class:`IndexError` if the
+ position is out of range."""
+ if isinstance(index, slice):
+ return self.__getitem_slice(index)
+ if index < 0:
+ # negative indexes access from the end
+ index = self._len + index
+ if index < 0 or index >= self._len:
+ raise IndexError('range object index out of range')
+ return self._start + index * self._step
+
+ def __getitem_slice(self, slce):
+ """Return a range which represents the requested slce
+ of the sequence represented by this range.
+ """
+ scaled_indices = (self._step * n for n in slce.indices(self._len))
+ start_offset, stop_offset, new_step = scaled_indices
+ return newrange(self._start + start_offset,
+ self._start + stop_offset,
+ new_step)
+
+ def __iter__(self):
+ """Return an iterator which enumerates the elements of the
+ sequence this range represents."""
+ return range_iterator(self)
+
+
+class range_iterator(Iterator):
+ """An iterator for a :class:`range`.
+ """
+ def __init__(self, range_):
+ self._stepper = islice(count(range_.start, range_.step), len(range_))
+
+ def __iter__(self):
+ return self
+
+ def next(self):
+ return next(self._stepper)
+
+
+__all__ = ['newrange']
« no previous file with comments | « third_party/google-endpoints/future/types/newopen.py ('k') | third_party/google-endpoints/future/types/newstr.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698