[Python-ideas] idea: Template.match function

Joe Strout joe at strout.net
Sat Oct 11 00:50:07 CEST 2008


OK, here's my pitch -- in rough PEP form, even though this may be  
small enough to not merit a PEP.  I'd really like your feedback on  
this idea.

Abstract

I propose we add a new function on the string.Template [1] class,  
match(), to perform the approximate inverse of the existing  
substitute() function.  That is, it attempts to match an input string  
against a template, and if successful, returns a dictionary providing  
the matched text for each template field.


Rationale

PEP 292 [2] added a simplified string substitution feature, allowing  
users to easily substitute text for named fields in a template  
string.  The inverse operation is also useful: given a template and an  
input string, one wishes to find the text in the input string matching  
the fields in the template.  However, Python currently has no easy way  
to do it.

While this named matching operation can be accomplished using RegEx,  
the constructions required are somewhat complex and error prone.  It  
can also be done using third-party modules such as pyparse, but again  
the setup requires more code and is not obvious to programmers  
inexperienced with that module.

In addition, the Template class already has all the data needed to  
perform this operation, so it is a natural fit to simply add a new  
method on this class to perform a match, in addition to the existing  
method to perform a substitution.


Proposal

Proposed is the addition of one new attribute, and one new function,  
on the existing Template class, as follows:

1. 'greedy' is a new attribute that determines whether the field  
matches should be done in a greedy manner, equivalent to regex pattern  
'(.*)'; or in a non-greedy manner, equivalent to '(.*?)'.  This  
attribute defaults to false.

2. 'match' is a new function which accepts one parameter, an input  
string.  If the input string can be matched to the template pattern  
(respecting the 'greedy' flag), then match returns a dictionary, where  
each field in the pattern maps to the corresponding part of the input  
string.  If the input string cannot be matched to the template  
pattern, then match returns NOne.

Examples:

     >>> from string import Template
     >>> s = Template('$name was born in ${country}')
     >>> print s.match('Guido was born in the Netherlands')
     {'name':'Guido', 'country':'the Netherlands'}
     >>> print s.match('Spam was born as a canned ham')
     None

Note that when the match is successful, the resulting dictionary could  
be passed through Template.substitute to reconstitute the original  
input string.  Conversely, any string created by Template.substitute  
could be matched by Template.match (though in unusual cases, the  
resulting dictionary might not exactly match the original, e.g. if the  
string could be matched in multiple ways).  Thus, .match  
and .substitute are inverse operations.


References

[1] Template Strings
     http://www.python.org/doc/2.5.2/lib/node40.html

[2] PEP 292: Simpler String Substitutions
     http://www.python.org/dev/peps/pep-0292/






More information about the Python-ideas mailing list