[lexical_cast] Locale used during conversion

lexical_cast does not allow to pass the locale to be used during conversion. This is justified with analogy of lexical_cast to other casts which all take only one parameter. So lexical_cast always uses the current global locale. A reasonable choice. However I wanted to propose some additional features. It would be useful to provide (lets call it so for now) classic_lexical_cast which would use std::locale::classic() instead of the global one. I just finalized globalization/localization of our application by adding setting of the global locale to appropriate value according to the selected language. I noticed that all of sudden serialized data (mainly projects) stopped loading/saving correctly. The reason was easy to find. Where previously we had XML node named "item1000" we now have "item1,000" in English or "item1 000" in Polish for example. The projects are no longer interchangeable between applications running in different language version. I corrected this by adding our own lexical_cast which resets the global locale to the classic one, calls boost::lexical_cast and finally resets the global locale back. This special cast is used now whenever we are dealing with texts which are not presented to the final user. This works fine however it seems that resetting the global locale often (each time we save a number in the project for example...) is causing significant performance overhead. (Exact tests have not been yet performed but this seems the only change which might have affected all serialization slowdown.) I might reset it before saving the project and then save the project as usually but this is not very handy as I would have to remember to do it each time I am serializing any data. Also other problems are implied. Other threads for the short period of time see different global locale as well and thus might produce bad strings. And in the end it is impractical. It would be handy to have classic_lexical_cast as well as it could introduce some optimizations knowing that the requested locale is the classic one. Another thing is that it would be handy to introduce a function textual_convert (another example name) which would act like lexical_cast but would take the requested locale as a parameter (this is no longer a cast so it may). lexical_cast might take that locale as a second parameter with default value being the global locale so it could still be used just as any other casting. But I suppose this would not be well seen. Thus why not introduce a different function for that (or maybe there already is one?). It seems those changes would not be difficult to implement and could be hidden in the details of lexical_cast easily. What do you think of that? Finally lexical_cast's documentation might mention explicitly that current global locale is used as it does not mention that if I am not mistaken (I haven't found "locale" word in that document). Adam Badura


FWIW https://svn.boost.org/trac/boost/wiki/LibrariesUnderConstruction#Boost.Conve...
Great. But it seems this might take some time. While changes I proposed are quite simple requiring little work. As a proof of that I attach lexical_cast.hpp changed to cover what I proposed. I have added classic_lexical_cast which uses std::locale::classic() during the casting. Both version propagate std::locale object to be used. If traditional version is used a NULL pointer is propagated so nothing actually changes and overhead should be marginal. Adding a cat (or other function) which takes arbitrary object should be easy with this code however I have not done it since I don't need it. What do you think about those changes? Can they be included in Boost 1.40? Adam Badura

It seems posting the text file damaged it somewhat (some lines were broken inappropriately) so here is a ZIP version of the file. Adam Badura

This time bad file was zipped. So for the last time (I hope so...) the correct zipped file. Sorry for the messages "noise". Adam Badura

-----Original Message----- From: boost-bounces@lists.boost.org [mailto:boost-bounces@lists.boost.org] On Behalf Of Adam Badura Sent: 30 May 2009 17:44 To: boost@lists.boost.org Subject: Re: [boost] [lexical_cast] Locale used during conversion
changes I proposed are quite simple requiring little work. As a proof of that I attach lexical_cast.hpp changed to cover what I proposed. I have added classic_lexical_cast which uses std::locale::classic() during the casting. Both version propagate std::locale object to be used. If traditional version is used a NULL pointer is propagated so nothing actually changes and overhead should be marginal. Adding a cat (or other function) which takes arbitrary object should be easy with this code however I have not done it since I don't need it.
What do you think about those changes? Can they be included in Boost 1.40?
At a glance this all seems reasonable and useful, but I am sure everyone is concerned at the risk of causing collateral damage - because lexical_cast is so very, very widely used. Can anyone wanting the new features volunteer to try out your version? I'd like to see some other reports of successful use of this, not necessarily to test the locale features. Would it be wise to do this before unleashing it on trunk to make that it don't cause trouble in the nightly tests? Paul --- Paul A. Bristow Prizet Farmhouse Kendal, UK LA8 8AB +44 1539 561830, mobile +44 7714330204 pbristow@hetp.u-net.com

At a glance this all seems reasonable and useful, but I am sure everyone is concerned at the risk of causing collateral damage - because lexical_cast is so very, very widely used.
Can anyone wanting the new features volunteer to try out your version?
I'd like to see some other reports of successful use of this, not necessarily to test the locale features.
In my company I replaced inclusion of Lexical Cast with the file I posted here and used classic_lexical_cast where appropriate and everything seems fine. However indeed it would be better if someone else checked as well since lexical_cast may cause collateral damage. I made this change because of this in the first place (I was a victim of consequences of changing global locale when lexical_cast is widely used). And that is why I tried to make changes so that the call to lexical_cast executes the same code with except of few null pointers passed as parameters and few ifs checking (and doing nothing in result) those pointers.
Would it be wise to do this before unleashing it on trunk to make that it don't cause trouble in the nightly tests?
It likely would. However I don't know how to do that and whether I even may do that... Adam Badura
participants (3)
-
Adam Badura
-
Alexander Nasonov
-
Paul A. Bristow