Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

String templates in Python: what are legal characters?

I can't quite figure out what's going on with string templates:

t = Template('cannot teach an ${dog.old} ${tricks.new}. ${why} is this ${not} working')
print t.safe_substitute({'dog.old': 'old dog', 'tricks.new': 'new tricks', 'why': 'OH WHY', 'not': '@#%@#% NOT'})

This prints:

cannot teach an ${dog.old} ${tricks.new}. OH WHY is this @#%@#% NOT working

I thought that the braces handled arbitrary strings. What characters are allowed in braces and is there any way I can subclass Template to do what I want?

like image 316
Jason S Avatar asked Feb 24 '10 14:02

Jason S


People also ask

What is a template string in Python?

The template string is a regular Python string that includes special placeholders. As we've seen before, these placeholders are created using a $ sign, along with a valid Python identifier. Once we have a valid template string, the placeholders can be replaced by our own values to create a more elaborated string.

What are the characters in Python?

Like many other popular programming languages, strings in Python are arrays of bytes representing unicode characters. However, Python does not have a character data type, a single character is simply a string with a length of 1. Square brackets can be used to access elements of the string.

Which character is used in Python for inserting characters that are available in a string?

To insert characters that are illegal in a string, use an escape character. An escape character is a backslash \ followed by the character you want to insert.

Does Python have template strings?

Template string is another method used to format strings in Python. In comparison with %operator, . format() and f-strings, it has a (arguably) simpler syntax and functionality.


2 Answers

From the documentation...

$identifier names a substitution placeholder matching a mapping key of "identifier". By default, "identifier" must spell a Python identifier. The first non-identifier character after the $ character terminates this placeholder specification.

The period is a non-identifier character, and braces are simply used to separate the identifier from adjacent non-identifier text.

like image 66
MikeWyatt Avatar answered Sep 22 '22 20:09

MikeWyatt


Aha, I tried this experiment:

from string import Template
import uuid

class MyTemplate(Template):
    idpattern = r'[a-z][_a-z0-9]*(\.[a-z][_a-z0-9]*)*'

t1 = Template('cannot teach an ${dog.old} ${tricks.new}. ${why} is this ${not} working')
t2 = MyTemplate('cannot teach an ${dog.old} ${tricks.new}. ${why} is this ${not} working')
map1 = {'dog.old': 'old dog', 
    'tricks.new': 'new tricks', 'why': 'OH WHY', 'not': '@#%@#% NOT'}
map2 = {'dog': {'old': 'old dog'}, 
        'tricks': {'new': 'new tricks'}, 'why': 'OH WHY', 'not': '@#%@#% NOT'}  
print t1.safe_substitute(map1)
print t1.safe_substitute(map2)
print t2.safe_substitute(map1)
print t2.safe_substitute(map2)

which prints

cannot teach an ${dog.old} ${tricks.new}. OH WHY is this @#%@#% NOT working
cannot teach an ${dog.old} ${tricks.new}. OH WHY is this @#%@#% NOT working
cannot teach an old dog new tricks. OH WHY is this @#%@#% NOT working
cannot teach an ${dog.old} ${tricks.new}. OH WHY is this @#%@#% NOT working

so the third one (print t2.safe_substitute(map1)) works.

like image 23
Jason S Avatar answered Sep 22 '22 20:09

Jason S