C++ append unsigned char to wstring - c++

I want to append an unsigned char to a wstring for debugging reasons.
However, I don't find a function to convert the unsigned char to a wstring, so I can not append it.
Edit:
The solutions posted so far do not really do what I need.
I want to convert 0 to "0".
The solutions so far convert 0 to a 0 character, but not to a "0" string.
Can anybody help?
Thank you.
unsigned char SomeValue;
wstring sDebug;
sDebug.append(SomeValue);

The correct call for appending a char to a string (or in this case, a wchar_t to a wstring) is
sDebug.push_back(SomeValue);
Documentation here.
To widen your char to a wchar_t, you can also use std::btowc which will widen according to your current locale.
sDebug.push_back(std::btowc(SomeValue));

Just cast your unsigned char to char:
sDebug.append(1, static_cast<char>(SomeValue));
And if you want to use operator+ try this:
sDebug+= static_cast<char>(SomeValue);
Or even this:
sDebug+=boost::numeric_cast<char>(SomeValue);

There's an overload of append that also takes the number of times to append the given character:
sDebug.append(1, SomeValue);
However, this will result in a conversion between unsigned char and wchar_t. Perhaps you want SomeValue to be a wchar_t.

wstring has a constructor that takes a char. That would create a wstring from a char which you can then append.

Related

Only first character is assigned converting LPCTSTR to char*

I'm completely new to C++. In my program there's a function which has to take a LPCTSTR as a parameter. I want to convert it into a char*. What I tried is as follows,
char* GetChar(LPCTSTR var){
char* id = (char*)var;
.....
}
But while debugging I noticed that only first letter of var is assigned to id.
What have I done wrong?
(I tried various answers in StackOverflow about converting LPCTSTR to char* before coming to this solution. None of them worked for me.)
UPDATE
What i want is to get full string pointed by var to be treated as char*
It is much more useful to just pick a character set (wchar_t, or char), and just stick to it, in your application, since trying to use TCHAR, when trying to support both, may cause you some headaches. To be fair, today, you can just, safely, use wchar_t (or WCHAR, since from the current types you are using, I suspect that you are using Windows headers).
The problem that you have, is because casting a pointer does not have any impact on its contents. And, since, typically wchar_t is 2 bytes in size, while char is 1 byte in size, storing the value, that fits inside a char, in wchar_t, leaves 2nd byte of wchar_t set to \0. And when you try to print null(\0)-terminated string of wchar_ts as a string of chars, the printing function reaches the \0 character after reading the first symbol, and assumes it is the end of the string. \0 character in wchar_t is 2 bytes long.
For example, the string
LPCWSTR test = L"Hi!";
is stored in memory as:
48 00 69 00 21 00 00 00
If you want to convert between the wchar_t version of the string to char version, or vice-versa, there exist some functions, that can do the conversion, and since I noticed that you probably are using Windows headers (from LPCTSTR define), those functions are WideCharToMultiByte/ MultiByteToWideChar.
You may now start to think: I am not using wchar_t! I am using TCHAR!
Typically TCHAR is defined in the following way:
#ifdef UNICODE
typedef WCHAR TCHAR;
#else
typedef char TCHAR;
#endif
So you could do similar handling in your conversion code:
template<int N>
bool GetChar(LPCTSTR var, char (&out)[N])){
#ifdef UNICODE
return WideCharToMultiByte (CP_ACP, 0, var, -1, out, N, NULL, NULL) != 0;
#else
return strcpy_s (out, var) == 0;
#endif
}
Note, the return value of GetChar function is true if the function Succeeds; false - otherwise.
You code has told the compiler to convert var (which is a pointer) into a pointer to a character and then assign that converted value to id. The only thing it converts is the pointer value. It doesn't make any changes to the thing var points to, copy it, or convert it. So you haven't done anything to the string var points to.
It's not clear what you're trying to do. But your code doesn't really do anything but convert a pointer value without changing or affecting the thing pointed to in any way.
When you convert a LPCTSTR (a long pointer to a const tchar string) to a char*, you get a char* that points to a CTSTR (a const tchar string). What use is that? What sense does that make?
Most probaby LPCTSTR is const wchar_t*, so if you cast it to char* (which is Undefined Behaviour - as var could point to literal), the LSB byte (wchar_t under Visual Studio is 16bits) of *var is zero so it is treated as '\0' - which indicates end of string. So in the end you get only one char.
To convert LPCTSTR to char* you can use wsctombs for example, see here: Convert const wchar_t* to const char*.
Here's an easy solution I found based on other answers given here.
char* GetChar(LPCTSTR var){
char id[30];
int i = 0;
while (var[i] != '\0')
{
id[i] = (char)var[i];
i++;
}
id[i] = '\0';
UPDATE
As mentioned in comments this is not a good way to solve this problem. But if someone has the same problem and cannot understand any other solution, this will help a bit.
Therefore I won't remove this answer.

C++ atoi with unsigned char

I got an unsigned char with the value of 1, I need to put this in a string like "1".
But if I try to put this directly into a stringstream it will get the value of char(1) and I need it to be "1".
I know that if I can get this into the function atoi it will return the "1" value.
But I tried to cast it to char and put it in the atoi function, but it throws an exception.
Already tried to put it in a string and them cast c_str() into atoi function, but without success yet.
If someone can help me I'll apreciate.
Simply cast a char to an int before inserting it into the std::stringstream:
ss << static_cast<int>(c);
This will treat the value of the char not as a character but as a numerical value.
I believe you're confusing two functions here.
You wish to convert an integer to a string.
atoi (ascii to integer) however takes a string and parses it into an integer, making "123" into 123.
You are looking for the itoa function here, which has this prototype:
char * itoa ( int value, char * str, int base );
In your case, this would look like this:
char Buf[10];
itoa(123, Buf, 10);
printf("%s", Buf); //Outputs 123
Please remember though, that itoa is not part of the standard, even though it is supported by some compilers. For a more standard-compliant version use:
sprintf(Buf, "%d", 123);
Of course all of this is plain C, but any C++ compiler will work with this all the same.
To convert a numeric value in the range [0,9] to the corresponding character, just add '0' to it. That's guaranteed to work on all systems.

how to convert char * to uchar16 in JNI C++

here's what I am trying to do:
typedef uint16_t uchar16_t;
uchar16_t buf[32];
// buf will contain timezone information like GMT-6, Eastern Daylight Time, etc
char * str = "Test";
for (int i = 0; i <= strlen(str); i++)
buf[i] = str[i];
I guess that's not correct since uchar16_t would contain 2 bytes and str contains 1 byte.
What is it that I am supposed to do ?
Strlen? buf[32]? Trying to destroy the universe?
You want to use a wstringstream.
std::wstringstream lols;
lols << "Test";
std::wstring cakes;
lols >> cakes;
Edit#Comment:
You shouldn't use strlen because any decent string system allows embedded zeros, and strlen is seriously slow. In addition, you didn't resize your buffer as needed, so if you had a string of size > 31 you would get a buffer overflow. In addition, you would have to (if you did dynamically size your buffer) manually free it afterwards. Both of these things are serious failings of the C string system. My example code makes your standard library writer do all the work and avoid all these problems for you.
That's actually OK if your string will always be ASCII. To do it correctly, the portable function is mbstowcs which assumes you're converting from the default locale or if you're on Windows then there's API functions that let you specify the source code page explicitly.
Your code will work, as long as str is ASCII; calling strlen() in the loop condition is probably a bad idea, though. It might be easier to just use swprintf() if it's available on your system:
uchar16_t buf[32];
char *str = "Test";
swprintf(buf, sizeof buf, "%s", str);
Have a look here.
Also, is there a good reason you are defining your own type?
If you have a (narrow) char string, you cannot convert it to
a wchar_t string by setting your locale to "C" and then passing
the string through mbstowcs(). That's because the "C" locale specifies
a -particular- character encoding, and that encoding might not match
the encoding of the execution character set, so mbstowcs() might
map the characters to something unexpected, or could even fail
(if the execution character set happened to use encodings that
were incompatible with the encoding structure for the C locale
character set.)
Thus, in order to convert a char
string into a wider string, you have
to copy the chars one by one into an
array of wchar_t . If you need to work
with Unicode or utf-16 or whatever
after that, then wcstombs() is what
you should look at.

How to sprintf an unsigned char?

This doesn't work:
unsigned char foo;
foo = 0x123;
sprintf("the unsigned value is:%c",foo);
I get this error:
cannot convert parameter 2 from
'unsigned char' to 'char'
Before you go off looking at unsigned chars causing the problem, take a closer look at this line:
sprintf("the unsigned value is:%c",foo);
The first argument of sprintf is always the string to which the value will be printed. That line should look something like:
sprintf(str, "the unsigned value is:%c",foo);
Unless you meant printf instead of sprintf.
After fixing that, you can use %u in your format string to print out the value of an unsigned type.
Use printf() formta string's %u:
printf("%u", 'c');
EDIT
snprintf is a little more safer. It's up to the developer to ensure the right buffer size is used.
Try this :
char p[255]; // example
unsigned char *foo;
...
foo[0] = 0x123;
...
snprintf(p, sizeof(p), " 0x%X ", (unsigned char)foo[0]);
I think your confused with the way sprintf works. The first parameter is a string buffer, the second is a formatting string, and then the variables you want to output.
You should not use sprintf as it can easily cause a buffer overflow.
You should prefer snprintf (or _snprintf when programming with the Microsoft standard C library). If you have allocated the buffer on the stack in the local function, you can do:
char buffer[SIZE];
snprintf(buffer, sizeof(buffer), "...fmt string...", parameters);
The data may get truncated but that is definitely preferable to overflowing the buffer.

Storing an integer into a char* in C++

I'm writing some code that returns an integer, which then needs to be outputted using printw from the ncurses library. However, since printw only takes char*, I can't figure out how to output it.
Essentially, is there a way to store a integer into a char array, or output an integer using printw?
printw() accepts const char * as a format specifier. What you want is
printw("%d",yournumber);
The itoa function converts an int to char*.
Use itoa() or sprintf() to convert integer to ascii string.
Example:
char s[50];
sprintf(s, "%d", someInteger);
now u can pass s as char*
itoa will help you.