Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

PEP 378: Format Specifier for Thousands Separator

87 views
Skip to first unread message

Carlos Nepomuceno

unread,
May 21, 2013, 1:17:36 AM5/21/13
to pytho...@python.org
Is there a way to format integers with thousands separator (digit grouping) like the format specifier of str.format()?

I'm currently using the following:

>>> sys.stdout.write('Number = %s\n' % '{:,.0f}'.format(x))
Number = 12,345

'x' is unsigned integer so it's like using a sledgehammer to crack a nut!

I'd like to have something like:

sys.stdout.write('Number = %,u\n' % x)


Is that possible? How can I do it if not already available?

Ned Deily

unread,
May 21, 2013, 1:44:08 AM5/21/13
to pytho...@python.org
In article <BLU176-W10190CB89...@phx.gbl>,
For Python 3.2+ or 2.7, why not just:

>>> print('Number = {:,}'.format(x))
Number = 12,345

--
Ned Deily,
n...@acm.org

Alysson Bruno

unread,
May 21, 2013, 8:03:13 AM5/21/13
to pytho...@python.org
This work in 3.1+:

$ python3
Python 3.1.3 (r313:86834, Nov 28 2010, 11:28:10)
[GCC 4.4.5] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> one_number = 1234567
>>> print('number={:,}'.format(one_number))
number=1,234,567
>>>


paz e amor (love and peace),

Alysson Bruno
===============================================
Palmas(TO)
Brasil

Blog: http://abruno.com


=================================================================
Meu alterego Escritor:

Leia alguns contos que escrevo, não esqueça de me dar sua opinião: http://goo.gl/Wjn4p

=================================================================


Carlos Nepomuceno

unread,
May 21, 2013, 2:49:28 PM5/21/13
to pytho...@python.org
________________________________
> From: alysso...@gmail.com
> Date: Tue, 21 May 2013 09:03:13 -0300
> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> To: pytho...@python.org
>
> This work in 3.1+:
>
> $ python3
> Python 3.1.3 (r313:86834, Nov 28 2010, 11:28:10)
> [GCC 4.4.5] on linux2
> Type "help", "copyright", "credits" or "license" for more information.
> >>> one_number = 1234567
> >>> print('number={:,}'.format(one_number))
> number=1,234,567
> >>>
>

Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.

I've looked into the source code of CPython 2.7.5 and I've found no evidence of the thousands separator been implemented on formatint() in "Objects/unicodeobject.c".

I also didn't find the _PyString_FormatLong() used in formatlong(). Where is _PyString_FormatLong() located?

So, the question is: Where would I change the CPython 2.7.5 source code to enable '%' (BINARY_MODULO) to format using the thousands separator like str.format() does, such as:

>>>sys.stderr.write('%,d\n' % 1234567)
1,234,567

Chris “Kwpolska” Warrick

unread,
May 21, 2013, 3:06:11 PM5/21/13
to Carlos Nepomuceno, pytho...@python.org
On Tue, May 21, 2013 at 8:49 PM, Carlos Nepomuceno
<carlosne...@outlook.com> wrote:
> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.

There is no real reason to do this. `str.format()` is the new shiny
thing you should be using all the time. Also, '%' is BINARY_MODULO
(where did you even get that name from?) if and only if you have two
numbers, and it performs the modulo division (eg. 27 % 5 = 2)

> So, the question is: Where would I change the CPython 2.7.5 source code to enable '%' (BINARY_MODULO) to format using the thousands separator like str.format() does, such as:
>
>>>>sys.stderr.write('%,d\n' % 1234567)
> 1,234,567

This will make your code unportable and useless, depending on one
patch you made. Please don’t do that. Instead,

> >>> sys.stdout.write('Number = %s\n' % '{:,.0f}'.format(x))
> Number = 12,345
>
> 'x' is unsigned integer so it's like using a sledgehammer to crack a nut!

In Python? Tough luck, every int is signed. And it isn’t just a
sledgehammer, it’s something worse. Just do that:

>>> sys.stdout.write('Number = {:,.0f}\n'.format(x))

Much more peaceful.

You can also do a print, like everyone sane would. Where did you
learn Python from? “Python Worst Practice for Dummies”?

--
Kwpolska <http://kwpolska.tk> | GPG KEY: 5EAAEA16
stop html mail | always bottom-post
http://asciiribbon.org | http://caliburn.nl/topposting.html

Skip Montanaro

unread,
May 21, 2013, 3:13:05 PM5/21/13
to Carlos Nepomuceno, pytho...@python.org
> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.

That's unlikely to change. If not deprecated already string
interpolation using the modulo operator has lost favor to the string
object's format method.

You might be able to get by with a change of your LOCALE setting
and/or a peek at the documentation for the locale module.

Skip

Mark Lawrence

unread,
May 21, 2013, 3:26:41 PM5/21/13
to pytho...@python.org
On 21/05/2013 20:13, Skip Montanaro wrote:
>> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.
>
> That's unlikely to change. If not deprecated already string
> interpolation using the modulo operator has lost favor to the string
> object's format method.
>

Please stop perpetuating this myth, see
http://mail.python.org/pipermail/python-dev/2012-February/116789.html
and http://bugs.python.org/issue14123

--
If you're using GoogleCrap� please read this
http://wiki.python.org/moin/GoogleGroupsPython.

Mark Lawrence

Carlos Nepomuceno

unread,
May 21, 2013, 3:39:35 PM5/21/13
to pytho...@python.org
----------------------------------------
> From: kwpo...@gmail.com
> Date: Tue, 21 May 2013 21:06:11 +0200

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> To: carlosne...@outlook.com
> CC: pytho...@python.org

>
> On Tue, May 21, 2013 at 8:49 PM, Carlos Nepomuceno
> <carlosne...@outlook.com> wrote:
>> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.
>
> There is no real reason to do this. `str.format()` is the new shiny
> thing you should be using all the time. Also, '%' is BINARY_MODULO
> (where did you even get that name from?) if and only if you have two
> numbers, and it performs the modulo division (eg. 27 % 5 = 2)

I did:

>>> def fmt(s):
...     return '%s' % s
...
>>> import dis
>>> dis.dis(fmt)
  2           0 LOAD_CONST               1 ('%s')
              3 LOAD_FAST                0 (s)
              6 BINARY_MODULO
              7 RETURN_VALUE
>>>

Then I've looked for 'BINARY_MODULO' in "Python/ceval.c" and found:

        case BINARY_MODULO:
            w = POP();
            v = TOP();
            if (PyString_CheckExact(v))
                x = PyString_Format(v, w);
            else
                x = PyNumber_Remainder(v, w);


Then I've looked for 'PyString_Format' and found it in "Objects/stringobject.c"

Analysing the code of "stringobject.c" I've found formatint() and formatlong().

I'm not using str.format() because it's slower than '%' and because I love '%'. str.format() looks like Java shit to me!

>> So, the question is: Where would I change the CPython 2.7.5 source code to enable '%' (BINARY_MODULO) to format using the thousands separator like str.format() does, such as:
>>
>>>>>sys.stderr.write('%,d\n' % 1234567)
>> 1,234,567
>
> This will make your code unportable and useless, depending on one
> patch you made. Please don’t do that. Instead,

I'm just learning how to improve things! ;)

>>>>> sys.stdout.write('Number = %s\n' % '{:,.0f}'.format(x))
>> Number = 12,345
>>
>> 'x' is unsigned integer so it's like using a sledgehammer to crack a nut!
>
> In Python? Tough luck, every int is signed. And it isn’t just a
> sledgehammer, it’s something worse. Just do that:
>
>>>> sys.stdout.write('Number = {:,.0f}\n'.format(x))
>
> Much more peaceful.

Indeed! I just cut and pasted my code to create an example for the message. The actual format operation isn't done at the sys.stdout.write().

> You can also do a print, like everyone sane would. Where did you
> learn Python from? “Python Worst Practice for Dummies”?

lol I'm learning from my big mistakes up to now and a ton of online tutorials, besides "Dive into Python" (2004)[1], "Python Programming" (2012)[2] and "Programming Python, 3rd Ed" (2006) [print]

print isn't thread safe. That's why I've chosen sys.stdout.write() -- it's faster and thread safe by default.

I don't need any fancy formating, just need to send the string to screen.


[1] http://www.diveintopython.net/
[1] http://en.wikibooks.org/wiki/Python_Programming

Carlos Nepomuceno

unread,
May 21, 2013, 3:41:51 PM5/21/13
to pytho...@python.org
> Analysing the code of "stringobject.c" I've found formatint() and formatlong().

I mean _PyString_FormatLong()

Andrew Berg

unread,
May 21, 2013, 3:53:54 PM5/21/13
to comp.lang.python
On 2013.05.21 14:26, Mark Lawrence wrote:
> On 21/05/2013 20:13, Skip Montanaro wrote:
>>> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.
>>
>> That's unlikely to change. If not deprecated already string
>> interpolation using the modulo operator has lost favor to the string
>> object's format method.
>>
>
> Please stop perpetuating this myth, see
> http://mail.python.org/pipermail/python-dev/2012-February/116789.html
> and http://bugs.python.org/issue14123
>
What myth? People should indeed be using .format(), but no one said % formatting was going away soon. Also, the suggested change to the docs
wasn't made and the issue is closed. The current docs do not say that % formatting isn't going to be deprecated, but it does mention its
caveats and suggests .format(). If you are trying to say that % formatting will never ever go away, then you are wrong. It is highly
unlikely to go away in a 3.x release, but /may/ get phased out in Python 4.0.
--
CPython 3.3.2 | Windows NT 6.2.9200 / FreeBSD 9.1

Ethan Furman

unread,
May 21, 2013, 3:41:36 PM5/21/13
to pytho...@python.org
On 05/21/2013 12:06 PM, Chris “Kwpolska” Warrick wrote:
> On Tue, May 21, 2013 at 8:49 PM, Carlos Nepomuceno wrote:
>>
>> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.
>
> There is no real reason to do this. `str.format()` is the new shiny
> thing you should be using all the time.

.format() is useful, and has it's place, but % formatting is not going away.


>> So, the question is: Where would I change the CPython 2.7.5 source code to enable '%' (BINARY_MODULO) to format using the thousands separator like str.format() does, such as:
>>
>>--> sys.stderr.write('%,d\n' % 1234567)
>> 1,234,567
>
> This will make your code unportable and useless, depending on one
> patch you made. Please don’t do that.

Agreed. Unless you're willing to have your programs either run differently, or not at all, on other systems this is the
wrong way to fix it.


> Where did you learn Python from? “Python Worst Practice for Dummies”?

Chris Warrick,

Was that necessary? Useful? Helpful in any way? If you can't be civil, keep your posts to yourself.

--
~Ethan~

Carlos Nepomuceno

unread,
May 21, 2013, 4:02:10 PM5/21/13
to pytho...@python.org
----------------------------------------
> To: pytho...@python.org
> From: bream...@yahoo.co.uk

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> Date: Tue, 21 May 2013 20:26:41 +0100

>
> On 21/05/2013 20:13, Skip Montanaro wrote:
>>> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.
>>
>> That's unlikely to change. If not deprecated already string
>> interpolation using the modulo operator has lost favor to the string
>> object's format method.
>>

I used to think str.__mod__() was going to be deprecated until Steven told me it was a myth! Think I got that idea from the own Python docs, but it's gone by now. Nevermind...

The fact is I have no need for str.format(). It's slow and awkward. str.format() looks like COBOL/Java idiom to me. I love Python! '%' is much more cool!!!

> --
> If you're using GoogleCrap™ please read this
> http://wiki.python.org/moin/GoogleGroupsPython.
>
> Mark Lawrence
>
> --
> http://mail.python.org/mailman/listinfo/python-list

Carlos Nepomuceno

unread,
May 21, 2013, 4:22:24 PM5/21/13
to comp.lang.python
----------------------------------------
> Date: Tue, 21 May 2013 14:53:54 -0500
> From: bahamut...@gmail.com
> To: pytho...@python.org
[...]

>>
> What myth? People should indeed be using .format(), but no one said % formatting was going away soon. Also, the suggested change to the docs
> wasn't made and the issue is closed. The current docs do not say that % formatting isn't going to be deprecated, but it does mention its
> caveats and suggests .format(). If you are trying to say that % formatting will never ever go away, then you are wrong. It is highly
> unlikely to go away in a 3.x release, but /may/ get phased out in Python 4.0.

I vote for keeping str.__mod__()!

Anyway, is it possible to overload str.__mod__() without deriving a class? I mean to have something like:

old_mod = str.__mod__
def new_mod(x):
    global old_mod
    try:
        old_mod(x)
    except ValueError, ex:
        #catch ValueError: unsupported format character ',' (0x2c) at index 1
        #process new '%,d' format here
        return '{:,}'.format(x)  #just to illustrate the behaviour. it would have it's own faster code

str.__mod__ = new_mod  #this raises TypeError: can't set attributes of built-in/extension type 'str'
sys.stdout.write('num=%,d\n' % 1234567)


> --
> CPython 3.3.2 | Windows NT 6.2.9200 / FreeBSD 9.1

> --
> http://mail.python.org/mailman/listinfo/python-list

Steven D'Aprano

unread,
May 21, 2013, 10:42:56 PM5/21/13
to
On Tue, 21 May 2013 23:22:24 +0300, Carlos Nepomuceno wrote:

> Anyway, is it possible to overload str.__mod__() without deriving a
> class? I mean to have something like:

No, not in Python. If you want to monkey-patch built-in classes on the
fly, with all the troubles that causes, use Ruby.


--
Steven

Carlos Nepomuceno

unread,
May 21, 2013, 10:56:53 PM5/21/13
to pytho...@python.org
----------------------------------------
> From: steve+comp....@pearwood.info

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> Date: Wed, 22 May 2013 02:42:56 +0000
> To: pytho...@python.org

So, the only alternative to have "'%,d' % x" rendering the thousands separator output would a C source code modification?

> --
> Steven
> --
> http://mail.python.org/mailman/listinfo/python-list

Steven D'Aprano

unread,
May 21, 2013, 10:59:22 PM5/21/13
to
On Tue, 21 May 2013 14:53:54 -0500, Andrew Berg wrote:

> On 2013.05.21 14:26, Mark Lawrence wrote:

>> Please stop perpetuating this myth, see
>> http://mail.python.org/pipermail/python-dev/2012-February/116789.html
>> and http://bugs.python.org/issue14123
>>
> What myth?

The myth that % string formatting is deprecated. It is not deprecated.

> People should indeed be using .format(),

If it is useful to them, and not too slow, or indeed if they merely want
to. And if not, then not.

This is a good case where the original poster *should* use str.format,
since it does exactly what he wants, and % does not. Python gives you
many tools, and the wise man uses the right tool for the job. Sometimes
that is % and sometimes it is str.format and sometimes it is
string.Template.

That str.format looks like Java is irrelevant. Method call syntax is
common in Python, and is not original to Java. Besides, Python looks like
many languages: some parts look like Java, some parts look like C, some
parts remind me of functional languages like Lisp and Haskell, and some
parts look like Algol or Pascal.


> but no one said % formatting was going away soon.

True, but only for the definition "no one = all the people who insist
that % is deprecated, or soon to be deprecated".


> Also, the suggested change to the docs
> wasn't made and the issue is closed. The current docs do not say that %
> formatting isn't going to be deprecated, but it does mention its caveats
> and suggests .format(). If you are trying to say that % formatting will
> never ever go away, then you are wrong. It is highly unlikely to go away
> in a 3.x release, but /may/ get phased out in Python 4.0.

What happens in Python 4000 is irrelevant. If somebody is trying to
"future proof" their code for a version that *may never exist*, and if it
does exist is likely to be six or eight years away from even starting the
design phase, they are wasting their time. It is hard enough to track a
moving target, it is impossible to track a target that isn't even a gleam
in GvR's eye yet.



--
Steven

Steven D'Aprano

unread,
May 21, 2013, 11:08:54 PM5/21/13
to
That's one alternative. But the language you would be then running will
no longer be Python.

Another alternative would be to write a pre-processor that parses your
Python source code, extracts any reference to the above, and replaces it
with a call to the appropriate format call. But not only is that a lot of
work for very little gain, but it's also more or less impossible to do in
full generality. And again, what you are running will be something
different than Python, it will be Python plus a pre-processor.


Don't fight the language. You will lose.



--
Steven

Andrew Berg

unread,
May 21, 2013, 11:38:01 PM5/21/13
to comp.lang.python
On 2013.05.21 21:59, Steven D'Aprano wrote:
> On Tue, 21 May 2013 14:53:54 -0500, Andrew Berg wrote:
>
>> On 2013.05.21 14:26, Mark Lawrence wrote:
>
>>> Please stop perpetuating this myth, see
>>> http://mail.python.org/pipermail/python-dev/2012-February/116789.html
>>> and http://bugs.python.org/issue14123
>>>
>> What myth?
>
> The myth that % string formatting is deprecated. It is not deprecated.
Skip didn't say that it was deprecated.

>> but no one said % formatting was going away soon.
>
> True, but only for the definition "no one = all the people who insist
> that % is deprecated, or soon to be deprecated".
Perhaps I missed something, but who is insisting this?

> What happens in Python 4000 is irrelevant. If somebody is trying to
> "future proof" their code for a version that *may never exist*, and if it
> does exist is likely to be six or eight years away from even starting the
> design phase, they are wasting their time. It is hard enough to track a
> moving target, it is impossible to track a target that isn't even a gleam
> in GvR's eye yet.
I think you misunderstand. I'm not suggesting that format() be used simply because % formatting could be deprecated at some unknown time
years from now; I was clarifying the status of % formatting.

Carlos Nepomuceno

unread,
May 21, 2013, 11:38:45 PM5/21/13
to pytho...@python.org
----------------------------------------
> From: steve+comp....@pearwood.info
> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> Date: Wed, 22 May 2013 03:08:54 +0000
> To: pytho...@python.org
[...]

>> So, the only alternative to have "'%,d' % x" rendering the thousands
>> separator output would a C source code modification?
>
> That's one alternative. But the language you would be then running will
> no longer be Python.
>
> Another alternative would be to write a pre-processor that parses your
> Python source code, extracts any reference to the above, and replaces it
> with a call to the appropriate format call. But not only is that a lot of
> work for very little gain, but it's also more or less impossible to do in
> full generality. And again, what you are running will be something
> different than Python, it will be Python plus a pre-processor.
>
>
> Don't fight the language. You will lose.

Not fighting the language. In fact it's not even a language issue.
All I need is a standard library[1] improvement: "%,d"! That's all!

Just to put in perspective the performance difference of str.__mod__() and str.format():

C:\Python27>python -m timeit -cv -n10000000 "'%d'%12345"
raw times: 0.386 0.38 0.373
10000000 loops, best of 3: 0.0373 usec per loop

C:\Python27>python -m timeit -cv -n10000000 "'{:d}'.format(12345)"
raw times: 7.91 7.89 7.98
10000000 loops, best of 3: 0.789 usec per loop

C:\Python27>python -m timeit -cv -n10000000 "'{:,d}'.format(12345)"
raw times: 8.7 8.67 8.78
10000000 loops, best of 3: 0.867 usec per loop

That shows str.format() is 20 times slower than str.__mod__() for a simple decimal integer literal formatting.
And it's additionally 10% slower if the thousands separator format specifier (',') is used.

[1] I think that translates to Python source code in 'Objects/stringobject.c' and maybe 'Objects/unicodeobject.c'

88888 Dihedral

unread,
May 22, 2013, 3:14:13 AM5/22/13
to
Carlos Nepomuceno於 2013年5月22日星期三UTC+8上午11時38分45秒寫道:
The conversions of the 32 bit integers and 64 bit floats
to the strings of the base 10 digits require an
efficint div and mod normally in the low level.

Skip Montanaro

unread,
May 22, 2013, 6:45:12 AM5/22/13
to Andrew Berg, comp.lang.python
>>>> Please stop perpetuating this myth, see
>>>> http://mail.python.org/pipermail/python-dev/2012-February/116789.html
>>>> and http://bugs.python.org/issue14123
>>>>
>>> What myth?
>>
>> The myth that % string formatting is deprecated. It is not deprecated.
> Skip didn't say that it was deprecated.

I didn't mean to create a tempest in a teapot. I was away from
comp.lang.python, python-bugs, and python-dev for a few years. In
particular, I didn't ever see the aforementioned thread from Feb 2012.
Had I known of that thread I would have worded the sentence which
shall not be repeated differently.

My apologies...

Skip

Ned Batchelder

unread,
May 22, 2013, 7:25:13 AM5/22/13
to Carlos Nepomuceno, pytho...@python.org

On 5/21/2013 11:38 PM, Carlos Nepomuceno wrote:
>> From:steve+comp....@pearwood.info
>> >Subject: Re: PEP 378: Format Specifier for Thousands Separator
>> >Date: Wed, 22 May 2013 03:08:54 +0000
>> >To:pytho...@python.org
> [...]
>>> >>So, the only alternative to have "'%,d' % x" rendering the thousands
>>> >>separator output would a C source code modification?
>> >
>> >That's one alternative. But the language you would be then running will
>> >no longer be Python.
>> >
>> >Another alternative would be to write a pre-processor that parses your
>> >Python source code, extracts any reference to the above, and replaces it
>> >with a call to the appropriate format call. But not only is that a lot of
>> >work for very little gain, but it's also more or less impossible to do in
>> >full generality. And again, what you are running will be something
>> >different than Python, it will be Python plus a pre-processor.
>> >
>> >
>> >Don't fight the language. You will lose.
> Not fighting the language. In fact it's not even a language issue.
> All I need is a standard library[1] improvement: "%,d"! That's all!

You have to keep in mind that 2.7 is not getting any new features, no
matter how small they seem. If you create a patch that implements the
comma flag in %-formatting, it *might* go into 3.x, but it will not go
into 2.7.

--Ned.

Carlos Nepomuceno

unread,
May 22, 2013, 7:52:15 AM5/22/13
to pytho...@python.org
----------------------------------------
> Date: Wed, 22 May 2013 07:25:13 -0400
> From: n...@nedbatchelder.com
[...]

> You have to keep in mind that 2.7 is not getting any new features, no
> matter how small they seem. If you create a patch that implements the
> comma flag in %-formatting, it *might* go into 3.x, but it will not go
> into 2.7.
>
> --Ned.

No problem. I have just discovered i was measuring the wrong thing.

My test case is been optimized at compile time by CPython that treats "'%d' % 12345" as a constant.
My use case is different because I almost have no literals been used with % operator.

So my gain isn't that great. In fact it's faster with str.format() than %, and it's even faster if I use the default format specifier.

C:\Python27>python -m timeit -cv -n10000000 -s"v=12345" "'%d'%v"
raw times: 10.5 10.7 10.7
10000000 loops, best of 3: 1.05 usec per loop

C:\Python27>python -m timeit -cv -n10000000 -s"v=12345" "'{:d}'.format(v)"
raw times: 8.11 8.09 8.02
10000000 loops, best of 3: 0.802 usec per loop

C:\Users\Josue\Documents\Python>python -m timeit -cv -n10000000 -s"v=12345" "'{}'.format(v)"
raw times: 5.3 5.5 5.62
10000000 loops, best of 3: 0.53 usec per loop

Using variables (100% of cases) makes str.format() 50% faster than %.

Steven D'Aprano

unread,
May 22, 2013, 10:58:08 AM5/22/13
to
On Wed, 22 May 2013 05:45:12 -0500, Skip Montanaro wrote:

> I didn't mean to create a tempest in a teapot. I was away from
> comp.lang.python, python-bugs, and python-dev for a few years. In
> particular, I didn't ever see the aforementioned thread from Feb 2012.
> Had I known of that thread I would have worded the sentence which
> shall not be repeated differently.
>
> My apologies...

No problem, it's not about you specifically, it's just that some of us
fans of % formatting can be a tad sensitive about it, especially since
the idea that it has been deprecated (or soon will be deprecated, or one
day will be deprecated, and therefore code using it is bad) is relatively
widespread on the Internet.

Glad to have you back here!



--
Steven

Ned Batchelder

unread,
May 22, 2013, 2:30:09 PM5/22/13
to Steven D'Aprano, pytho...@python.org
Seems like maybe this should become a question in the Python FAQ.

--Ned.

nn

unread,
May 22, 2013, 4:26:23 PM5/22/13
to
Maybe a cformat(formatstring, variables) function should be created
in the string module so people who prefer that can use it. I don't
mind the C formatting syntax but I don't like the fact that the %
operator does something totally different when the first variable is
an integer and the fact that it misbehaves if the second variable is a
tuple.

Carlos Nepomuceno

unread,
May 22, 2013, 6:31:20 PM5/22/13
to nn, pytho...@python.org
----------------------------------------
> Date: Wed, 22 May 2013 13:26:23 -0700

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> From: prue...@latinmail.com
> To: pytho...@python.org
[...]

>
> Maybe a cformat(formatstring, variables) function should be created
> in the string module so people who prefer that can use it. I don't
> mind the C formatting syntax but I don't like the fact that the %
> operator does something totally different when the first variable is
> an integer and the fact that it misbehaves if the second variable is a
> tuple.
> --
> http://mail.python.org/mailman/listinfo/python-list

I still don't understand why % benefits from literals optimization ("'%d'%12345") while '{:d}'.format(12345) doesn't.

What "totally different" you talking about? Please give me an example.

Oscar Benjamin

unread,
May 22, 2013, 8:30:53 PM5/22/13
to Carlos Nepomuceno, nn, pytho...@python.org
On 22 May 2013 23:31, Carlos Nepomuceno <carlosne...@outlook.com> wrote:
>
> I still don't understand why % benefits from literals optimization ("'%d'%12345") while '{:d}'.format(12345) doesn't.

There's no reason why that optimisation can't happen in principle.
However no one has written a patch for it. Why don't you look into
what it would take to make it happen?


Oscar

Carlos Nepomuceno

unread,
May 22, 2013, 8:44:36 PM5/22/13
to pytho...@python.org
----------------------------------------
> From: oscar.j....@gmail.com
> Date: Thu, 23 May 2013 01:30:53 +0100

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> To: carlosne...@outlook.com
> CC: prue...@latinmail.com; pytho...@python.org

Maybe I'll look into that later, but I couldn't even find how the hell they made _Py_InsertThousandsGrouping() been called.

That's what I got when analysing % formating:

Thousands separator format specifier for str.__mod__()
======================================================

@Objects/stringobject.c: implements formatint() for '%' processing
-Looking for code used in str.format()

@Objects/stringlib/formatter.h: implements str.format()
-It uses STRINGLIB_GROUPING() to do the job.

@Objects/stringlib/stringdefs.h: #define STRINGLIB_GROUPING       _PyString_InsertThousandsGrouping
@Objects/stringlib/unicodedefs.h: #define STRINGLIB_GROUPING       _PyUnicode_InsertThousandsGrouping
@Objects/stringobject.c: #define _Py_InsertThousandsGrouping _PyString_InsertThousandsGrouping
@Objects/stringobject.h: declares _PyString_InsertThousandsGrouping()
@???: ??? _PyString_InsertThousandsGrouping ??? _Py_InsertThousandsGrouping
@Objects/stringlib/localeutil.h: implements _Py_InsertThousandsGrouping()


Let me explain what that means. I found no relating declarations/definitions that turn _PyString_InsertThousandsGrouping into _Py_InsertThousandsGrouping.

So, I don't even know how that source code compiles without error.

:/ really strange...


Not to mention the lots of code inside header definition files! Weird!!!!

nn

unread,
May 23, 2013, 9:44:05 AM5/23/13
to
On May 22, 6:31 pm, Carlos Nepomuceno <carlosnepomuc...@outlook.com>
wrote:
> ----------------------------------------
>
> > Date: Wed, 22 May 2013 13:26:23 -0700
> > Subject: Re: PEP 378: Format Specifier for Thousands Separator
> > From: prueba...@latinmail.com
> > To: python-l...@python.org
> [...]
>
> > Maybe a cformat(formatstring, variables) function should be created
> > in the string module so people who prefer that can use it. I don't
> > mind the C formatting syntax but I don't like the fact that the %
> > operator does something totally different when the first variable is
> > an integer and the fact that it misbehaves if the second variable is a
> > tuple.
> > --
> >http://mail.python.org/mailman/listinfo/python-list
>
> I still don't understand why % benefits from literals optimization ("'%d'%12345") while '{:d}'.format(12345) doesn't.
>
> What "totally different" you talking about? Please give me an example.

>>> def eggs(spam, ham): return spam % ham

>>> def milk(beef, steak): return beef.format(steak)

>>> a='%s'
>>> c=9
>>> d=4
>>> e=[1,2]
>>> f=(3,5)
>>> d='{}'

>>> eggs(a,4)
'4'
>>> eggs(c,4)
1
>>> eggs(a,e)
'[1, 2]'
>>> eggs(a,f)
Traceback (most recent call last):
File "<pyshell#29>", line 1, in <module>
eggs(a,f)
File "<pyshell#1>", line 1, in eggs
def eggs(spam, ham): return spam % ham
TypeError: not all arguments converted during string formatting
>>> '%s'%(5%3)
'2'

>>> milk(d,4)
'4'
>>> milk(c,4)
Traceback (most recent call last):
File "<pyshell#53>", line 1, in <module>
milk(c,4)
File "<pyshell#49>", line 1, in milk
def milk(beef, steak): return beef.format(steak)
AttributeError: 'int' object has no attribute 'format'
>>> milk(d,e)
'[1, 2]'
>>> milk(d,f)
'(3, 5)'
>>> '{}'.format(5%3)
'2'

Carlos Nepomuceno

unread,
May 23, 2013, 11:26:49 AM5/23/13
to pytho...@python.org
----------------------------------------
> Date: Thu, 23 May 2013 06:44:05 -0700

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> From: prue...@latinmail.com
> To: pytho...@python.org
[...]

>>>> eggs(a,f)
> Traceback (most recent call last):
> File "<pyshell#29>", line 1, in <module>
> eggs(a,f)
> File "<pyshell#1>", line 1, in eggs
> def eggs(spam, ham): return spam % ham
> TypeError: not all arguments converted during string formatting
>>>> '%s'%(5%3)
> '2'

So % doesn't handle tuples! Why's that? Is it intentional (by design)?

Dave Angel

unread,
May 23, 2013, 2:42:47 PM5/23/13
to pytho...@python.org
On 05/23/2013 11:26 AM, Carlos Nepomuceno wrote:
> ----------------------------------------
>> Date: Thu, 23 May 2013 06:44:05 -0700
>> Subject: Re: PEP 378: Format Specifier for Thousands Separator
>> From: prue...@latinmail.com
>> To: pytho...@python.org
> [...]

You left out the part where a and f are initialized:


>>> a='%s'
>>> f=(3,5)


>>>>> eggs(a,f)
>> Traceback (most recent call last):
>> File "<pyshell#29>", line 1, in <module>
>> eggs(a,f)
>> File "<pyshell#1>", line 1, in eggs
>> def eggs(spam, ham): return spam % ham
>> TypeError: not all arguments converted during string formatting
>>>>> '%s'%(5%3)
>> '2'
>
> So % doesn't handle tuples! Why's that? Is it intentional (by design)?
>

It's a conflict in the design. A tuple is used to supply multiple
arguments to the % operator. So if you want to have a tuple as the
first argument, you need to enclose it in another tuple.

try the following:

print a % (f,)

The trouble is, it doesn't generalize very readily, so it's difficult to
use in a function like eggs()

--
DaveA

Terry Jan Reedy

unread,
May 23, 2013, 4:19:33 PM5/23/13
to pytho...@python.org
On 5/23/2013 2:42 PM, Dave Angel wrote:
> On 05/23/2013 11:26 AM, Carlos Nepomuceno wrote:

>
>>>>>> eggs(a,f)
>>> Traceback (most recent call last):
>>> File "<pyshell#29>", line 1, in <module>
>>> eggs(a,f)
>>> File "<pyshell#1>", line 1, in eggs
>>> def eggs(spam, ham): return spam % ham
>>> TypeError: not all arguments converted during string formatting
>>>>>> '%s'%(5%3)
>>> '2'
>>
>> So % doesn't handle tuples! Why's that? Is it intentional (by design)?
>>
>
> It's a conflict in the design. A tuple is used to supply multiple
> arguments to the % operator. So if you want to have a tuple as the
> first argument, you need to enclose it in another tuple.

The problem is that interpolating 1 to many items into a string is *not*
a binary operation. The needed hack to pretend that it is, using a tuple
to represent multiple items rather than just itself, was one of the
reasons for making string formatting a honest function, where multiple
items to be formatted are passed as multiple arguments.


Carlos Nepomuceno

unread,
May 23, 2013, 6:20:26 PM5/23/13
to pytho...@python.org
----------------------------------------
> To: pytho...@python.org
> From: tjr...@udel.edu
[...]

>> It's a conflict in the design. A tuple is used to supply multiple
>> arguments to the % operator. So if you want to have a tuple as the
>> first argument, you need to enclose it in another tuple.
>
> The problem is that interpolating 1 to many items into a string is *not*
> a binary operation. The needed hack to pretend that it is, using a tuple
> to represent multiple items rather than just itself, was one of the
> reasons for making string formatting a honest function, where multiple
> items to be formatted are passed as multiple arguments.

Thanks so much guys! Now I understand why some people hate %-formatting!

I don't think that's a problem because there's no format specifier for tuples in the %-formatting definition[1].
So it's up to the user to make the necessary conversion.

I still love the %-formatting style!

Can str.format() do the following?

f = '%d %d %d'
v = '1,2,3'
print f % eval(v)

If yes, how?


[1] http://docs.python.org/2/library/stdtypes.html#string-formatting

Jerry Hill

unread,
May 23, 2013, 9:17:54 PM5/23/13
to Carlos Nepomuceno, pytho...@python.org
On Thu, May 23, 2013 at 6:20 PM, Carlos Nepomuceno <carlosne...@outlook.com> wrote:
Can str.format() do the following?

f = '%d %d %d'
v = '1,2,3'
print f % eval(v)

​Sure:

Python 3.2.2 (default, Sep  4 2011, 09:51:08) [MSC v.1500 32 bit (Intel)] on win32
>>> f = "{} {} {}"
>>> v = "1,2,3"
>>> print(f.format(*eval(v)))
1 2 3
>>>

The * unpacks the tuple returned from eval(), so that you get 3 separate parameters passed to format(), instead of the single tuple.​

--

Jerry​

Carlos Nepomuceno

unread,
May 23, 2013, 9:41:22 PM5/23/13
to pytho...@python.org
Thank you! Hail Eris!!! :)

________________________________
> Date: Thu, 23 May 2013 21:17:54 -0400

> Subject: Re: PEP 378: Format Specifier for Thousands Separator

> From: malac...@gmail.com
> To: carlosne...@outlook.com
> CC: pytho...@python.org

>
> On Thu, May 23, 2013 at 6:20 PM, Carlos Nepomuceno

> <carlosne...@outlook.com<mailto:carlosne...@outlook.com>>

88888 Dihedral

unread,
May 23, 2013, 10:29:14 PM5/23/13
to
Carlos Nepomuceno於 2013年5月22日星期三UTC+8上午2時49分28秒寫道:
> ________________________________
> > From: alysso...@gmail.com
> > Date: Tue, 21 May 2013 09:03:13 -0300
> > Subject: Re: PEP 378: Format Specifier for Thousands Separator
> > To: pytho...@python.org
> >
> > This work in 3.1+:
> >
> > $ python3
> > Python 3.1.3 (r313:86834, Nov 28 2010, 11:28:10)
> > [GCC 4.4.5] on linux2
> > Type "help", "copyright", "credits" or "license" for more information.
> > >>> one_number = 1234567
> > >>> print('number={:,}'.format(one_number))
> > number=1,234,567
> > >>>
> >
>
> Thank you, but let me rephrase it. I'm already using str.format() but I'd like to use '%' (BINARY_MODULO) operator instead.
>
> I've looked into the source code of CPython 2.7.5 and I've found no evidence of the thousands separator been implemented on formatint() in "Objects/unicodeobject.c".
>
> I also didn't find the _PyString_FormatLong() used in formatlong(). Where is _PyString_FormatLong() located?
>
> So, the question is: Where would I change the CPython 2.7.5 source code to enable '%' (BINARY_MODULO) to format using the thousands separator like str.format() does, such as:
>
> >>>sys.stderr.write('%,d\n' % 1234567)
> 1,234,567

Could a separate instance like the I/O device of a subprocess
to be easily available in Python?

The next question would be whether the flow of several I/O data streams could be easily piped and manipulated in the high level
programming designs without consuming too much resources.





nn

unread,
May 24, 2013, 9:50:51 AM5/24/13
to
On May 23, 2:42 pm, Dave Angel <da...@davea.name> wrote:
> On 05/23/2013 11:26 AM, Carlos Nepomuceno wrote:
>
> > ----------------------------------------
> >> Date: Thu, 23 May 2013 06:44:05 -0700
> >> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> >> From: prueba...@latinmail.com
> >> To: python-l...@python.org
> > [...]
>
> You left out the part where a and f are initialized:
>
>  >>> a='%s'
>  >>> f=(3,5)
>
> >>>>> eggs(a,f)
> >> Traceback (most recent call last):
> >> File "<pyshell#29>", line 1, in <module>
> >> eggs(a,f)
> >> File "<pyshell#1>", line 1, in eggs
> >> def eggs(spam, ham): return spam % ham
> >> TypeError: not all arguments converted during string formatting
> >>>>> '%s'%(5%3)
> >> '2'
>
> > So % doesn't handle tuples! Why's that? Is it intentional (by design)?
>
> It's a conflict in the design.  A tuple is used to supply multiple
> arguments to the % operator.  So if you want to have a tuple as the
> first argument, you need to enclose it in another tuple.
>
> try the following:
>
> print a % (f,)
>
> The trouble is, it doesn't generalize very readily, so it's difficult to
> use in a function like eggs()
>
> --
> DaveA

It's all there, it's just that quoting ate it. Let's try this again:

>>> def eggs(spam, ham): return spam % ham
>>> def milk(beef, steak): return beef.format(steak)
>>> a='%s'
>>> c=9
>>> d=4
>>> e=[1,2]
>>> f=(3,5)
>>> d='{}'
>>> eggs(a,4)
'4'
>>> eggs(c,4)
1
>>> eggs(a,e)
'[1, 2]'
>>> eggs(a,f)

Traceback (most recent call last):
File "<pyshell#29>", line 1, in <module>
eggs(a,f)
File "<pyshell#1>", line 1, in eggs
def eggs(spam, ham): return spam % ham
TypeError: not all arguments converted during string formatting
>>> '%s'%(5%3)
'2'

>>> milk(d,4)
'4'
>>> milk(c,4)

Traceback (most recent call last):
File "<pyshell#53>", line 1, in <module>
milk(c,4)
File "<pyshell#49>", line 1, in milk
def milk(beef, steak): return beef.format(steak)
AttributeError: 'int' object has no attribute 'format'
>>> milk(d,e)
'[1, 2]'
>>> milk(d,f)
'(3, 5)'
>>> '{}'.format(5%3)
'2'

The three issues represented:
1. Functions in which both values of the operator are parameters might
not return a string but an integer instead. It is not always
immediately obvious when reading such functions if modulus or
formatting is intended.
2. Function doesn't handle tuple properly unless carefully written
3. Too much % noise because % is used for 3 things: the special
placeholder character inside format strings, the format operator and
the modulus operator.

Carlos Nepomuceno

unread,
May 24, 2013, 11:25:45 AM5/24/13
to pytho...@python.org
----------------------------------------
> Date: Thu, 23 May 2013 19:29:14 -0700

> Subject: Re: PEP 378: Format Specifier for Thousands Separator
> From: dihedr...@gmail.com
[...]

> Could a separate instance like the I/O device of a subprocess
> to be easily available in Python?
>
> The next question would be whether the flow of several I/O data streams could be easily piped and manipulated in the high level
> programming designs without consuming too much resources.


I'm sorry but I don't understand your question.

Do you mean returning the output of another process to the caller? Like:

import subprocess
output = subprocess.check_output(['ping', 'google.com'])

Andreas Perstinger

unread,
May 24, 2013, 1:28:29 PM5/24/13
to pytho...@python.org
On 24.05.2013 17:25, Carlos Nepomuceno wrote:
> ----------------------------------------
>> Date: Thu, 23 May 2013 19:29:14 -0700
>> Subject: Re: PEP 378: Format Specifier for Thousands Separator
>> From: dihedr...@gmail.com
>> [some typical dihedral stuff]
>
> I'm sorry but I don't understand your question.

Don't worry. I guess most people on this list don't understand it either.

It looks like dihedral is a bot although nobody knows for sure. Search
for some other posts from him/her/it in the archive and form your own
opinion.

IMHO you can simply ignore him/her/it.

Bye, Andreas

Carlos Nepomuceno

unread,
May 24, 2013, 5:07:41 PM5/24/13
to pytho...@python.org
lol that reminds me of George! lol
;)

----------------------------------------
> Date: Fri, 24 May 2013 19:28:29 +0200
> From: andip...@gmail.com
> To: pytho...@python.org


> Subject: Re: PEP 378: Format Specifier for Thousands Separator
>

> On 24.05.2013 17:25, Carlos Nepomuceno wrote:
>> ----------------------------------------
>>> Date: Thu, 23 May 2013 19:29:14 -0700

>>> Subject: Re: PEP 378: Format Specifier for Thousands Separator

>>> From: dihedr...@gmail.com
>>> [some typical dihedral stuff]
>>
>> I'm sorry but I don't understand your question.
>
> Don't worry. I guess most people on this list don't understand it either.
>
> It looks like dihedral is a bot although nobody knows for sure. Search
> for some other posts from him/her/it in the archive and form your own
> opinion.
>
> IMHO you can simply ignore him/her/it.
>
> Bye, Andreas
>

> --
> http://mail.python.org/mailman/listinfo/python-list

0 new messages