Hex in char array - c

If the following is a one byte array:
char arr[] = "\xFF";
If we do the following:
char arr[] = "\xFFmyrandomstringappendedafterbyte";
printing it would result in this:
byteValueGoesHEREmyrandomstringappendedafterbyte
However, if I try to do the following:
char arr[] = "\xFF98";
It will result in a warning:
warning: hex escape sequence out of range
It treats 98 as part of the hexcode. However, I would it to be treated as a string (as is myrandomstringappendedafterbyte).
I would like to have this as output byteValueGoesHERE98.
How can this be achieved without a whitespace? How can I denote that 98 should be treated as a string?

When string literals have only whitespace (or nothing) between them, the preprocessor combines them into a single string literal, but this does not "merge" escape sequences. So you can just write your desired string using two strings:
char arr[] = "\xFF" "98";
This is four bytes including the terminating '\0'.

Related

Are there other ways to specify or enter a Unicode code point in C other than using string literals?

In the following program I am trying to provide a Unicode code point to the ncurses function setcchar() as an array string instead of as a string literal. However the output that I'm getting is the first character of the array only, namely the backslash character.
Is there another way to specify a Unicode code point other than as a string literal? And why are the two expressions L"\u4e09" and wcsarr not producing the same result in this context...
#define _XOPEN_SOURCE_EXTENDED 1
#include <curses.h>
#include <stdio.h>
#include <stdlib.h>
#include <locale.h>
#include <wchar.h>
#include <time.h>
int main() {
setlocale(LC_ALL, "");
cchar_t kanji;
wchar_t wcsarr[7];
wcsarr[0] = L'\\';
wcsarr[1] = L'u';
wcsarr[2] = L'4';
wcsarr[3] = L'e';
wcsarr[4] = L'0';
wcsarr[5] = L'9';
wcsarr[6] = L'\0';
initscr();
setcchar(&kanji, wcsarr, WA_NORMAL, 5, NULL);
addstr("Code point entered as an array string: ");
add_wch(&kanji);
addstr("\n");
setcchar(&kanji, L"\u4e09", WA_NORMAL, 5, NULL);
addstr("Code point entered as a string literal: ");
add_wch(&kanji);
addstr("\n");
refresh();
getch();
endwin();
return EXIT_SUCCESS;
}
An array containing the six characters \u4e09 is an array containing six characters, just as an array containing a backslash followed by an n is an array of two characters, not a newline. The compiler converts escape sequence in literals. Nothing (except what you yourself write) does anything to character arrays.
So your array wcsarr is not a single wide character. It's a (null-terminated) wide string using six wchar_t values to encode six ascii characters. setcchar requires that its second argument contain only one spacing character (possibly followed by several non-spacing combining characters), and your program does not conform to this specification.
You could do something like this:
wchar_t wcsarr[] = {0, 0};
wcsarr[0] = L'\u4e09`;
If you knew that your locale used Unicode code points as wide character codes, you could write:
wcsarr[0] = 0x4e09;
since wchar_t, like char, is an integer type. That's occasionally useful if you need to compute a character code (such as non-latin digits), but normally it's considered better style to use wide character literals.
If you really need to decode a character string containing an escape sequence, you'll need to verify that the syntax is correct and then use something like strtol with the base parameter set to 16. Note, however, that strtol does not have any mechanism to restrict its argument to exactly four digits, so if the escape sequence appears in text where it might be followed by what looks like a hexadecimal digit, you will have to somehow extract it. Either copy it to a temporary buffer, or null-terminate it if the character string can be modified. Or you could write your own hexadecimal decoder; it's not hard.

printf variable placeholder? Is it even a thing?

#include <stdio.h>
char pos[] = {34,92,48,51,51,91,57,59,57,72,37,115,34}; // "\033[9;9H%s"
main() {
printf(pos,"Aaaaaaa"); // (1) This doesnt work as intended
printf("\033[9;9H%s","Aaaaaaa"); // (2) Works as intended
}
So why (2) works and (1) doesn't?
There are two problems with pos.
First what you have is a character array, not a null terminated string. You need to add a 0 to the end of that array.
Second, you don't have the same characters. In the string literal "\033[9;9H%s" there are a total of 8 characters while pos has 13.
The sequence \033 represent a single character whose value is 33 octal or 27 decimal. You instead have the literal characters '\', '0', '3', and '3'. So replace 92,48,51,51 with 27. Also, you have 34 for the first and last characters in pos, which is the double quote character ". These characters are not part of the string literal but are used to denote it in code. So get rid of those.
pos should now look like this:
char pos[] = {27,91,57,59,57,72,37,115,0};
You've got three differences:
You don't need the initial and final 34 character ("), since string (2) doesn't print them out.
You need a null terminator to ensure that you print only your string and nothing more.
If \033 is meant to be an escape character, then its value is just 27, not 92,48,51,51.
After addressing those differences, your pos array:
{34,92,48,51,51,91,57,59,57,72,37,115,34}
Should instead look like this (aligned to match the original array):
{27,91,57,59,57,72,37,115,0}

Can't initialize char array to a variable in c

While using Turbo c++ initializing array of char variable getting error code as follows
int gd=DETECT,gm,i,d=0,x,y;
char s[12]={"3","4","5","6","7","8","9","10","11","12","1","2","\0"};
initgraph(&gd,&gm,"..\\BGI");
but while used to initialize s[12][3], the initializer list works fine!
There is a difference between "3" and '3'.
"3" is a string literal
'3' is a character constant (to nitpick: integer character constant)
here, to initialize an array of char type, you seem to need (brace-enclosed) list of character constants, not strings.
but while using s[12][3] works fine
Well, there you're initializing arrays.
Moral of the story: When in doubt, check the data types!!
You need to change:
char s[12]={"3","4","5","6","7","8","9","10","11","12","1","2","\0"};
to
char s[13]={'3','4','5','6','7','8','9','10','11','12','1','2','\0'};
As char array elements should be char literals not string literals
You are trying to store chars, not strings, so why do you use double quotes?
"a" is a string, 'a' is a character.
What you actually want to store is strings, and for that you need a 2D array, like this:
s[12][3] = {"3","4","5","6","7","8","9","10","11","12","1","2"};
You cannot express 10 as a single character, I mean '10' does not exist. Single characters are from 0 to 9 when it comes to digits. For that reason, you need a string for 10, like this "10".
Now, you need the second dimension of your array to be 3, because the string "10" (for example) is a null-terminated string, thus 2 characters for its actual contents, plus one for the null-terminator, gives as 3.
PS: Turbo-C++ is an ancient compiler. Upgrade to GCC or anything else, really.

Does C omit the placement of the null character in a string constant if i explicitly place it for myself, or will it still add it?

Suppose you have this code:
char word[] = "Hello!\0"
Will the word array have one or two terminating null characters?
The string literal always appends a nul ('\0') byte unless you specified the size of the array, so you will have two nul bytes in the string "Hello!\0". If you wrote char word[7] = "Hello!\0" you would only have one nul byte in the array, since the size is now restricted to seven characters.
According to the C Standard (6.4.5 String literals)
6 In translation phase 7, a byte or code of value zero is appended
to each multibyte character sequence that results from a string
literal or literals.78) The multibyte character sequence is then
used to initialize an array of static storage duration and length just
sufficient to contain the sequence. For character string literals, the
array elements have type char, and are initialized with the individual
bytes of the multibyte character sequence....
And (6.7.9 Initialization)
14 An array of character type may be initialized by a character string
literal or UTF−8 string literal, optionally enclosed in braces.
Successive bytes of the string literal (including the terminating
null character if there is room or if the array is of unknown size)
initialize the elements of the array.
You can check it yourself running the following code snippet
char word[] = "Hello!\0";
printf( "%zu\n", sizeof( word ) );
The output will be equal to 8.
it will add a terminator automaticly however when you want to print the word or use any function that stop when it detict \0 it will stop there .
example : string x = "loop007" ; if you print it the result would be the same loop007
however string x = "loo\0p007" will only print "loo" since the compiler has found the terminator even though it is not the right on .
long story short , yes it adds it eventhough you have assigned one allready .
Will the word array have one or two terminating null characters?
char word[] = "Hello!\0"
The array will have 2 terminating null characters and a size of 8.
The string located at the start of word[] will have 1 terminating null character. The '\0' after the string is not part of that string.
In C, string literals may contain many '\0's. The size of the string literal includes the coded characters and an appended null character: '\0',
printf("%zu\n", sizeof("Hello!\0Hello!\0Hello!\0Hello!\0"));
printf( "%zu\n", sizeof("Hello!\0" "Hello!\0" "Hello!\0" "Hello!\0"));
// both output 4*7+1 = 29
When initializing an character array with an unspecified length, the array size matches the size of the string literal.
char word[] = "Hello!\0Hello!\0Hello!\0Hello!\0"
printf("%zu\n", sizeof word);
// output 4*7+1 = 29
When printing a string (note this is not the same as string literal), printing continues up to, but not including the first encountered '\0'.
printf("[%s]\n", word);
// output [Hello!]
Pedantic detail: char word[] = "Hello!\0" contains a string literal, not string consonant.

char Array problem in C

char label[8] = "abcdefgh";
char arr[7] = "abcdefg";
printf("%s\n",label);
printf("%s",arr);
====output==========
abcdefgh
abcdefgÅ
Why Å is appended at the end of the string arr?
I am running C code in Turbo C ++.
printf expects NUL-terminated strings. Increase the size of your char arrays by one to make space for the terminating NUL character (it is added automatically by the = "..." initializer).
If you don't NUL-terminate your strings, printf will keep reading until it finds a NUL character, so you will get a more or less random result.
Your variables label and arr are not strings. They are arrays of characters.
To be strings (and for you to be able to pass them to functions declared in <string.h>) they need a NUL terminator in the space reserved for them.
Definition of "string" from the Standard
7.1.1 Definitions of terms
1 A string is a contiguous sequence of characters terminated by and including
the first null character. The term multibyte string is sometimes used
instead to emphasize special processing given to multibyte characters
contained in the string or to avoid confusion with a wide string. A pointer
to a string is a pointer to its initial (lowest addressed) character. The
length of a string is the number of bytes preceding the null character and
the value of a string is the sequence of the values of the contained
characters, in order.
Your string is not null terminated, so printf is running into junk data. You need to use the '\0' at the end of the string.
Using GCC (on Linux), it prints more garbage:
abcdefgh°ÃÕÄÕ¿UTÞÄÕ¿UTÞ·
abcdefgabcdefgh°ÃÕÄÕ¿UTÞÄÕ¿UTÞ·
This is because, you are printing two character arrays as strings (using %s).
This works fine:
char label[9] = "abcdefgh\0"; char arr[8] = "abcdefg\0";
printf("%s\n",label); printf("%s",arr);
However, you need not mention the "\0" explicitly. Just make sure the array size is large enough, i.e 1 more than the number of characters in your strings.

Resources