Declare a static variable inside a function call in C ++

I have a C ++ program with many thousands of string literals in code that need to be translated, for example:

statusBar->Print( "My Message" ); 

I wrapped string literals with a function that searches for a value in a dictionary and returns the translated version:

 statusBar->Print( Translated( "My Message" ) ); 

The problem is that after profiling, I found that doing this search in all the code is a performance issue. What I would like to do is change the following lines:

 static const char * translatedMessage5 = Translated( "My Message" ); statusBar->Print( translatedMessage5 ); 

But due to the many thousands of instances of this code, it will be error prone (and a bit of a maintenance nightmare). I was hoping I could turn Translated into a macro that declares a static variable in a string. This is clearly not working. Anyone have a better idea?

+4
source share
3 answers

The I / O time required to print your message should be several orders of magnitude longer than any dictionary search time. If this is not the case, you are doing something wrong.

Trial and tested software that does what you need is available. I suggest you either learn the GNU Gettext , which is used by every other FOSS project there, or simply use it in your program instead of the homebrew solution.

EDIT : With C ++ 0x, you can do what you want, but still use the GNU Gettext as your real l10n engine. Here are some small code examples:

 #include <iostream> const char* realTranslate(const char* txt) { std::cout << "*** translated " << txt << std::endl; return txt; // use a real translation here such as gnu gettext } #define Translate(txt) \ (([]()->const char* \ {static const char* out = realTranslate(txt); return out;})()) int main () { for (int i = 0; i < 10; ++i) { std::cout << Translate("This is a message") << std::endl; std::cout << Translate("This is a message") << std::endl; std::cout << Translate("This is another message") << std::endl; } } 

I'm not sure what the current C ++ standard will indicate, but under gcc-4.6, the realTranslate() function is called 3 times.

+3
source

Can you switch to unique error codes and index them into a vector? This simplifies code and search, and adding additional error messages becomes trivial. In addition, error messages added in this way are more noticeable (for example, an external application, for example, can easily be published in the User Guide or similar).

 #include <string> #include <vector> enum ErrorMessages { my_message, my_other_message, ... msg_high }; std::vector<std::string> error_messages; void init() { error_messages.resize(msg_high); error_messages[my_msg] = "My Message"; error_messages[my_other_msg] = "My Other Message"; ... } const char* const Translate(const ErrorMessage msg) { return error_messages[msg].c_str(); } void f() { statusBar->Print(Translated(my_msg)); } 
+3
source

This may not help you, but what you could do is declare std :: map, which will display a map of hash → text pairs. The question here is that computing a hash code on a string will be the same level of effort as translating it, and I don't know that.

 char * Translate(char *source) { static std::map<int, char*> sources; static std::map<int, char*> results; int hashcode = CalculateHashCode(source); std::map<int, char*>::const_iterator it = sources.find( source ); if ( it != sources.end() ) { return results[ hashcode ]; } ... code to translate ... results[ hashcode ] = translated; } 
0
source

All Articles