2011-05-20 202 views
5

好吧,所以我最近做出了將我的應用程序中的每個字符串放入STRINGTABLE的決定,所以我可以很容易地翻譯成不同的語言。 我知道如何使用LoadString()api,但是這涉及到我想要加載的每個字符串都有一個不同的變量,如果我的應用程序有100個字符串,那就是很多變量。這是做這件事的最好方法嗎?或者我應該創建一個全局變量,用作緩衝區來根據需要加載字符串?另外,既然沒有辦法知道我的字符串有多大,我應該創建一個足夠大的緩衝區來容納我可能擁有的任何字符串,或者有更好的方法來做到這一點?C++ win32從資源加載字符串

還正在根據需要加載字符串性能不好?有什麼方法可以預先加載它們嗎?

RE:好吧我試圖創建一個緩衝區的大小爲256字節,並加載字符串放到需要,但我遇到了一個小問題...

這裏是我的代碼多數民衆贊成顯示錯誤消息,錯誤是「錯誤分配內存!」

LoadString(g_hInst, IDS_ERROR_MEMORY, szBuffer, sizeof(szBuffer)/sizeof(TCHAR)); 
MessageBox(NULL, szBuffer, TEXT("Error"), MB_OK | MB_ICONERROR); 
ExitProcess(1);

我有我的緩衝區作爲一個全局變量:TCHAR szBuffer[256];

這工作,但我還想給「錯誤」的文字也存儲到字符串表並加載,當我想要顯示的錯誤,問題是這將需要我有2個全局變量來加載字符串,並且有一些地方我需要加載更多,然後在一次。

是否有更好的解決方案,然後有多個全局變量?

+0

使用支持本地化的GUI框架會容易得多 – 2011-05-20 18:22:24

回答

4

如果您願意,您當然可以預先加載它們。你只需要創建一個字符串指針數組並將每個字符串加載到該數組中。或者你可以使用哈希映射或類似的東西。

性能不好?這取決於。如果您將這些字符串顯示爲用戶界面中的提示,我不會看到如何加載每個字符串,因爲它將是一個性能問題。無論如何,操作系統會做一些智能緩存,所以它不會像你需要顯示的每一個字符串一樣敲擊磁盤。另一方面,如果你要在緊密的循環中處理這些字符串,那麼最好將它們預加載到內存中,這樣就不必一直呼叫LoadString

就緩衝區而言,我總是分配一個緩衝區,它的大小與我在資源文件中預期的最大字符串一樣大。考慮到用戶界面字符串通常非常小,256字節的緩衝區就足夠了。任何比這更大的東西,我要麼在啓動時預先加載到內存中,這樣我可以保留它,或者我編寫了一個單獨的方法,在加載時分配一個字符串,而不是保留一個緩衝區。

附加信息:

而不是定義你的字符串的全局變量,可以考慮寫一個加載資源串,使得它的拷貝,複製了返回的功能。那就是:

char * LoadStringFromResource(uint id) 
{ 
    // szBuffer is a globally pre-defined buffer of some maximum length 
    LoadString(ghInst, id, szBuffer, bufferSize); 
    // yes, I know that strdup has problems. But you get the idea. 
    return strdup(szBuffer); 
} 

您的代碼,就變成了:

char* errMem = LoadStringFromResource(IDS_ERROR_MEMORY); 
char* errText = LoadStringFromResource(IDS_ERROR_TEXT); 
MessageBox(NULL, errMem, errText, MB_OK | MB_ICONERROR); 
free(errMem); 
free(errText); 

以上是C代碼,但是你可以很容易地轉換爲C++。特別是,你可能想要修改包裝函數,以便它返回一個C++字符串 - 當它超出作用域時(使用智能指針或任何現代等價物),它將自動釋放。

+0

感謝這很好。 – Josh 2011-05-20 19:21:49

+0

'strdup()'不是ISO C標準的一部分,它更像是Posix。 MinGW接受它在GNU C方言中編譯。 – Salvador 2014-06-19 02:24:48

+2

哇。因爲我在示例中使用了'strdup',因此降低了投票率?苛刻。我甚至評論了我的使用情況,以防止因此而遭到批評。好吧。不討人喜歡。 – 2014-06-19 12:07:22