[Python-checkins] python/nondist/sandbox/itertools itertools.c,1.2,1.3 libitertools.tex,1.3,1.4 test_itertools.py,1.1,1.2 todo.txt,1.3,1.4
rhettinger@users.sourceforge.net
rhettinger@users.sourceforge.net
Sun, 26 Jan 2003 20:24:16 -0800
- Previous message: [Python-checkins] python/nondist/sandbox/pickletools pickletools.py,1.29,1.30
- Next message: [Python-checkins] python/nondist/sandbox/itertools itertools.c,1.3,1.4 libitertools.tex,1.4,1.5 test_itertools.py,1.2,1.3 todo.txt,1.4,1.5
- Messages sorted by:
[ date ]
[ thread ]
[ subject ]
[ author ]
Update of /cvsroot/python/python/nondist/sandbox/itertools
In directory sc8-pr-cvs1:/tmp/cvs-serv10416
Modified Files:
itertools.c libitertools.tex test_itertools.py todo.txt
Log Message:
Added imap()
Index: itertools.c
===================================================================
RCS file: /cvsroot/python/python/nondist/sandbox/itertools/itertools.c,v
retrieving revision 1.2
retrieving revision 1.3
diff -C2 -d -r1.2 -r1.3
*** itertools.c 27 Jan 2003 00:27:41 -0000 1.2
--- itertools.c 27 Jan 2003 04:24:14 -0000 1.3
***************
*** 2,5 ****
--- 2,161 ----
#include "Python.h"
+ /* imap object ************************************************************/
+
+ typedef struct {
+ PyObject_HEAD
+ PyObject *iters;
+ PyObject *argtuple;
+ PyObject *func;
+ } imapobject;
+
+ PyTypeObject imap_type;
+
+ static PyObject *
+ imap_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
+ {
+ PyObject *it, *iters, *argtuple;
+ imapobject *lz;
+ int numargs, i;
+
+ numargs = PyTuple_Size(args);
+ if (numargs == 0) {
+ // XXX raise Err for not having a function arg
+ return NULL;
+ }
+
+ iters = PyTuple_New(numargs-1);
+ if (iters == NULL)
+ return NULL;
+
+ argtuple = PyTuple_New(numargs-1);
+ if (argtuple == NULL) {
+ Py_DECREF(iters);
+ return NULL;
+ }
+
+ for (i=1 ; i<numargs ; i++) {
+ /* Get iterator. */
+ it = PyObject_GetIter(PyTuple_GET_ITEM(args, i));
+ if (it == NULL) {
+ Py_DECREF(argtuple);
+ Py_DECREF(iters);
+ return NULL;
+ }
+ PyTuple_SET_ITEM(iters, i-1, it);
+ }
+
+ /* create imapobject structure */
+ lz = (imapobject *)type->tp_alloc(type, 0);
+ if (lz == NULL) {
+ Py_DECREF(argtuple);
+ Py_DECREF(iters);
+ return NULL;
+ }
+ lz->iters = iters;
+ lz->argtuple = argtuple;
+ lz->func = PyTuple_GET_ITEM(args, 0);
+
+ return (PyObject *)lz;
+ }
+
+ static void
+ imap_dealloc(imapobject *lz)
+ {
+ PyObject_GC_UnTrack(lz);
+ //Py_XDECREF(lz->argtuple);
+ //Py_XDECREF(lz->iters);
+ lz->ob_type->tp_free(lz);
+ }
+
+ static int
+ imap_traverse(imapobject *lz, visitproc visit, void *arg)
+ {
+ if (lz->argtuple)
+ return visit(lz->argtuple, arg);
+ return 0;
+ }
+
+ static PyObject *
+ imap_next(imapobject *lz)
+ {
+ PyObject *val;
+ PyObject *iters=lz->iters, *argtuple=lz->argtuple;
+ int numargs, i;
+
+ numargs = PyTuple_Size(lz->iters);
+
+ for (i=0 ; i<numargs ; i++) {
+ val = PyIter_Next(PyTuple_GET_ITEM(lz->iters, i));
+ if (val == NULL)
+ return NULL;
+ PyTuple_SET_ITEM(argtuple, i, val);
+ }
+ return PyObject_Call(lz->func, argtuple, NULL);
+ }
+
+ static PyObject *
+ imap_getiter(PyObject *lz)
+ {
+ Py_INCREF(lz);
+ return lz;
+ }
+
+ PyDoc_STRVAR(imap_doc,
+ "imap(func, *iterables) --> imap object\n\
+ \n\
+ Make an iterator that computes the function using arguments from\n\
+ each of the iterables. Like map() except 1) that it returns\n\
+ an iterator instead of a list, 2) that it stops when the shortest\n\
+ iterable is exhausted instead of filling in None for shorter\n\
+ iterables, and 3) that it does not accept None for func.");
+
+ PyTypeObject imap_type = {
+ PyObject_HEAD_INIT(NULL)
+ 0, /* ob_size */
+ "itertools.imap", /* tp_name */
+ sizeof(imapobject), /* tp_basicsize */
+ 0, /* tp_itemsize */
+ /* methods */
+ (destructor)imap_dealloc, /* tp_dealloc */
+ 0, /* tp_print */
+ 0, /* tp_getattr */
+ 0, /* tp_setattr */
+ 0, /* tp_compare */
+ 0, /* 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 | Py_TPFLAGS_HAVE_GC |
+ Py_TPFLAGS_BASETYPE, /* tp_flags */
+ imap_doc, /* tp_doc */
+ (traverseproc)imap_traverse, /* tp_traverse */
+ 0, /* tp_clear */
+ 0, /* tp_richcompare */
+ 0, /* tp_weaklistoffset */
+ (getiterfunc)imap_getiter, /* tp_iter */
+ (iternextfunc)imap_next, /* tp_iternext */
+ 0, /* tp_methods */
+ 0, /* 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 */
+ PyType_GenericAlloc, /* tp_alloc */
+ imap_new, /* tp_new */
+ PyObject_GC_Del, /* tp_free */
+ };
+
+
/* times object ************************************************************/
***************
*** 195,199 ****
PyDoc_STRVAR(ifilter_doc,
! "filter(function or None, sequence [, invert]) --> ifilter object\n\
\n\
Return those items of sequence for which function(item) is true. If\n\
--- 351,355 ----
PyDoc_STRVAR(ifilter_doc,
! "ifilter(function or None, sequence [, invert]) --> ifilter object\n\
\n\
Return those items of sequence for which function(item) is true. If\n\
***************
*** 648,655 ****
m = Py_InitModule3("itertools", NULL, module_doc);
if (PyType_Ready(×_type) < 0)
return;
Py_INCREF(×_type);
- PyModule_AddObject(m, "times", (PyObject *)×_type);
if (PyType_Ready(&ifilter_type) < 0)
--- 804,816 ----
m = Py_InitModule3("itertools", NULL, module_doc);
+ PyModule_AddObject(m, "imap", (PyObject *)&imap_type);
+ if (PyType_Ready(&imap_type) < 0)
+ return;
+ Py_INCREF(&imap_type);
+
+ PyModule_AddObject(m, "times", (PyObject *)×_type);
if (PyType_Ready(×_type) < 0)
return;
Py_INCREF(×_type);
if (PyType_Ready(&ifilter_type) < 0)
Index: libitertools.tex
===================================================================
RCS file: /cvsroot/python/python/nondist/sandbox/itertools/libitertools.tex,v
retrieving revision 1.3
retrieving revision 1.4
diff -C2 -d -r1.3 -r1.4
*** libitertools.tex 27 Jan 2003 01:35:20 -0000 1.3
--- libitertools.tex 27 Jan 2003 04:24:14 -0000 1.4
***************
*** 27,31 ****
\code{imap(\var{f}, count())} and produce an equivalent result.
-
\item Some tools were dropped because they offer no advantage over their
pure python counterparts or because their behavior was too
--- 27,30 ----
***************
*** 44,48 ****
being written in C is its speed advantage.
! For instance, Python's
\module{__builtins__} module has an easy-to-use, no surprises version
of \function(zip()). This module's corresponding function,
--- 43,47 ----
being written in C is its speed advantage.
! For instance, the
\module{__builtins__} module has an easy-to-use, no surprises version
of \function(zip()). This module's corresponding function,
***************
*** 57,62 ****
one output list (saving the time to allocate and build a tuple on
every pass). Though very fast, using \function{loopzip()} outside of
! a \keyword{for} loop can result in surprising behavior and an
! unwelcome refresher lesson in mutability.
\item Another source of value comes from standardizing a core set of tools
--- 56,61 ----
one output list (saving the time to allocate and build a tuple on
every pass). Though very fast, using \function{loopzip()} outside of
! a \keyword{for} loop or other itertool can result in surprising
! behavior and an unwelcome refresher lesson in mutability.
\item Another source of value comes from standardizing a core set of tools
***************
*** 107,110 ****
--- 106,126 ----
\end{funcdesc}
+ \begin{funcdesc}{imap}{func, *iterables}
+ Make an iterator that computes the function using arguments from
+ each of the iterables. Like \function{map()} except 1) that it returns
+ an iterator instead of a list, 2) that it stops when the shortest
+ iterable is exhausted instead of filling in \code{None} for shorter
+ iterables, and 3) that it does not accept \code{None} for \var{func}.
+ Equivalent to:
+
+ \begin{verbatim}
+ def imap(func, *iterables):
+ iterables = map(iter, iterables)
+ while True:
+ args = [i.next() for i in iterables]
+ yield f(*args)
+ \end{verbatim}
+ \end{funcdesc}
+
\begin{funcdesc}{loopzip}{*iterables}
Make an iterator that aggregates elements from each of the iterables.
***************
*** 184,192 ****
\begin{verbatim}
! >>> enumerate = lambda s: izip(count(), s)
! >>> tabulate = lambda f: imap(f, count())
! >>> iteritems = lambda d: izip(d.iterkeys(), d.itervalues())
! >>> repeat = lambda o: cycle([o])
! >>> nth = lambda s, n: islice(n, n+1).next()
\end{verbatim}
--- 200,211 ----
\begin{verbatim}
! >>> def enumerate(s):
! ... return izip(count(), s)
! >>> def tabulate(f):
! ... return imap(f, count())
! >>> def iteritems(d):
! ... return izip(d.iterkeys(), d.itervalues())
! >>> def nth(s, n):
! ... return islice(n, n+1).next()
\end{verbatim}
Index: test_itertools.py
===================================================================
RCS file: /cvsroot/python/python/nondist/sandbox/itertools/test_itertools.py,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** test_itertools.py 27 Jan 2003 00:16:51 -0000 1.1
--- test_itertools.py 27 Jan 2003 04:24:14 -0000 1.2
***************
*** 20,29 ****
def test_repeat(self):
! self.assertEqual(zip(xrange(3),repeat('a')), [(0, 'a'), (1, 'a'), (2, 'a')])
def test_times(self):
self.assertEqual(list(times(3)), [None]*3)
!
def test_main():
suite = unittest.TestSuite()
--- 20,34 ----
def test_repeat(self):
! self.assertEqual(zip(xrange(3),repeat('a')),
! [(0, 'a'), (1, 'a'), (2, 'a')])
def test_times(self):
self.assertEqual(list(times(3)), [None]*3)
! def test_imap(self):
! import operator
! self.assertEqual(list(imap(operator.pow, range(3), range(1,7))),
! [0**1, 1**2, 2**3])
!
def test_main():
suite = unittest.TestSuite()
Index: todo.txt
===================================================================
RCS file: /cvsroot/python/python/nondist/sandbox/itertools/todo.txt,v
retrieving revision 1.3
retrieving revision 1.4
diff -C2 -d -r1.3 -r1.4
*** todo.txt 27 Jan 2003 01:35:21 -0000 1.3
--- todo.txt 27 Jan 2003 04:24:14 -0000 1.4
***************
*** 1,5 ****
Add:
islice(iterator, start, stop, step)
- imap(func, iter1, iter2, ...)
iapply
starmap()
--- 1,4 ----
- Previous message: [Python-checkins] python/nondist/sandbox/pickletools pickletools.py,1.29,1.30
- Next message: [Python-checkins] python/nondist/sandbox/itertools itertools.c,1.3,1.4 libitertools.tex,1.4,1.5 test_itertools.py,1.2,1.3 todo.txt,1.4,1.5
- Messages sorted by:
[ date ]
[ thread ]
[ subject ]
[ author ]