Small changes to map() and filter():
(1) If a sequence S is shorter than len(S) indicated, don't fail -- just use the shorter size. (I.e, len(S) is just a hint.) (2) Implement the special case map(None, S) as list(S) -- it's faster.
This commit is contained in:
parent
bfc725bf64
commit
fa4ac71dd6
|
@ -190,8 +190,6 @@ builtin_filter(self, args)
|
|||
int ok;
|
||||
|
||||
if ((item = (*sqf->sq_item)(seq, i)) == NULL) {
|
||||
if (i < len)
|
||||
goto Fail_1;
|
||||
if (PyErr_ExceptionMatches(PyExc_IndexError)) {
|
||||
PyErr_Clear();
|
||||
break;
|
||||
|
@ -784,6 +782,11 @@ builtin_map(self, args)
|
|||
func = PyTuple_GetItem(args, 0);
|
||||
n--;
|
||||
|
||||
if (func == Py_None && n == 1) {
|
||||
/* map(None, S) is the same as list(S). */
|
||||
return PySequence_List(PyTuple_GetItem(args, 1));
|
||||
}
|
||||
|
||||
if ((seqs = PyMem_NEW(sequence, n)) == NULL) {
|
||||
PyErr_NoMemory();
|
||||
goto Fail_2;
|
||||
|
@ -820,7 +823,6 @@ builtin_map(self, args)
|
|||
if ((result = (PyObject *) PyList_New(len)) == NULL)
|
||||
goto Fail_2;
|
||||
|
||||
/* XXX Special case map(None, single_list) could be more efficient */
|
||||
for (i = 0; ; ++i) {
|
||||
PyObject *alist, *item=NULL, *value;
|
||||
int any = 0;
|
||||
|
@ -840,8 +842,6 @@ builtin_map(self, args)
|
|||
else {
|
||||
item = (*sqp->sqf->sq_item)(sqp->seq, i);
|
||||
if (item == NULL) {
|
||||
if (i < sqp->len)
|
||||
goto Fail_0;
|
||||
if (PyErr_ExceptionMatches(
|
||||
PyExc_IndexError))
|
||||
{
|
||||
|
@ -897,6 +897,9 @@ builtin_map(self, args)
|
|||
}
|
||||
}
|
||||
|
||||
if (i < len && PyList_SetSlice(result, i, len, NULL) < 0)
|
||||
goto Fail_1;
|
||||
|
||||
PyMem_DEL(seqs);
|
||||
return result;
|
||||
|
||||
|
|
Loading…
Reference in New Issue