Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Apply the more trivial suggestions from code review
I'll address the other ones in a separate commit(s)

Co-authored-by: Hugo van Kemenade <[email protected]>
  • Loading branch information
jb2170 and hugovk authored May 16, 2025
commit d7d9cf0f00677bfae4a5361d4ab15e3f4e7af9b9
1 change: 0 additions & 1 deletion .github/CODEOWNERS
Original file line number Diff line number Diff line change
Expand Up @@ -664,7 +664,6 @@ peps/pep-0783.rst @hoodmane @ambv
peps/pep-0784.rst @gpshead
peps/pep-0785.rst @gpshead
peps/pep-0786.rst @ncoghlan
# ...
peps/pep-0787.rst @ncoghlan
peps/pep-0788.rst @ZeroIntensity @vstinner
# ...
Expand Down
18 changes: 9 additions & 9 deletions peps/pep-0786.rst
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
PEP: 786
Title: Precision and Modulo-Precision Flag format specifiers for integer fields
Title: Precision and modulo-precision flag format specifiers for integer fields
Author: Jay Berry <[email protected]>
Sponsor: Alyssa Coghlan <[email protected]>
Status: Draft
Expand All @@ -22,7 +22,7 @@ This PEP amends the clause of :pep:`3101` which states "[t]he precision is ignor
Rationale
=========

When string formatting integers in binary octal and hexadecimal, one often desires the resulting string to contain a guaranteed minimum number of digits. For unsigned integers of known machine-width bounds (eg 8 bit bytes) this often also ends up the exact resulting number of digits. This has previously been implemented in the old-style ``%`` formatting using the ``.`` "precision" format specifier, closely related to that of the C programming language.
When string formatting integers in binary octal and hexadecimal, one often desires the resulting string to contain a guaranteed minimum number of digits. For unsigned integers of known machine-width bounds (for example, 8-bit bytes) this often also ends up the exact resulting number of digits. This has previously been implemented in the old-style ``%`` formatting using the ``.`` "precision" format specifier, closely related to that of the C programming language.

.. code-block:: python

Expand All @@ -31,7 +31,7 @@ When string formatting integers in binary octal and hexadecimal, one often desir
>>> "0o%.3o" % 18
'0o022' # three octal digits, ideal for displaying a umask or file permissions

When :pep:`3101` new-style formatting was first introduced, used in ``str.format`` and ``f``\ strings, the `format specification <formatspec_>`_ was simple enough that the behavior of "precision" could be trivially emulated with the ``width`` format specifier. Precision therefore was left unimplemented and forbidden for ``int`` fields. However, as time has progressed and new format specifiers have been added, whose interactions with ``width`` noticeably diverge its behavior away from emulating precision, the readmission of precision as its own format specifier, ``.``, is sufficiently warranted.
When :pep:`3101` new-style formatting was first introduced, used in ``str.format`` and f-strings, the `format specification <formatspec_>`_ was simple enough that the behavior of "precision" could be trivially emulated with the ``width`` format specifier. Precision therefore was left unimplemented and forbidden for ``int`` fields. However, as time has progressed and new format specifiers have been added, whose interactions with ``width`` noticeably diverge its behavior away from emulating precision, the readmission of precision as its own format specifier, ``.``, is sufficiently warranted.

The ``width`` format specifier guarantees a minimum length of the entire replacement field, not just the number of digits in a formatted integer. For example, the wonderful ``#`` specifier that prepends the prefix of the corresponding presentation type consumes from ``width``:

Expand All @@ -54,7 +54,7 @@ One could attempt to argue that since the length of a prefix is known to always

It is clear at this point that the reduction of complexity that would be provided by precision's implementation for ``int`` fields would be beneficial to any user. Nor is this proposal a new special-case behavior being demanded exclusively at the behest of ``int`` fields: the precision token ``.`` is already implemented as prescribed in :pep:`3101` for ``str`` data to truncate the field's length, and for ``float`` data to ensure that there are a fixed number of digits after the decimal point, eg ``f"{0.1+0.2: .4f}"`` producing ``' 0.3000'``. Thus no new tokens need adding to the `format specification <formatspec_>`_ because of this proposal, maintaining its modest size.

For the sake of completion, and lack of any reasonable objection, we propose that precision shall work also in decimal, base 10. Explicitly, the integer presentation types laid out in :pep:`3101` that are permitted to implement precision are ``'b'``, ``'d'``, ``'o'``, ``'x'``, ``'X'``, ``'n'``, and ``'' (None)``. The only presentation type not permitted is ``c`` ('character'), whose purpose is to format an integer to a single Unicode character, or an appropriate replacement for non-printable characters, for which it does not make sense to implement precision. In the event that new integer presentation types are added in the future, such as ``'B'`` and ``'O'`` which mutatis-mutandis could provide the same behavior as ``'X'`` (that is a capitalized prefix and digits), their addition should appropriately consider whether precision should be implemented or not. In the case of ``'B'`` and ``'O'`` as described here it would be correct to implement precision. A ``ValueError`` shall be raised when precision is attempted to be used for invalid integer presentation types.
For the sake of completion, and lack of any reasonable objection, we propose that precision shall work also in decimal, base 10. Explicitly, the integer presentation types laid out in :pep:`3101` that are permitted to implement precision are ``'b'``, ``'d'``, ``'o'``, ``'x'``, ``'X'``, ``'n'``, and ``''`` (``None``). The only presentation type not permitted is ``c`` ('character'), whose purpose is to format an integer to a single Unicode character, or an appropriate replacement for non-printable characters, for which it does not make sense to implement precision. In the event that new integer presentation types are added in the future, such as ``'B'`` and ``'O'`` which mutatis-mutandis could provide the same behavior as ``'X'`` (that is a capitalized prefix and digits), their addition should appropriately consider whether precision should be implemented or not. In the case of ``'B'`` and ``'O'`` as described here it would be correct to implement precision. A ``ValueError`` shall be raised when precision is attempted to be used for invalid integer presentation types.


Precision For Negative Numbers
Expand Down Expand Up @@ -166,7 +166,7 @@ A final compromise to consider and reject is implementing ``z`` not as a flag *d
Infinite Length Indication
''''''''''''''''''''''''''

Another, less popular, rejected alternative was for ``z`` to directly acknowledge the infinite prefix of ``0``\ s or ``1``\ s that precede a non-negative or negative number respectively. For example
Another, less popular, rejected alternative was for ``z`` to directly acknowledge the infinite prefix of ``0``\ s or ``1``\ s that precede a non-negative or negative number respectively. For example:

.. code-block:: python

Expand Down Expand Up @@ -199,7 +199,7 @@ Python's ``int`` type is indeed not limited by a maximum machine-width. Thus to
>>> f"{y:z#.8b}"
'0b[...1]11111111'

This may have been useful to educate beginner users on how bitwise binary operations work, for example showing how ``-1 & x`` is always trivially equal to ``x``, or how the binary representation of the negation of a number can be obtained by adding one to its bitwise complement:
This may have been useful to educate beginners on how bitwise binary operations work, for example showing how ``-1 & x`` is always trivially equal to ``x``, or how the binary representation of the negation of a number can be obtained by adding one to its bitwise complement:

.. code-block:: python

Expand Down Expand Up @@ -264,11 +264,11 @@ Syntax
Backwards Compatibility
=======================

To quote :pep:`682`
To quote :pep:`682`:

The new formatting behavior is opt-in, so numerical formatting of existing programs will not be affected
The new formatting behavior is opt-in, so numerical formatting of existing programs will not be affected.

unless someone out there is specifically relying upon ``.`` raising a ``ValueError`` for integers as it currently does, but to quote :pep:`475`
unless someone out there is specifically relying upon ``.`` raising a ``ValueError`` for integers as it currently does, but to quote :pep:`475`:

The authors of this PEP don't think that such applications exist

Expand Down