none
CString VS std::string RRS feed

  • 问题

  • 很老套的问题,在网上搜了一些,还是想听听大家的意见.我是新手.

    先说我不想用CString的理由:
    1.我在写WTL的工程,非MFC.我在WTL的类库里面有用字符串相关的函数的情况,都是LPCTSTR 之类的.没有直接用CString.这种情况下,我用std:string与CString选择的话没有哪个会更好的理由.

    2.经过比较,我已经放弃使用TCHAR类型的函数,工程使用Unicode.我感觉这样更清晰,T类型的函数让我更迷惑,要不使用char* 要不就用wchar_t*.更心安些.CString也许在处理TCHAR一类的有些方便之处.在这种情况下也没用了

    3.我在使用一些网上的开源库的时候,别人的代码都是std:string.如果我使用CString.给我带来很多转换不方便.让我在写类函数接口时返回到底是是哪个.很纠结

    4.看到有人说CString比string快,.NET我都用了,我不在意那点性能.

    5.CString支持的方法的确比较string多.比如Format,很方便.我相信std:string肯定也有方法.我搜索即可.

    我还有必要使用CString么?我想放弃之了.

    学VC++给我最大的痛苦不是C++语言的复杂性.却是什么东西都让我选择,貌似选哪个都行,选哪个都不行.




    欢迎多交流http://solo.cnblogs.com
    2010年3月9日 2:04

答案

  • CString 最早是MFC 用户的最爱。十几年前,曾经是用户转向使用MFC 的一个重要理由。当然,CString 也有一些问题。 其实你今天说到的这个问题,可大可小。
    现就你的观点发表一下评论,一家之言,仅供参考:

    1) CString 历经MFC4.2 MFC7.1 MFC8.0 MFC9.0 多个版本,但仍然是MFC 的一部分,因此,使用CString 就意味着你需要包含MFC 的头文件,链接MFC 的库。WTL 也不是不能使用CString,但是使用了,就意味着程序编译后将占用更多的磁盘空间。我记得早期的ATL Wizard 中专门保留了一个用户是否使用MFC的选项,如果勾选,就自动会配置项目包含MFC 头文件。

    2) TCHAR 宏的最大好处是不用程序员因为字符编码的问题将一个算法实现两遍。在编译时,#define UNICODE #define ANSI 就好。如果你的函数声明直接使用了char 或者wchar_t 就代表你的声明确定唯一的使用了某个类型。如果你的代码需要被另外的代码引用,或者你的代码要使用别人的第三方代码,可能麻烦就来了。如果你的代码编译为UNICODE,而第三方代码是ANSI。那么势必有一方要承担转换字符编码的任务。

    3) 开源代码一般来说都是针对多平台的,即使在一个平台下也有多种界面库可供使用(MFC、WTL……),大家当然不会采用只在MFC 里面定义的CString。说到CString 和std::string 的转换,我觉得还好吧。 std::string有一个c_str() 方法返回当前字符串的指针。 CSting有一个GetString() 方法返回当前字符串的指针。互转应该一行代码就可以搞定。 至于函数声明,此时建议你使用TCHAR* 来声明字符串指针作为参数。这样一来,string::c_str() 或者 CString::GetString() 都可以不经任何转换作为传入参数了。ANSI 和UNICODE 问题也被TCHAR 宏轻而易举的解决了。

    4) CString string 谁快,这个不是一件很有定论的事情。因为使用场景不确定。 早期CString 比较土(MFC42 那个),现在的CString 是用模板技术重写过的,还用了类似COM 的技术缓存字符串。诸多改进之后,现在的CString 性能还算好吧。std::string的问题相对复杂些。 因为ISO 定义的是文本规范。各个厂商都有自己的std::string 实现。std::string 性能问题就跟使用的操作系统平台,厂商算法的实现有关了。 这里有两个忠告: 1. 没事儿别把CString和std::string 声明为全局对象,这对你程序的性能确实有很大影响,编译器在这种情况下,基本上没法帮你做代码优化; 2. 用std::string 就要学会用好迭代器(iterator)。

    5) 这纯属是使用习惯问题。
    • 已标记为答案 Haozes 2010年3月11日 1:30
    2010年3月9日 3:01
    版主
  • 如果在MFC内部建议使用CString,比较方便。但是std::string 的跨平台性要比CString强很多。 CString可用的算法感觉比std::string要多。CString支持COW std::string,我不能确定是否支持COW。总的来说两者各有利弊。另外对于接口最好使用字符串数组或std::string。而不要用CString。
    麻烦把正确答案设为解答。
    • 已标记为答案 Haozes 2010年3月11日 1:30
    2010年3月10日 2:05
    版主

全部回复

  • CString 最早是MFC 用户的最爱。十几年前,曾经是用户转向使用MFC 的一个重要理由。当然,CString 也有一些问题。 其实你今天说到的这个问题,可大可小。
    现就你的观点发表一下评论,一家之言,仅供参考:

    1) CString 历经MFC4.2 MFC7.1 MFC8.0 MFC9.0 多个版本,但仍然是MFC 的一部分,因此,使用CString 就意味着你需要包含MFC 的头文件,链接MFC 的库。WTL 也不是不能使用CString,但是使用了,就意味着程序编译后将占用更多的磁盘空间。我记得早期的ATL Wizard 中专门保留了一个用户是否使用MFC的选项,如果勾选,就自动会配置项目包含MFC 头文件。

    2) TCHAR 宏的最大好处是不用程序员因为字符编码的问题将一个算法实现两遍。在编译时,#define UNICODE #define ANSI 就好。如果你的函数声明直接使用了char 或者wchar_t 就代表你的声明确定唯一的使用了某个类型。如果你的代码需要被另外的代码引用,或者你的代码要使用别人的第三方代码,可能麻烦就来了。如果你的代码编译为UNICODE,而第三方代码是ANSI。那么势必有一方要承担转换字符编码的任务。

    3) 开源代码一般来说都是针对多平台的,即使在一个平台下也有多种界面库可供使用(MFC、WTL……),大家当然不会采用只在MFC 里面定义的CString。说到CString 和std::string 的转换,我觉得还好吧。 std::string有一个c_str() 方法返回当前字符串的指针。 CSting有一个GetString() 方法返回当前字符串的指针。互转应该一行代码就可以搞定。 至于函数声明,此时建议你使用TCHAR* 来声明字符串指针作为参数。这样一来,string::c_str() 或者 CString::GetString() 都可以不经任何转换作为传入参数了。ANSI 和UNICODE 问题也被TCHAR 宏轻而易举的解决了。

    4) CString string 谁快,这个不是一件很有定论的事情。因为使用场景不确定。 早期CString 比较土(MFC42 那个),现在的CString 是用模板技术重写过的,还用了类似COM 的技术缓存字符串。诸多改进之后,现在的CString 性能还算好吧。std::string的问题相对复杂些。 因为ISO 定义的是文本规范。各个厂商都有自己的std::string 实现。std::string 性能问题就跟使用的操作系统平台,厂商算法的实现有关了。 这里有两个忠告: 1. 没事儿别把CString和std::string 声明为全局对象,这对你程序的性能确实有很大影响,编译器在这种情况下,基本上没法帮你做代码优化; 2. 用std::string 就要学会用好迭代器(iterator)。

    5) 这纯属是使用习惯问题。
    • 已标记为答案 Haozes 2010年3月11日 1:30
    2010年3月9日 3:01
    版主
  • 搭车问一句 :“1. 没事儿别把CString和std::string 声明为全局对象,这对你程序的性能确实有很大影响,编译器在这种情况下,基本上没法帮你做代码优化; ” 你指“全局” 包不包括 类的成员 ? 
    2010年3月9日 3:56
  • 类成员会好些吧。 我好多年以前,做过类似实验。
    2010年3月9日 4:04
    版主
  • 谢谢你的指导.
    也许问题就像这个帖子所说:
    The more you seek a simple answer, the harder this problem will get. The
    answer would be simple if you had enough evidence to back up your decision.
    到底用哪个还是取决于实际项目.我先尝试全部使用std:string. 在实践中证明选择是否正确.

    欢迎多交流http://solo.cnblogs.com
    2010年3月9日 5:59
  • 如果在MFC内部建议使用CString,比较方便。但是std::string 的跨平台性要比CString强很多。 CString可用的算法感觉比std::string要多。CString支持COW std::string,我不能确定是否支持COW。总的来说两者各有利弊。另外对于接口最好使用字符串数组或std::string。而不要用CString。
    麻烦把正确答案设为解答。
    • 已标记为答案 Haozes 2010年3月11日 1:30
    2010年3月10日 2:05
    版主