Skip to content

Commit

Permalink
gh-107406: Add better struct.Struct repr (#107407)
Browse files Browse the repository at this point in the history
  • Loading branch information
denballakh committed Aug 26, 2023
1 parent 8ba4714 commit e407cea
Show file tree
Hide file tree
Showing 4 changed files with 29 additions and 0 deletions.
9 changes: 9 additions & 0 deletions Doc/library/struct.rst
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
:mod:`struct` --- Interpret bytes as packed binary data
=======================================================

.. testsetup:: *

from struct import *

.. module:: struct
:synopsis: Interpret bytes as packed binary data.

Expand Down Expand Up @@ -597,6 +601,11 @@ The :mod:`struct` module also defines the following type:
The calculated size of the struct (and hence of the bytes object produced
by the :meth:`pack` method) corresponding to :attr:`format`.

.. versionchanged:: 3.13 The *repr()* of structs has changed. It
is now:

>>> Struct('i')
Struct('i')

.. _half precision format: https://en.wikipedia.org/wiki/Half-precision_floating-point_format

Expand Down
4 changes: 4 additions & 0 deletions Lib/test/test_struct.py
Original file line number Diff line number Diff line change
Expand Up @@ -774,6 +774,10 @@ def test_error_propagation(fmt_str):
test_error_propagation('N')
test_error_propagation('n')

def test_repr(self):
s = struct.Struct('=i2H')
self.assertEqual(repr(s), f'Struct({s.format!r})')

class UnpackIteratorTest(unittest.TestCase):
"""
Tests for iterative unpacking (struct.Struct.iter_unpack).
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Implement new :meth:`__repr__` method for :class:`struct.Struct`.
Now it returns ``Struct(<format repr>)``.
14 changes: 14 additions & 0 deletions Modules/_struct.c
Original file line number Diff line number Diff line change
Expand Up @@ -2165,6 +2165,19 @@ s_sizeof(PyStructObject *self, void *unused)
return PyLong_FromSize_t(size);
}

static PyObject *
s_repr(PyStructObject *self)
{
PyObject* fmt = PyUnicode_FromStringAndSize(
PyBytes_AS_STRING(self->s_format), PyBytes_GET_SIZE(self->s_format));
if (fmt == NULL) {
return NULL;
}
PyObject* s = PyUnicode_FromFormat("%s(%R)", _PyType_Name(Py_TYPE(self)), fmt);
Py_DECREF(fmt);
return s;
}

/* List of functions */

static struct PyMethodDef s_methods[] = {
Expand Down Expand Up @@ -2197,6 +2210,7 @@ static PyType_Slot PyStructType_slots[] = {
{Py_tp_dealloc, s_dealloc},
{Py_tp_getattro, PyObject_GenericGetAttr},
{Py_tp_setattro, PyObject_GenericSetAttr},
{Py_tp_repr, s_repr},
{Py_tp_doc, (void*)s__doc__},
{Py_tp_traverse, s_traverse},
{Py_tp_clear, s_clear},
Expand Down

0 comments on commit e407cea

Please sign in to comment.