converting char to int

I have a function that returns a file name as a char. I need to pass that file name onto another function that wants it as unsigned short int. How do I convert from char to unsigned short int?

All integer types are assignment-compatible.
1
2
3
char c = 'A';
int i = c;  // works fine
printf( "%c %d\n", c, i );


I'm a bit confused as to what you mean by converting a filename to an integer. A filename is a string of characters (byte-sized integers).
Thanks for the quick reply. I try to explain my problem better.

Most of my experience is with Matlab, so I feel somewhat uncomfortable around types.
Anyway, the function I write is a c-program so that I can add functionality to Matlab. From Matlab, I get a filename as a char array. However, the documentation to the program I should supply the filename to says "The SDK is Unicode and therefore all strings are represented as unsigned short int*"

Would it therefore work if I did the following
1
2
3
4
//this would normally be an input coming from Matlab
char fileName []="C:\\data\\\\test230.ext";
unsigned short int fileNameUSI = fileName;
out = functionThatWantsFileNameAsInt(fileNameUSI)
Last edited on
Sorry for the late response. (Dinner comes first :-) I get it now.

ASCII maps directly onto Unicode, so all you need to do is widen each element of the array. Here's a little C89 function that will do it for you.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
#include <stdlib.h>
#include <string.h>

/* ascii_to_unicode
     Converts a char[] to a wchar_t[].
   returns
     A newly-malloc()ed string, or NULL on error.
     Don't forget to free() it when you are done with it!
 */
wchar_t* ascii_to_unicode( const char* source )
  {
  const char* sp;
  wchar_t*    result, rp;
  unsigned    length = strlen( source ) +1;
  if (!source) return NULL;
  result = malloc( length *sizeof( wchar_t ) );
  if (result)
    {
    for (sp = source, rp = result; *sp; sp++, rp++)
      *rp = *sp;
    *rp = 0;
    }
  return result;
  }

The line of interest is line 20. It takes the char value addressed by sp, widens it to a wchar_t value, and sticks it at the wchar_t addressed by rp.

Here's an example of use:
1
2
3
4
5
6
7
8
9
10
11
// This is the original filename in 7-bit ASCII
char     a_filename[] = "C:\\WINDOWS\\example.txt";

// Here it is converted to UTF-8
wchar_t* u_filename = ascii_to_unicode( a_filename );

// Use it as you like
some_matlab_function( u_filename );

// Don't forget to free memory when done
free( u_filename );

Hope this helps.

Oh, before I forget. The type of things is very important --even in MatLab. For example, you cannot divide a real by a matrix. Likewise, a rational number is entirely different than a real number. MatLab will let you convert between some automatically (say, real to integer --only the whole part is preserved) and some others it will try to give you a good approximation (say, rational to real), etc. (PS. I've never used MatLab...)

Good luck!
Last edited on
Your code works, though I don't quite understand why :) (note I had to modify the type of length, because the compiler was complaining).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
wchar_t* ascii_to_unicode( const char* source )
  {
  const char *sp;
  wchar_t    *result, *rp;
  size_t    length = strlen( source ) +1;
  if (!source) return NULL;
  result = new wchar_t [length];
  if (result)
    {
    for (sp = source, rp = result; *sp; sp++, rp++) // what kind of condition is *sp?
      *rp = *sp; // writes the content of where sp points into where rp points
    *rp = 0; // doesn't this overwrite the copying from the previous line??
    }
  return result;
  }


However, it gives me wchar_t, not unsigned short int. So the compiler still complains about it.

Can I then just recast like this (sorry, cannot test the output on the real function because there seems to be a problem with a library)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
size_t fileNameLength;
	const char fileName []="C:\\data\\test230.ext";
	unsigned short int *fileNameForElementsP;
	
	wchar_t *fileNameUnicodeP = ascii_to_unicode( fileName );
	// now recast to unsigned short
        fileNameLength = strlen( fileName ) + 1;
	fileNameForElementsP = new unsigned short int [fileNameLength];
	*fileNameForElementsP = (unsigned short int) *fileNameUnicodeP;

        // call the function
        thatStupidFunction(fileNameForElementsP);

        // free memory
        delete( fileNameUnicodeP);
        delete( fileNameForElementsP);


fileNameForElementsP seems to be 2n+1 the size of fileNameUnicodeP, which worries me. Should it?


PS: In Matlab, types are indeed somewhat important. For example, most functions are only defined for doubles. But you can divide a scalar by a matrix, since Matlab will automatically expand that scalar. For example 1./[1 2] returns [1 0.5].
Hmm, sorry.

You are thinking too hard. ;-] Don't do so much work.

Change all instances of wchar_t in my function to unsigned short int and MatLab should stop complaining. (My brain went "Unicode --> wchar_t" instead of what you asked for... :-S )

Then to use it:
1
2
3
4
5
6
7
8
  const char fileName[] = "C:\\data\\test230.ext";
  unsigned short int *fileNameForElementsP;

  fileNameForElementsP = ascii_to_unicode( fileName );

  thatStupidFunction( fileNameForElementsP );

  free( fileNameForElementsP );

Don't mix delete with malloc(). It is dangerous. Just use free().

You can't just cast the entire array because the size of the elements don't change. If wchar_t is four bytes long, casting it to unsigned short (two bytes) just means you are treating it as an array of twice as many elements (where every-other one is a null character, since you are splitting the wchar_ts in half).

Nice fix with the size_t!
*sp is checking to see if the character addressed by sp is null. It is equivalent to: *sp != '\0' *rp = *sp; exactly. :-)
*rp = 0; nope. Remember, rp gets incremented at the same time as sp, so if sp is pointing to the null-terminator (a value of zero signals the end of a string), then rp should also be pointing at a zero. But we exited the loop as soon as we found sp's zero, so we have to specifically terminate the result string with a zero.
Whew. I hope that made sense.

1./[1 2] --> [1 0.5]
Hmm.. That's cheezy matlab magic, I guess... Cool trick though!
Last edited on
Thanks a lot! It works like a charm now.

I used new/delete, because malloc doesn't return any output, and because even though I do oo programming in Matlab, I prefer functions that return something, instead of just messing with pointers.

*sp as a condition is pretty nifty! I think I could get to like c++.

As for the *rp = 0, thanks for the explanation. I guess that rp isn't pointing at the same address as in the previous line, correct?

Oh, and should you ever need some cheezy Matlab magic, I would gladly help you out :)

Topic archived. No new replies allowed.