diff options
author | Raymond Hettinger <python@rcn.com> | 2004-03-08 18:17:31 (GMT) |
---|---|---|
committer | Raymond Hettinger <python@rcn.com> | 2004-03-08 18:17:31 (GMT) |
commit | 6ec099658ab49ed6d3c2861e437fe659e1c7037f (patch) | |
tree | 2a8f9f3e3192bba966382e4a473092d1f376f3f6 | |
parent | 73360a3e61274ffcc4c9fc3d09746bd6603e92a5 (diff) | |
download | cpython-6ec099658ab49ed6d3c2861e437fe659e1c7037f.zip cpython-6ec099658ab49ed6d3c2861e437fe659e1c7037f.tar.gz cpython-6ec099658ab49ed6d3c2861e437fe659e1c7037f.tar.bz2 |
SF patch #907403: Improvements to cStringIO.writelines()
The writelines() method now accepts any iterable argument and writes
the lines one at a time rather than using ''.join(lines) followed by
a single write. Results in considerable memory savings and makes
the method suitable for use with generator expressions.
-rw-r--r-- | Lib/StringIO.py | 6 | ||||
-rw-r--r-- | Modules/cStringIO.c | 51 |
2 files changed, 27 insertions, 30 deletions
diff --git a/Lib/StringIO.py b/Lib/StringIO.py index f35054e..9b79a88 100644 --- a/Lib/StringIO.py +++ b/Lib/StringIO.py @@ -178,8 +178,10 @@ class StringIO: self.len = newpos self.pos = newpos - def writelines(self, list): - self.write(''.join(list)) + def writelines(self, iterable): + write = self.write + for line in iterable: + write(line) def flush(self): _complain_ifclosed(self.closed) diff --git a/Modules/cStringIO.c b/Modules/cStringIO.c index 4ec5e88..1420bce 100644 --- a/Modules/cStringIO.c +++ b/Modules/cStringIO.c @@ -416,40 +416,35 @@ O_close(Oobject *self, PyObject *unused) { return Py_None; } - PyDoc_STRVAR(O_writelines__doc__, -"writelines(sequence_of_strings): write each string"); +"writelines(sequence_of_strings) -> None. Write the strings to the file.\n" +"\n" +"Note that newlines are not added. The sequence can be any iterable object\n" +"producing strings. This is equivalent to calling write() for each string."); static PyObject * O_writelines(Oobject *self, PyObject *args) { - PyObject *tmp = 0; - static PyObject *joiner = NULL; - - if (!joiner) { - PyObject *empty_string = PyString_FromString(""); - if (empty_string == NULL) + PyObject *it, *s; + + it = PyObject_GetIter(args); + if (it == NULL) + return NULL; + while ((s = PyIter_Next(it)) != NULL) { + int n; + char *c; + if (PyString_AsStringAndSize(s, &c, &n) == -1) { + Py_DECREF(it); + Py_DECREF(s); return NULL; - joiner = PyObject_GetAttrString(empty_string, "join"); - Py_DECREF(empty_string); - if (joiner == NULL) + } + if (O_cwrite((PyObject *)self, c, n) == -1) { + Py_DECREF(it); + Py_DECREF(s); return NULL; + } + Py_DECREF(s); } - - if (PyObject_Size(args) < 0) return NULL; - - args = PyTuple_Pack(1, args); - if (args == NULL) - return NULL; - tmp = PyObject_Call(joiner, args, NULL); - Py_DECREF(args); - UNLESS (tmp) return NULL; - - args = PyTuple_Pack(1, tmp); - Py_DECREF(tmp); - UNLESS (args) return NULL; - - tmp = O_write(self, args); - Py_DECREF(args); - return tmp; + Py_DECREF(it); + Py_RETURN_NONE; } static struct PyMethodDef O_methods[] = { |