Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Proposal: prepared statements #618

Closed
gabime opened this issue Dec 3, 2017 · 12 comments
Closed

Proposal: prepared statements #618

gabime opened this issue Dec 3, 2017 · 12 comments

Comments

@gabime
Copy link
Contributor

gabime commented Dec 3, 2017

While #613 would be great, but will probably only supported for c++17.

Another approach would be to have kind of prepared templates (or prepared statements - a bit like in db, but fmt need not to store or manage the handle anywhere - the handle itself would contain all the needed info).

The user would pass a format string he expects to use a lot and get a handle to a "compiled" version of the format string:

// fmt returns a handle object that can be executed like this:
auto handle = fmt::prepare("My name is {}. I am {} years old."); 


// and then the user can make heavy use of it
auto result = handle->format(arg1, arg2);
// or maybe
auto result = fmt::format(handle, arg1, arg2);

The handle would contain an efficient representation of the format - list of actual formatters to use, their flags, and their offsets in the format string.
I am not sure if the result would be much faster for simple format strings, but complex format strings, it might give big performance boost.

@vitaut
Copy link
Contributor

vitaut commented Dec 4, 2017

Thanks for the suggestion. It sounds very similar to what Bengt Gustafsson's proposed in https://groups.google.com/a/isocpp.org/forum/#!msg/std-proposals/4wOU-1_3D0A/xiNQSmO1CAAJ:

I think it may make sense to allow pre-creating a formatting object for an entire format string, so that the parsing of that string occurs only once.

and, in fact, I've already done most of the work to make this possible, namely separated parsing and formatting as part of compile-time format string parsing support. It still needs to be packaged in an API similar to the one you proposed with the main difference that prepare function or its equivalent should take argument types in addition to format string:

auto formatter = fmt::prepare<std::string, int>("My name is {}. I am {} years old.");

@vitaut
Copy link
Contributor

vitaut commented Dec 5, 2017

BTW #613 can work with C++14.

@gabime
Copy link
Contributor Author

gabime commented Dec 5, 2017

Do you think adding this feature, or will you do #613 first ?

@vitaut
Copy link
Contributor

vitaut commented Dec 6, 2017

Not sure, #613 will give much better runtime performance but, as you noticed, it will require a modern compiler. This one is a small optimization, mostly for the case when you need to process the same format string multiple times. My main focus right now is addressing standards proposal feedback (#518), but I'll get back to this idea afterwards.

@stryku
Copy link
Contributor

stryku commented Oct 18, 2018

Hello, does this proposal need to wait for some other dependency than #581, or I can fool around a little and try to implement this? Or you want to postpone it?

@vitaut
Copy link
Contributor

vitaut commented Oct 19, 2018

No this doesn't have to wait on anything.

I can fool around a little and try to implement this?

Please do. Contributions are always welcome!

@stryku
Copy link
Contributor

stryku commented Nov 24, 2018

I think I've finished implementation for this (at least for the first review). Now I'm checking whether my changes are compilable by all of the supported compilers and I have one question. Against which compilers should I check my code? In the Portability section, GCC 4.4, Clang 2.9 and MSVC 18.0 (2013) are listed but in the travis script there is a clang 4.0, not 2.9. So which one should I test?

@vitaut
Copy link
Contributor

vitaut commented Nov 24, 2018

Testing the ones listed in the Travis CI config should be fine, particularly GCC 4.4 which is the oldest.

@vitaut vitaut closed this as completed Aug 10, 2019
@ton
Copy link

ton commented Oct 2, 2019

Is fmt::prepare a thing? I would like to have something like that. Maybe some other functionality made it obsolete?

@vitaut
Copy link
Contributor

vitaut commented Oct 2, 2019

It has been renamed to fmt::compile.

@simonhf
Copy link

simonhf commented Jul 15, 2020

Is fmt::compile similar to the idea presented here [1] back in February 2016 where "compiling" avoids "reparsing"?

Is there any info regarding possible performance gains to be had with fmt::compile?

[1] #269

@vitaut
Copy link
Contributor

vitaut commented Jul 15, 2020

Yes, although it has been superseded by FMT_COMPILE: https://fmt.dev/latest/api.html#compile-api. Performance gains depend on the actual arguments, some results for integers are available here: http://www.zverovich.net/2020/06/13/fast-int-to-string-revisited.html.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants