Mercurial > cpython-lru_cache-weakref
view Objects/sliceobject.c @ 56121:ea697cde6882 3.1
Merged revisions 74881-74885,74888,74891-74895,74900,74905-74906,74931-74932,74934,74941-74942,74944,74956 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/branches/py3k
........
r74881 | r.david.murray | 2009-09-17 15:12:49 -0400 (Thu, 17 Sep 2009) | 2 lines
Check in first draft of maintainers.rst.
........
r74882 | eric.smith | 2009-09-17 15:22:30 -0400 (Thu, 17 Sep 2009) | 1 line
Typo.
........
r74883 | mark.dickinson | 2009-09-17 15:37:28 -0400 (Thu, 17 Sep 2009) | 1 line
Add some more module maintainers.
........
r74884 | mark.dickinson | 2009-09-17 15:39:12 -0400 (Thu, 17 Sep 2009) | 1 line
Revert accidental changes to Objects/longobject.c
........
r74885 | mark.dickinson | 2009-09-17 16:20:01 -0400 (Thu, 17 Sep 2009) | 1 line
Add decimal maintainers
........
r74888 | r.david.murray | 2009-09-17 18:10:48 -0400 (Thu, 17 Sep 2009) | 2 lines
Maintainer additions from MAL.
........
r74891 | georg.brandl | 2009-09-17 18:18:01 -0400 (Thu, 17 Sep 2009) | 1 line
Some more maintainers.
........
r74892 | r.david.murray | 2009-09-17 19:23:56 -0400 (Thu, 17 Sep 2009) | 2 lines
Add a couple interest areas for Nick per his request.
........
r74893 | r.david.murray | 2009-09-17 19:43:20 -0400 (Thu, 17 Sep 2009) | 2 lines
Benajmin is also compiler-knowledgeable.
........
r74894 | alexandre.vassalotti | 2009-09-17 20:59:05 -0400 (Thu, 17 Sep 2009) | 2 lines
Added myself to my areas of interest.
........
r74895 | brett.cannon | 2009-09-17 21:03:35 -0400 (Thu, 17 Sep 2009) | 1 line
Add myself to a couple places as maintainer.
........
r74900 | georg.brandl | 2009-09-18 05:06:37 -0400 (Fri, 18 Sep 2009) | 1 line
Add myself in interest areas.
........
r74905 | ezio.melotti | 2009-09-18 05:58:43 -0400 (Fri, 18 Sep 2009) | 1 line
Add myself in interest areas and mark effbot as inactive in winsound
........
r74906 | antoine.pitrou | 2009-09-18 09:15:23 -0400 (Fri, 18 Sep 2009) | 3 lines
Add myself in a couple of places
........
r74931 | r.david.murray | 2009-09-18 17:25:36 -0400 (Fri, 18 Sep 2009) | 5 lines
Add some names gleaned from the "Tracker Archeology" thread
on python-dev from back in February. Also consolidate
the autoconf and makefiles topics into one, and add tracker
and svn/hg topics.
........
r74932 | r.david.murray | 2009-09-18 17:32:16 -0400 (Fri, 18 Sep 2009) | 2 lines
Remove non-committer mistakenly added.
........
r74934 | r.david.murray | 2009-09-18 17:40:30 -0400 (Fri, 18 Sep 2009) | 2 lines
More descriptive/generic name for the svn/hg entry (version control)
........
r74941 | benjamin.peterson | 2009-09-18 18:45:59 -0400 (Fri, 18 Sep 2009) | 1 line
add a new category for myself
........
r74942 | benjamin.peterson | 2009-09-18 18:50:55 -0400 (Fri, 18 Sep 2009) | 1 line
add myself for symtable
........
r74944 | georg.brandl | 2009-09-19 03:39:05 -0400 (Sat, 19 Sep 2009) | 1 line
I would like to maintain the token module!
........
r74956 | r.david.murray | 2009-09-19 14:40:08 -0400 (Sat, 19 Sep 2009) | 3 lines
Add everyone who we know has been a release manager
as a resource for the 'release management' topic.
........
| author | R. David Murray <rdmurray@bitdance.com> |
|---|---|
| date | Sat, 19 Sep 2009 19:04:37 +0000 |
| parents | b5e2bcbbfa74 |
| children | cab14be0ada1 |
line wrap: on
line source
/* Written by Jim Hugunin and Chris Chase. This includes both the singular ellipsis object and slice objects. Guido, feel free to do whatever you want in the way of copyrights for this file. */ /* Py_Ellipsis encodes the '...' rubber index token. It is similar to the Py_NoneStruct in that there is no way to create other objects of this type and there is exactly one in existence. */ #include "Python.h" #include "structmember.h" static PyObject * ellipsis_repr(PyObject *op) { return PyUnicode_FromString("Ellipsis"); } PyTypeObject PyEllipsis_Type = { PyVarObject_HEAD_INIT(&PyType_Type, 0) "ellipsis", /* tp_name */ 0, /* tp_basicsize */ 0, /* tp_itemsize */ 0, /*never called*/ /* tp_dealloc */ 0, /* tp_print */ 0, /* tp_getattr */ 0, /* tp_setattr */ 0, /* tp_reserved */ ellipsis_repr, /* tp_repr */ 0, /* tp_as_number */ 0, /* tp_as_sequence */ 0, /* tp_as_mapping */ 0, /* tp_hash */ 0, /* tp_call */ 0, /* tp_str */ PyObject_GenericGetAttr, /* tp_getattro */ 0, /* tp_setattro */ 0, /* tp_as_buffer */ Py_TPFLAGS_DEFAULT, /* tp_flags */ }; PyObject _Py_EllipsisObject = { _PyObject_EXTRA_INIT 1, &PyEllipsis_Type }; /* Slice object implementation start, stop, and step are python objects with None indicating no index is present. */ PyObject * PySlice_New(PyObject *start, PyObject *stop, PyObject *step) { PySliceObject *obj = PyObject_New(PySliceObject, &PySlice_Type); if (obj == NULL) return NULL; if (step == NULL) step = Py_None; Py_INCREF(step); if (start == NULL) start = Py_None; Py_INCREF(start); if (stop == NULL) stop = Py_None; Py_INCREF(stop); obj->step = step; obj->start = start; obj->stop = stop; return (PyObject *) obj; } PyObject * _PySlice_FromIndices(Py_ssize_t istart, Py_ssize_t istop) { PyObject *start, *end, *slice; start = PyLong_FromSsize_t(istart); if (!start) return NULL; end = PyLong_FromSsize_t(istop); if (!end) { Py_DECREF(start); return NULL; } slice = PySlice_New(start, end, NULL); Py_DECREF(start); Py_DECREF(end); return slice; } int PySlice_GetIndices(PySliceObject *r, Py_ssize_t length, Py_ssize_t *start, Py_ssize_t *stop, Py_ssize_t *step) { /* XXX support long ints */ if (r->step == Py_None) { *step = 1; } else { if (!PyLong_Check(r->step)) return -1; *step = PyLong_AsSsize_t(r->step); } if (r->start == Py_None) { *start = *step < 0 ? length-1 : 0; } else { if (!PyLong_Check(r->start)) return -1; *start = PyLong_AsSsize_t(r->start); if (*start < 0) *start += length; } if (r->stop == Py_None) { *stop = *step < 0 ? -1 : length; } else { if (!PyLong_Check(r->stop)) return -1; *stop = PyLong_AsSsize_t(r->stop); if (*stop < 0) *stop += length; } if (*stop > length) return -1; if (*start >= length) return -1; if (*step == 0) return -1; return 0; } int PySlice_GetIndicesEx(PySliceObject *r, Py_ssize_t length, Py_ssize_t *start, Py_ssize_t *stop, Py_ssize_t *step, Py_ssize_t *slicelength) { /* this is harder to get right than you might think */ Py_ssize_t defstart, defstop; if (r->step == Py_None) { *step = 1; } else { if (!_PyEval_SliceIndex(r->step, step)) return -1; if (*step == 0) { PyErr_SetString(PyExc_ValueError, "slice step cannot be zero"); return -1; } } defstart = *step < 0 ? length-1 : 0; defstop = *step < 0 ? -1 : length; if (r->start == Py_None) { *start = defstart; } else { if (!_PyEval_SliceIndex(r->start, start)) return -1; if (*start < 0) *start += length; if (*start < 0) *start = (*step < 0) ? -1 : 0; if (*start >= length) *start = (*step < 0) ? length - 1 : length; } if (r->stop == Py_None) { *stop = defstop; } else { if (!_PyEval_SliceIndex(r->stop, stop)) return -1; if (*stop < 0) *stop += length; if (*stop < 0) *stop = (*step < 0) ? -1 : 0; if (*stop >= length) *stop = (*step < 0) ? length - 1 : length; } if ((*step < 0 && *stop >= *start) || (*step > 0 && *start >= *stop)) { *slicelength = 0; } else if (*step < 0) { *slicelength = (*stop-*start+1)/(*step)+1; } else { *slicelength = (*stop-*start-1)/(*step)+1; } return 0; } static PyObject * slice_new(PyTypeObject *type, PyObject *args, PyObject *kw) { PyObject *start, *stop, *step; start = stop = step = NULL; if (!_PyArg_NoKeywords("slice()", kw)) return NULL; if (!PyArg_UnpackTuple(args, "slice", 1, 3, &start, &stop, &step)) return NULL; /* This swapping of stop and start is to maintain similarity with range(). */ if (stop == NULL) { stop = start; start = NULL; } return PySlice_New(start, stop, step); } PyDoc_STRVAR(slice_doc, "slice([start,] stop[, step])\n\ \n\ Create a slice object. This is used for extended slicing (e.g. a[0:10:2])."); static void slice_dealloc(PySliceObject *r) { Py_DECREF(r->step); Py_DECREF(r->start); Py_DECREF(r->stop); PyObject_Del(r); } static PyObject * slice_repr(PySliceObject *r) { return PyUnicode_FromFormat("slice(%R, %R, %R)", r->start, r->stop, r->step); } static PyMemberDef slice_members[] = { {"start", T_OBJECT, offsetof(PySliceObject, start), READONLY}, {"stop", T_OBJECT, offsetof(PySliceObject, stop), READONLY}, {"step", T_OBJECT, offsetof(PySliceObject, step), READONLY}, {0} }; static PyObject* slice_indices(PySliceObject* self, PyObject* len) { Py_ssize_t ilen, start, stop, step, slicelength; ilen = PyNumber_AsSsize_t(len, PyExc_OverflowError); if (ilen == -1 && PyErr_Occurred()) { return NULL; } if (PySlice_GetIndicesEx(self, ilen, &start, &stop, &step, &slicelength) < 0) { return NULL; } return Py_BuildValue("(nnn)", start, stop, step); } PyDoc_STRVAR(slice_indices_doc, "S.indices(len) -> (start, stop, stride)\n\ \n\ Assuming a sequence of length len, calculate the start and stop\n\ indices, and the stride length of the extended slice described by\n\ S. Out of bounds indices are clipped in a manner consistent with the\n\ handling of normal slices."); static PyObject * slice_reduce(PySliceObject* self) { return Py_BuildValue("O(OOO)", Py_TYPE(self), self->start, self->stop, self->step); } PyDoc_STRVAR(reduce_doc, "Return state information for pickling."); static PyMethodDef slice_methods[] = { {"indices", (PyCFunction)slice_indices, METH_O, slice_indices_doc}, {"__reduce__", (PyCFunction)slice_reduce, METH_NOARGS, reduce_doc}, {NULL, NULL} }; static PyObject * slice_richcompare(PyObject *v, PyObject *w, int op) { PyObject *t1; PyObject *t2; PyObject *res; if (!PySlice_Check(v) || !PySlice_Check(w)) { Py_INCREF(Py_NotImplemented); return Py_NotImplemented; } if (v == w) { /* XXX Do we really need this shortcut? There's a unit test for it, but is that fair? */ switch (op) { case Py_EQ: case Py_LE: case Py_GE: res = Py_True; break; default: res = Py_False; break; } Py_INCREF(res); return res; } t1 = PyTuple_New(3); t2 = PyTuple_New(3); if (t1 == NULL || t2 == NULL) return NULL; PyTuple_SET_ITEM(t1, 0, ((PySliceObject *)v)->start); PyTuple_SET_ITEM(t1, 1, ((PySliceObject *)v)->stop); PyTuple_SET_ITEM(t1, 2, ((PySliceObject *)v)->step); PyTuple_SET_ITEM(t2, 0, ((PySliceObject *)w)->start); PyTuple_SET_ITEM(t2, 1, ((PySliceObject *)w)->stop); PyTuple_SET_ITEM(t2, 2, ((PySliceObject *)w)->step); res = PyObject_RichCompare(t1, t2, op); PyTuple_SET_ITEM(t1, 0, NULL); PyTuple_SET_ITEM(t1, 1, NULL); PyTuple_SET_ITEM(t1, 2, NULL); PyTuple_SET_ITEM(t2, 0, NULL); PyTuple_SET_ITEM(t2, 1, NULL); PyTuple_SET_ITEM(t2, 2, NULL); Py_DECREF(t1); Py_DECREF(t2); return res; } static long slice_hash(PySliceObject *v) { PyErr_SetString(PyExc_TypeError, "unhashable type"); return -1L; } PyTypeObject PySlice_Type = { PyVarObject_HEAD_INIT(&PyType_Type, 0) "slice", /* Name of this type */ sizeof(PySliceObject), /* Basic object size */ 0, /* Item size for varobject */ (destructor)slice_dealloc, /* tp_dealloc */ 0, /* tp_print */ 0, /* tp_getattr */ 0, /* tp_setattr */ 0, /* tp_reserved */ (reprfunc)slice_repr, /* tp_repr */ 0, /* tp_as_number */ 0, /* tp_as_sequence */ 0, /* tp_as_mapping */ (hashfunc)slice_hash, /* tp_hash */ 0, /* tp_call */ 0, /* tp_str */ PyObject_GenericGetAttr, /* tp_getattro */ 0, /* tp_setattro */ 0, /* tp_as_buffer */ Py_TPFLAGS_DEFAULT, /* tp_flags */ slice_doc, /* tp_doc */ 0, /* tp_traverse */ 0, /* tp_clear */ slice_richcompare, /* tp_richcompare */ 0, /* tp_weaklistoffset */ 0, /* tp_iter */ 0, /* tp_iternext */ slice_methods, /* tp_methods */ slice_members, /* tp_members */ 0, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ 0, /* tp_descr_get */ 0, /* tp_descr_set */ 0, /* tp_dictoffset */ 0, /* tp_init */ 0, /* tp_alloc */ slice_new, /* tp_new */ };
