在VC 7下,我遇到这样的BUG:如下代码正常运行
CString line;char *p1=COLE2T(key);
char *p2=COLE2T(value);
line.Format("<name>%s</name>\n<text>%s</text>\n",p1,p2);这样改写就不行line.Format("<name>%s</name>\n<text>%s</text>\n",COLE2T(key),COLE2T(value));那位大虾能告诉我为什么?注意这是在VC 7下使用ATL 7.0 和 MFC 7.0,所以 CString 和 COLE2T 都与 VC 6 下的不同。

解决方案 »

  1.   

    不行的原因:
    你看过Format的原型定义吗?从它的第二个参数开始,都是没有确定的类型,所以编译器将一个COLE2T对象压入了堆栈,而Format却把它当作一个字符串(%s)取出来,当然会出错了。
    你应该这样写
    line.Format(_T("<name>%s</name>\n<text>%s</text>\n"),(LPCTSTR)COLE2T(key),(LPCTSTR)COLE2T(value));另外你的第一种写法也存在问题,你应该这样写
    COLE2T ole2tkey(key);      //应该先这样做,msdn上写得很清楚,你看一下
    COLE2T ole2tvalue(value);TCHAR *p1=ole2tkey;
    TCHAR *p2=ole2tvalue;
    line.Format(_("<name>%s</name>\n<text>%s</text>\n"),p1,p2);另请注意:COLE2T 中T的含义,unicode 下是unsigned short, mbcs下是char
    所以程序中应该使用TCHAR 而不是char, 并且对字符串应该使用_T宏。
      

  2.   

    对于编译器来说
    TCHAR* p1 = COLE2T(name);
    相当于
    TCHAR* p1;
    {
         COLE2T ole2ttemp(name);
         p1 = ole2t;
    }
    看出问题了吗?
      

  3.   

    不好意思,写错了对于编译器来说
    TCHAR* p1 = COLE2T(name);
    相当于
    TCHAR* p1;
    {
         COLE2T ole2ttemp(name);
         p1 = ole2ttemp;
    }
    看出问题了吗?
      

  4.   

    呵呵,我搞错了。  你是说其实是 ole2ttemp 这样的对象入栈了是吗。
    我正开始看《C++对象模型》,能否留个联系讨论的方式?
      

  5.   

    呵呵,p1 指针的值正确。在我所写的两个变量中 p1、p2 都是指向正确的数据。 呵呵,所以至少那些内存没有重新利用。或者说是“野指针”?我简单看了看CW2A的代码,它用malloc分配空间,析构的时候使用free,所以我觉得这个类(是 ATL 7.0 的类,不是 3.0 的宏了)的有效期是函数内部。我理解你的意思了,因为是FORMAT无参数,所以就相当于COLE2T的类型直接入栈,没有 p1 = ole2ttemp; 这个转换的步骤了。是否?呵呵,可以继续讨论。我的信箱:[email protected]