This is not a duplicate, as this regards using the newer str.format()
, the above linked question is also of lower quality, and I think this question is sufficiently different to justify its canonicity.
The question:
One might expect an error here, but we can provide the str.format
method with unused keyword arguments.
>>> '{a}{b}'.format(a='foo', b='bar', c='baz')
'foobar'
This enables code like:
>>> foo = 'bar'
>>> baz = 'fizzbuzz'
>>> '{foo}{baz}'.format(**locals())
'barfizzbuzz'
>>> baz = datetime.datetime.now()
>>> '{foo}_{baz}'.format(**locals())
'bar_2013-12-20 18:36:55.624000'
Is this a good practice to do inside a closure like a function?
def make_foo_time_string():
foo = 'bar'
baz = datetime.datetime.now()
return '{foo}{baz}'.format(**locals())
What would be the possible downsides? Extra variables loaded using extra cycles? Is this a matter of convenience? I don't recall seeing this used much, would it be considered idiomatic of Python?
Update I have found a canonical suggested usage using the old style string interpolation: https://wiki.python.org/moin/PythonSpeed/PerformanceTips Nevertheless, it does seem a rather old document.
"Even better, for readability (this has nothing to do with efficiency other than yours as a programmer), use dictionary substitution:"
out = "<html>%(head)s%(prologue)s%(query)s%(tail)s</html>" % locals()
Python locals() Function The locals() function returns the local symbol table as a dictionary. A symbol table contains necessary information about the current program.
The __format__ method is responsible for interpreting the format specifier, formatting the value, and returning the resulting string. It is safe to call this function with a value of “None” (because the “None” value in Python is an object and can have methods.)
Learn about string formatting in Python. String formatting is also known as String interpolation. It is the process of inserting a custom string or variable in predefined text. As a data scientist, you would use it for inserting a title in a graph, show a message or an error, or pass a statement to a function.
%d is used as a placeholder for numeric or decimal values. For example (for python 3) print ('%s is %d years old' % ('Joe', 42))
What would be the possible downsides? Extra variables loaded using extra cycles? Is this a matter of convenience? I don't recall seeing this used much, would it be considered idiomatic of Python?
You just hit on the biggest downside: It's not idiomatic.
And the reason it's not idiomatic is, as the Zen says, "Explicit is better than implicit."
Obviously many people would not write '{foo}{baz}'.format(foo=foo, baz=baz)
(especially if you get too far beyond 2 variables), because that violates DRY pretty horribly… but there's a way to do this that's just as concise as your code, and at least as explicit, and doesn't require sort-of-advanced-level knowledge like locals
:
>>> '{}{}'.format(foo, baz)
This doesn't work when the format string is dynamic, but that's a good thing, because dynamic format strings are usually a red flag.
(Some people have also argued the "static-checking" benefit here—if you embed the names in the format string, you get a much less decipherable error than the simple NameError
from using a variable that doesn't exist in the arguments to format
. I put this in parentheses near the bottom because I personally don't think this argument is very good, even if I have seen it multiple times…)
However, as with any style/idiom question, there is no universal agreement on this one, and it gets debated regularly on python-list (and python-ideas, when someone suggests a way to make locals()
a default for format
or the like) until everyone stops paying attention.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With