
On 25Apr2021 10:54, Cameron Simpson <cs@cskk.id.au> wrote:
On 24Apr2021 22:35, Stephen J. Turnbull <turnbull.stephen.fw@u.tsukuba.ac.jp> wrote: [...]
My use case is presupplied strings, eg a command line supplied format string.
In that case the format string is user input, and x is a variable in the program that the user can have substituted into their string?
Assuming that *exact* use case, wouldn't
class LowerableStr(str): ... def __format__(self, fmt): ... if fmt == 'lc': ... return self.lower() ... else: ... return str.__format__(self, fmt) ... "{x} is {x:lc} in lowercase".format_map({'x' : LowerableStr("This")}) 'This is this in lowercase'
do?
You're perfectly correct. ":lc" can be shoehorned into doing what I ask. But __format__ is in the wrong place for how I'd like to do this.
Just to follow up on this, I've been experimenting with Stephen's suggestion of using ":foo" style format specifiers. With enough success that I'm probably going to run with it is I can make the implementation clean enough. I'm currently making a subclass of the Formatter builtin class, which supplies the string parser and lets one override various methods to implemenent the "{...}" parts. Currently I can do this: I've got a little ontology, saying that a tag named "colour" is "a colour, a hue" and expects to be a Python str. It also has metadata for the particular colour "blue". { 'type.colour': TagSet:{'description': 'a colour, a hue', 'type': 'str'}, 'meta.colour.blue': TagSet:{'url': 'https://en.wikipedia.org/wiki/Blue', 'wavelengths': '450nm-495nm'} } And I've got a tag set describing some object which is blue: {'colour': 'blue', 'labels': ['a', 'b', 'c'], 'size': 9} The TagSet class has a .format_as(format_string) method which hooks into the Formatter subclass and formats a string according to the TagSet. A little test programme to write information into some command line supplied format strings: [~/hg/css-tagsets(hg:tagsets)]fleet2*> py3 -m cs.tagset '{colour}' '{colour:meta}' '{colour:meta.url}' {colour} => 'blue' {colour:meta} => 'url="https://en.wikipedia.org/wiki/Blue" wavelengths="450nm-495nm"' {colour:meta.url} => 'https://en.wikipedia.org/wiki/Blue' Looking promising to me. Cheers, Cameron Simpson <cs@cskk.id.au>