Tuesday 15 March 2011

c++ - Deep copy of TCHAR array is truncated -



c++ - Deep copy of TCHAR array is truncated -

i've created class test functionality need use. class take deep re-create of passed in string , create available via getter. using visual studio 2012. unicode enabled in project settings.

the problem memcpy operation yielding truncated string. output so;

thisisatest: instancedataconstructor: testing testing 123 testing te_ready

where first line check of passed in tchar* string & sec line output populating allocated memory memcpy operation. output expected is; "testing testing 123".

can explain wrong here?

n.b. got #ifndef unicode typedefs here: how-to-convert-tchar-array-to-stdstring

#ifndef instance_data_h//if not defined #define instance_data_h//then define #include <string> //tchar typedef, depending on compilation configuration, either defaults char or wchar. //standard template library supports both ascii (with std::string) , wide character sets (with std::wstring). //all need typedef string either std::string or std::wstring depending on compilation configuration. //to maintain flexibility can utilize next code: #ifndef unicode typedef std::string string; #else typedef std::wstring string; #endif //now may utilize string in code , allow compiler handle nasty parts. string have constructors lets convert tchar std::string or std::wstring. class instancedata { public: instancedata(tchar* strin) : strmessage(strin)//constructor { //check passed in string string outmsg(l"thisisatest: instancedataconstructor: ");//l wide character string literal outmsg += strmessage;//concatenate message const wchar_t* finalmsg = outmsg.c_str();//prepare outputting outputdebugstringw(finalmsg);//print message //prepare tchar dynamic array. deep copy. chararrayptr = new tchar[strmessage.size() +1]; chararrayptr[strmessage.size()] = 0;//null terminate std::memcpy(chararrayptr, strmessage.data(), strmessage.size());//copy characters array pointed passed in tchar*. outputdebugstringw(chararrayptr);//print copied message check } ~instancedata()//destructor { delete[] chararrayptr; } //getter tchar* getmessage() const { homecoming chararrayptr; } private: tchar* chararrayptr; string strmessage;//is used conveniently ascertain length of passed in underlying tchar array. }; #endif//header guard

please pay attending next lines in code:

// prepare tchar dynamic array. deep copy. chararrayptr = new tchar[strmessage.size() + 1]; chararrayptr[strmessage.size()] = 0; // null terminate // re-create characters array pointed passed in tchar*. std::memcpy(chararrayptr, strmessage.data(), strmessage.size());

the 3rd argument pass memcpy() count of bytes copy. if string simple ascii string stored in std::string, count of bytes same of count of ascii characters.

but, if string wchar_t unicode utf-16 string, each wchar_t occupies 2 bytes in visual c++ (with gcc things different, windows win32/c++ code compiled vc++, let's focus on vc++). so, have scale size count memcpy(), considering proper size of wchar_t, e.g.:

memcpy(chararrayptr, strmessage.data(), strmessage.size() * sizeof(tchar));

so, if compile in unicode (utf-16) mode, tchar expanded wchar_t, , sizeof(wchar_t) 2, content of original string should deep-copied.

as alternative, unicode utf-16 strings in vc++ may utilize wmemcpy(), considers wchar_t "unit of copy". so, in case, don't have scale size factor sizeof(wchar_t).

as side note, in constructor have:

instancedata(tchar* strin) : strmessage(strin)//constructor

since strin input string parameter, consider passing const pointer, i.e.:

instancedata(const tchar* strin)

c++ arrays unicode deep-copy tchar

No comments:

Post a Comment