Added 'list_only' option (and modified 'run()' to respect it).
[python/dscho.git] / Objects / sliceobject.c
bloba232296705788a41e4e11711e0ac3fb9ff2583f9
1 /*
2 Written by Jim Hugunin and Chris Chase.
4 This includes both the singular ellipsis object and slice objects.
6 Guido, feel free to do whatever you want in the way of copyrights
7 for this file.
8 */
10 /*
11 Py_Ellipsis encodes the '...' rubber index token. It is similar to
12 the Py_NoneStruct in that there is no way to create other objects of
13 this type and there is exactly one in existence.
16 #include "Python.h"
18 static PyObject *
19 ellipsis_repr(op)
20 PyObject *op;
22 return PyString_FromString("Ellipsis");
25 static PyTypeObject PyEllipsis_Type = {
26 PyObject_HEAD_INIT(&PyType_Type)
28 "ellipsis",
31 0, /*tp_dealloc*/ /*never called*/
32 0, /*tp_print*/
33 0, /*tp_getattr*/
34 0, /*tp_setattr*/
35 0, /*tp_compare*/
36 (reprfunc)ellipsis_repr, /*tp_repr*/
37 0, /*tp_as_number*/
38 0, /*tp_as_sequence*/
39 0, /*tp_as_mapping*/
40 0, /*tp_hash */
43 PyObject _Py_EllipsisObject = {
44 PyObject_HEAD_INIT(&PyEllipsis_Type)
48 /* Slice object implementation
50 start, stop, and step are python objects with None indicating no
51 index is present.
54 PyObject *
55 PySlice_New(start, stop, step)
56 PyObject *start;
57 PyObject *stop;
58 PyObject *step;
60 PySliceObject *obj =
61 (PySliceObject *) PyObject_NEW(PySliceObject, &PySlice_Type);
63 if (step == NULL) step = Py_None;
64 Py_INCREF(step);
65 if (start == NULL) start = Py_None;
66 Py_INCREF(start);
67 if (stop == NULL) stop = Py_None;
68 Py_INCREF(stop);
70 obj->step = step;
71 obj->start = start;
72 obj->stop = stop;
74 return (PyObject *) obj;
77 int
78 PySlice_GetIndices(r, length, start, stop, step)
79 PySliceObject *r;
80 int length;
81 int *start;
82 int *stop;
83 int *step;
85 if (r->step == Py_None) {
86 *step = 1;
87 } else {
88 if (!PyInt_Check(r->step)) return -1;
89 *step = PyInt_AsLong(r->step);
91 if (r->start == Py_None) {
92 *start = *step < 0 ? length-1 : 0;
93 } else {
94 if (!PyInt_Check(r->start)) return -1;
95 *start = PyInt_AsLong(r->start);
96 if (*start < 0) *start += length;
98 if (r->stop == Py_None) {
99 *stop = *step < 0 ? -1 : length;
100 } else {
101 if (!PyInt_Check(r->stop)) return -1;
102 *stop = PyInt_AsLong(r->stop);
103 if (*stop < 0) *stop += length;
105 if (*stop > length) return -1;
106 if (*start >= length) return -1;
107 if (*step == 0) return -1;
108 return 0;
111 static void
112 slice_dealloc(r)
113 PySliceObject *r;
115 Py_DECREF(r->step);
116 Py_DECREF(r->start);
117 Py_DECREF(r->stop);
118 PyMem_DEL(r);
121 static PyObject *
122 slice_repr(r)
123 PySliceObject *r;
125 PyObject *s, *comma;
127 s = PyString_FromString("slice(");
128 comma = PyString_FromString(", ");
129 PyString_ConcatAndDel(&s, PyObject_Repr(r->start));
130 PyString_Concat(&s, comma);
131 PyString_ConcatAndDel(&s, PyObject_Repr(r->stop));
132 PyString_Concat(&s, comma);
133 PyString_ConcatAndDel(&s, PyObject_Repr(r->step));
134 PyString_ConcatAndDel(&s, PyString_FromString(")"));
135 Py_DECREF(comma);
136 return s;
140 static PyObject *slice_getattr(self, name)
141 PySliceObject *self;
142 char *name;
144 PyObject *ret;
146 ret = NULL;
147 if (strcmp(name, "start") == 0) {
148 ret = self->start;
150 else if (strcmp(name, "stop") == 0) {
151 ret = self->stop;
153 else if (strcmp(name, "step") == 0) {
154 ret = self->step;
156 else if (strcmp(name, "__members__") == 0) {
157 return Py_BuildValue("[sss]",
158 "start", "stop", "step");
160 else {
161 PyErr_SetString(PyExc_AttributeError, name);
162 return NULL;
164 Py_INCREF(ret);
165 return ret;
169 PyTypeObject PySlice_Type = {
170 PyObject_HEAD_INIT(&PyType_Type)
171 0, /* Number of items for varobject */
172 "slice", /* Name of this type */
173 sizeof(PySliceObject), /* Basic object size */
174 0, /* Item size for varobject */
175 (destructor)slice_dealloc, /*tp_dealloc*/
176 0, /*tp_print*/
177 (getattrfunc)slice_getattr, /*tp_getattr*/
178 0, /*tp_setattr*/
179 0, /*tp_compare*/
180 (reprfunc)slice_repr, /*tp_repr*/
181 0, /*tp_as_number*/
182 0, /*tp_as_sequence*/
183 0, /*tp_as_mapping*/