CString( 七 )

你还可以根据 vt 域的不同来建立更通用的转换例程 。为此你可能会考虑:CString VariantToString(VARIANT * va){CString s;switch(va->vt){ /* vt */case VT_BSTR:return CString(vaData->bstrVal);case VT_BSTR | VT_BYREF:return CString(*vaData->pbstrVal);case VT_I4:s.Format(_T("%d"),va->lVal);return s;case VT_I4 | VT_BYREF:s.Format(_T("%d"),*va->plVal);case VT_R8:s.Format(_T("%f"),va->dblVal);return s;... 剩下的类型转换由读者自己完成default:ASSERT(FALSE); // unknown VARIANT type (this ASSERT is optional)return CString("");} /* vt */}字元资源如果你想创建一个容易进行语言版本移植的应用程式,你就不能在你的原始码中直接包含本土语言字元串 (下面这些例子我用的语言都是英语,因为我的本土语是英语),比如下面这种写法就很糟:CString s = "There is an error"; 你应该把你所有特定语言的字元串单独摆放(调试信息、在发布版本中不出现的信息除外) 。这意味着向下面这样写比较好:s.Format(_T("%d - %s"),code,text);在你的程式中,文字字元串不是语言敏感的 。不管怎样,你必须很小心,不要使用下面这样的串:【CString】// fmt is "Error in %s file %s"// readorwrite is "reading" or "writing"s.Format(fmt,readorwrite,filename);这是我的切身体会 。在我的第一个国际化的应用程式中我犯了这个错误,儘管我懂德语,知道在德语的语法中动词放在句子的最后面,我们的德国方面的发行人还是苦苦的抱怨他们不得不提取那些不可思议的德语错误提示信息然后重新格式化以让它们能正常工作 。比较好的办法是使用两个字元串,一个用于读,一个用于写,在使用时载入合适的版本,使得它们对字元串参数是非敏感的 。也就是说载入整个格式,而不是载入串"reading","writing":// fmt is "Error in reading file %s"// "Error in writing file %s"s.Format(fmt,filename);一定要注意,如果你有好几个地方需要替换,你一定要保证替换后句子的结构不会出现问题,比如在英语中,可以是主语-宾语,主语-谓语,动词-宾语的结构等等 。在这里,我们并不讨论 FormatMessage,其实它比 sprintf/Format 还要有优势,但是不太容易和CString 结合使用 。解决这种问题的办法就是我们按照参数出现在参数表中的位置给参数取名字,这样在你输出的时候就不会把他们的位置排错了 。接下来我们讨论我们这些独立的字元串放在什幺地方 。我们可以把字元串的值放入资源档案中的一个称为 STRINGTABLE 的段中 。过程如下:首先使用 Visual Studio 的资源编辑器创建一个字元串,然后给每一个字元串取一个ID,一般我们给它取名字都以 IDS_开头 。所以如果你有一个信息,你可以创建一个字元串资源然后取名为 IDS_READING_FILE,另外一个就取名为 IDS_WRITING_FILE 。它们以下面的形式出现在你的 .rc 档案中:STRINGTABLEIDS_READING_FILE "Reading file %s"IDS_WRITING_FILE "Writing file %s"END注意:这些资源都以 Unicode 的格式保存,不管你是在什幺环境下编译 。他们在Win9x系统上也是以Unicode 的形式存在,虽然 Win9x 不能真正处理 Unicode 。然后你可以这样使用这些资源:// 在使用资源串表之前,程式是这样写的:CString fmt;if(...)fmt = "Reading file %s";elsefmt = "Writing file %s";...// much laterCString s;s.Format(fmt,filename);// 使用资源串表之后,程式这样写:CString fmt;if(...)fmt.LoadString(IDS_READING_FILE);elsefmt.LoadString(DS_WRITING_FILE);...// much laterCString s;s.Format(fmt,filename);