[Python-checkins] python/dist/src/Objects enumobject.c, 1.14, 1.15 listobject.c, 2.188, 2.189 rangeobject.c, 2.49, 2.50

rhettinger at users.sourceforge.net rhettinger at users.sourceforge.net
Wed Mar 10 05:10:45 EST 2004


Update of /cvsroot/python/python/dist/src/Objects
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv20181/Objects

Modified Files:
	enumobject.c listobject.c rangeobject.c 
Log Message:
Tidied up the implementations of reversed (including the custom ones
for xrange and list objects).

* list.__reversed__ now checks the length of the sequence object before
  calling PyList_GET_ITEM() because the mutable could have changed length.
  
* all three implementations are now tranparent with respect to length and
  maintain the invariant len(it) == len(list(it)) even when the underlying
  sequence mutates.
  
* __builtin__.reversed() now frees the underlying sequence as soon
  as the iterator is exhausted.

* the code paths were rearranged so that the most common paths
  do not require a jump.



Index: enumobject.c
===================================================================
RCS file: /cvsroot/python/python/dist/src/Objects/enumobject.c,v
retrieving revision 1.14
retrieving revision 1.15
diff -C2 -d -r1.14 -r1.15
*** enumobject.c	10 Mar 2004 08:32:46 -0000	1.14
--- enumobject.c	10 Mar 2004 10:10:42 -0000	1.15
***************
*** 218,238 ****
  {
  	PyObject *item;
  
! 	if (ro->index < 0)
! 		return NULL;
! 
! 	assert(PySequence_Check(ro->seq));
! 	item = PySequence_GetItem(ro->seq, ro->index);
! 	if (item == NULL)
! 		return NULL;
! 
! 	ro->index--;
! 	return item;
! }
! 
! static int
! reversed_len(reversedobject *ro)
! {
! 	return PyObject_Size(ro->seq);
  }
  
--- 218,236 ----
  {
  	PyObject *item;
+ 	long index = ro->index;
  
! 	if (index >= 0) {
! 		item = PySequence_GetItem(ro->seq, index);
! 		if (item != NULL) {
! 			ro->index--;
! 			return item;
! 		}
! 	}
! 	ro->index = -1;
! 	if (ro->seq != NULL) {
! 		Py_DECREF(ro->seq);
! 		ro->seq = NULL;
! 	}
! 	return NULL;
  }
  
***************
*** 242,245 ****
--- 240,249 ----
  "Return a reverse iterator");
  
+ static int
+ reversed_len(reversedobject *ro)
+ {
+ 	return ro->index + 1;
+ }
+ 
  static PySequenceMethods reversed_as_sequence = {
  	(inquiry)reversed_len,		/* sq_length */

Index: listobject.c
===================================================================
RCS file: /cvsroot/python/python/dist/src/Objects/listobject.c,v
retrieving revision 2.188
retrieving revision 2.189
diff -C2 -d -r2.188 -r2.189
*** listobject.c	9 Mar 2004 13:05:06 -0000	2.188
--- listobject.c	10 Mar 2004 10:10:42 -0000	2.189
***************
*** 2794,2812 ****
  listreviter_next(listreviterobject *it)
  {
! 	PyObject *item = NULL;
  
! 	assert(PyList_Check(it->it_seq));
! 	if (it->it_index >= 0) {
! 		assert(it->it_index < PyList_GET_SIZE(it->it_seq));
! 		item = PyList_GET_ITEM(it->it_seq, it->it_index);
  		it->it_index--;
  		Py_INCREF(item);
! 	} else if (it->it_seq != NULL) {
! 		Py_DECREF(it->it_seq);
  		it->it_seq = NULL;
  	}
! 	return item;
  }
  
  PyTypeObject PyListRevIter_Type = {
  	PyObject_HEAD_INIT(&PyType_Type)
--- 2794,2826 ----
  listreviter_next(listreviterobject *it)
  {
! 	PyObject *item;
! 	long index = it->it_index;
! 	PyListObject *seq = it->it_seq;
  
! 	if (index>=0 && index < PyList_GET_SIZE(seq)) {
! 		item = PyList_GET_ITEM(seq, index);
  		it->it_index--;
  		Py_INCREF(item);
! 		return item;
! 	}
! 	it->it_index = -1;
! 	if (seq != NULL) {
  		it->it_seq = NULL;
+ 		Py_DECREF(seq);
  	}
! 	return NULL;
! }
! 
! static int
! listreviter_len(listreviterobject *it)
! {
! 	return it->it_index + 1;
  }
  
+ static PySequenceMethods listreviter_as_sequence = {
+ 	(inquiry)listreviter_len,	/* sq_length */
+ 	0,				/* sq_concat */
+ };
+ 
  PyTypeObject PyListRevIter_Type = {
  	PyObject_HEAD_INIT(&PyType_Type)
***************
*** 2823,2827 ****
  	0,					/* tp_repr */
  	0,					/* tp_as_number */
! 	0,					/* tp_as_sequence */
  	0,					/* tp_as_mapping */
  	0,					/* tp_hash */
--- 2837,2841 ----
  	0,					/* tp_repr */
  	0,					/* tp_as_number */
! 	&listreviter_as_sequence,		/* tp_as_sequence */
  	0,					/* tp_as_mapping */
  	0,					/* tp_hash */

Index: rangeobject.c
===================================================================
RCS file: /cvsroot/python/python/dist/src/Objects/rangeobject.c,v
retrieving revision 2.49
retrieving revision 2.50
diff -C2 -d -r2.49 -r2.50
*** rangeobject.c	6 Nov 2003 14:06:47 -0000	2.49
--- rangeobject.c	10 Mar 2004 10:10:42 -0000	2.50
***************
*** 289,292 ****
--- 289,304 ----
  }
  
+ static int
+ rangeiter_len(rangeiterobject *r)
+ {
+ 	return r->len - r->index;
+ }
+ 
+ static PySequenceMethods rangeiter_as_sequence = {
+ 	(inquiry)rangeiter_len,		/* sq_length */
+ 	0,				/* sq_concat */
+ };
+ 
+ 
  static PyTypeObject Pyrangeiter_Type = {
  	PyObject_HEAD_INIT(&PyType_Type)
***************
*** 303,307 ****
  	0,                                      /* tp_repr */
  	0,                                      /* tp_as_number */
! 	0,                                      /* tp_as_sequence */
  	0,                                      /* tp_as_mapping */
  	0,                                      /* tp_hash */
--- 315,319 ----
  	0,                                      /* tp_repr */
  	0,                                      /* tp_as_number */
! 	&rangeiter_as_sequence,			/* tp_as_sequence */
  	0,                                      /* tp_as_mapping */
  	0,                                      /* tp_hash */




More information about the Python-checkins mailing list