From 63c883dd18f1f4fc7d1d9420a173af9bd4281ce0 Mon Sep 17 00:00:00 2001 From: Raymond Hettinger Date: Sun, 7 Oct 2018 15:44:21 -0700 Subject: [PATCH 1/4] Speed-up bisect_right --- Modules/_bisectmodule.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/Modules/_bisectmodule.c b/Modules/_bisectmodule.c index 831e10aa6078bb..4001975fa160d5 100644 --- a/Modules/_bisectmodule.c +++ b/Modules/_bisectmodule.c @@ -53,9 +53,14 @@ bisect_right(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:bisect_right", - keywords, &list, &item, &lo, &hi)) - return NULL; + if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + list = PyTuple_GET_ITEM(args, 0); + item = PyTuple_GET_ITEM(args, 1); + } else { + if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:bisect_right", + keywords, &list, &item, &lo, &hi)) + return NULL; + } index = internal_bisect_right(list, item, lo, hi); if (index < 0) return NULL; From 933a8d9d2e9170b5ae819b0b27e6fbd81faefdc6 Mon Sep 17 00:00:00 2001 From: Raymond Hettinger Date: Sun, 7 Oct 2018 15:56:21 -0700 Subject: [PATCH 2/4] Optimize remaining functions --- Modules/_bisectmodule.c | 37 ++++++++++++++++++++++++++----------- 1 file changed, 26 insertions(+), 11 deletions(-) diff --git a/Modules/_bisectmodule.c b/Modules/_bisectmodule.c index 4001975fa160d5..a2f6389fc7b749 100644 --- a/Modules/_bisectmodule.c +++ b/Modules/_bisectmodule.c @@ -8,7 +8,7 @@ Converted to C by Dmitry Vasiliev (dima at hlabs.spb.ru). _Py_IDENTIFIER(insert); -static Py_ssize_t +static inline Py_ssize_t internal_bisect_right(PyObject *list, PyObject *item, Py_ssize_t lo, Py_ssize_t hi) { PyObject *litem; @@ -88,9 +88,14 @@ insort_right(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:insort_right", - keywords, &list, &item, &lo, &hi)) - return NULL; + if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + list = PyTuple_GET_ITEM(args, 0); + item = PyTuple_GET_ITEM(args, 1); + } else { + if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:insort_right", + keywords, &list, &item, &lo, &hi)) + return NULL; + } index = internal_bisect_right(list, item, lo, hi); if (index < 0) return NULL; @@ -117,7 +122,7 @@ If x is already in a, insert it to the right of the rightmost x.\n\ Optional args lo (default 0) and hi (default len(a)) bound the\n\ slice of a to be searched.\n"); -static Py_ssize_t +static inline Py_ssize_t internal_bisect_left(PyObject *list, PyObject *item, Py_ssize_t lo, Py_ssize_t hi) { PyObject *litem; @@ -162,9 +167,14 @@ bisect_left(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:bisect_left", - keywords, &list, &item, &lo, &hi)) - return NULL; + if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + list = PyTuple_GET_ITEM(args, 0); + item = PyTuple_GET_ITEM(args, 1); + } else { + if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:bisect_left", + keywords, &list, &item, &lo, &hi)) + return NULL; + } index = internal_bisect_left(list, item, lo, hi); if (index < 0) return NULL; @@ -192,9 +202,14 @@ insort_left(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:insort_left", - keywords, &list, &item, &lo, &hi)) - return NULL; + if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + list = PyTuple_GET_ITEM(args, 0); + item = PyTuple_GET_ITEM(args, 1); + } else { + if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:insort_left", + keywords, &list, &item, &lo, &hi)) + return NULL; + } index = internal_bisect_left(list, item, lo, hi); if (index < 0) return NULL; From b7699a1e2432b0ce0a5751dba1d1cccd645bddba Mon Sep 17 00:00:00 2001 From: Raymond Hettinger Date: Sun, 7 Oct 2018 20:37:24 -0700 Subject: [PATCH 3/4] Add news blurb --- .../NEWS.d/next/Library/2018-10-07-20-37-02.bpo-34925.KlkZ-Y.rst | 1 + 1 file changed, 1 insertion(+) create mode 100644 Misc/NEWS.d/next/Library/2018-10-07-20-37-02.bpo-34925.KlkZ-Y.rst diff --git a/Misc/NEWS.d/next/Library/2018-10-07-20-37-02.bpo-34925.KlkZ-Y.rst b/Misc/NEWS.d/next/Library/2018-10-07-20-37-02.bpo-34925.KlkZ-Y.rst new file mode 100644 index 00000000000000..b7853684a959f1 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2018-10-07-20-37-02.bpo-34925.KlkZ-Y.rst @@ -0,0 +1 @@ +25% speedup in argument parsing for the functions in the bisect module. From fd687e4311976b6400b7a0c07305e88748df49d3 Mon Sep 17 00:00:00 2001 From: Raymond Hettinger Date: Mon, 8 Oct 2018 07:19:39 -0700 Subject: [PATCH 4/4] PEP 7 nits --- Modules/_bisectmodule.c | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/Modules/_bisectmodule.c b/Modules/_bisectmodule.c index a2f6389fc7b749..7dd73f94750b3d 100644 --- a/Modules/_bisectmodule.c +++ b/Modules/_bisectmodule.c @@ -53,10 +53,11 @@ bisect_right(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + if (kw == NULL && PyTuple_GET_SIZE(args) == 2) { list = PyTuple_GET_ITEM(args, 0); item = PyTuple_GET_ITEM(args, 1); - } else { + } + else { if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:bisect_right", keywords, &list, &item, &lo, &hi)) return NULL; @@ -88,10 +89,11 @@ insort_right(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + if (kw == NULL && PyTuple_GET_SIZE(args) == 2) { list = PyTuple_GET_ITEM(args, 0); item = PyTuple_GET_ITEM(args, 1); - } else { + } + else { if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:insort_right", keywords, &list, &item, &lo, &hi)) return NULL; @@ -102,7 +104,8 @@ insort_right(PyObject *self, PyObject *args, PyObject *kw) if (PyList_CheckExact(list)) { if (PyList_Insert(list, index, item) < 0) return NULL; - } else { + } + else { result = _PyObject_CallMethodId(list, &PyId_insert, "nO", index, item); if (result == NULL) return NULL; @@ -167,10 +170,11 @@ bisect_left(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + if (kw == NULL && PyTuple_GET_SIZE(args) == 2) { list = PyTuple_GET_ITEM(args, 0); item = PyTuple_GET_ITEM(args, 1); - } else { + } + else { if (!PyArg_ParseTupleAndKeywords(args, kw, "OO|nn:bisect_left", keywords, &list, &item, &lo, &hi)) return NULL; @@ -202,7 +206,7 @@ insort_left(PyObject *self, PyObject *args, PyObject *kw) Py_ssize_t index; static char *keywords[] = {"a", "x", "lo", "hi", NULL}; - if (kw==NULL && PyTuple_GET_SIZE(args)==2) { + if (kw == NULL && PyTuple_GET_SIZE(args) == 2) { list = PyTuple_GET_ITEM(args, 0); item = PyTuple_GET_ITEM(args, 1); } else {