No. of strings in format string specifier [duplicate] - c

This question already has answers here:
How does concatenation of two string literals work?
(4 answers)
Closed last year.
I have seen this way of using combination of strings in printf and scanf statements.
int a;
printf("Printing" "using" "multiple" "strings" "%d", a);
// The above is just an example, some usage that I saw was for printing specific integer types like int_32
// uint32_t var; printf("Value is %" PRTu32, var);
I always thought that we could only use a single string as a format specifier. Like as written in the definition of printf function it seems format can point to only one string.
int printf ( const char * format, ... );
So out of curiosity I tried the following code and it ran successfully!
char arr[] = "Hello " "World";
printf("%s",arr); // Output - Hello World
Could anyone explain how this concatenation thing works and what is the correct way of doing it. Any help is appreciated.

If you give a space or no space in between two string literals it concatenates the string literals.
That's one of the C feature: This is defined by the ISO C standard, adjacent string literals are automatically combined/concatinated into a single one.

Related

partial C String initialisation [duplicate]

This question already has answers here:
How does concatenation of two string literals work?
(4 answers)
Closed 1 year ago.
In some code I today read, a type of C-String initialisation existed which is new to me.
It chains multiple String-Initialisation like "A""B""C"...
It also allows splinting the String Initialisation to multiple Lines
I set up a small Hello World demo, so you can see what I am talking about:
#include <stdio.h>
#define SPACE " "
#define EXCLAMATION_MARK "!"
#define HW "Hello"SPACE"World"EXCLAMATION_MARK
int main()
{
char hw_str[] =
"Hello"
SPACE
"World"
"!";
printf("%s\n",hw_str);
printf("%s\n",HW);
return 0;
}
So here are some questions:
is this valid according to the standard?
why this works? "abc" is like a array {'a','b','c'} right?, so why are array initialisations concatenated over multiple pairs of "" working?
has this feature an official name - like when you enter it in google, you find some documentation describing it?
is this portable?
From the C Standard (5.1.1.2 Translation phases)
1 The precedence among the syntax rules of translation is specified by
the following phases.
Adjacent string literal tokens are concatenated
So for example this part of the program
char hw_str[] =
"Hello"
SPACE
"World"
"!";
that after macro substitutions looks like
char hw_str[] =
"Hello"
" "
"World"
"!";
is processed by the preprocessor in the sixth phase by concatenating adjacent string literals and you have
char hw_str[] =
"Hello World!";

C chars add themselves up for no reason [duplicate]

This question already has answers here:
Space for Null character in c strings
(5 answers)
Closed 3 years ago.
I think I'm going insane because I cannot find an explanation to why C is combining my chars.
I've made you guys a test programm...
#include <stdio.h>
#include <stdlib.h>
int main()
{
char alphabet_big[26] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
char alphabet_small[26] = "abcdefghijklmnopqrstuvwxyz";
printf("%s\n", alphabet_small);
return 0;
}
Results: abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZV
Why is C combining alphabet_small and alphabet_big? That's not making sense. And why is there a "V" at the end of the char?
I hope someone can provide me an answer to this "problem".
Best regards.
Keep in mind that a C String is defined as a null terminated char array.
Change the declaration and initialization statement here: (for both statements.)
char alphabet_big[26] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";//forces compiler to use only 26 char
//regardless of the count of initializers
//(leaving no room for NULL terminator)
To
char alphabet_big[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";//allows compiler to set aside
^^ //the proper space, no matter how many initializers
The first produces undefined behavior when using with any of the string functions, such as strcpy, strcmp, and in this case printf with the "%s" format specifier.
The first produces the following, which is not is not a C string:
|A|B|C|D|E|F|G|H|I|J|K|L|M|N|O|P|Q|R|S|T|U|V|W|X|Y|Z|?|?|?|
While the 2nd produces the following, which is a C string:
|A|B|C|D|E|F|G|H|I|J|K|L|M|N|O|P|Q|R|S|T|U|V|W|X|Y|Z|\0|?|?|
Note - The ? symbols used in above illustration depict memory locations that are not owned by the program, and for which the contents are unknown, or may not even exist. A program attempting to access these locations would be invoking undefined behavior.
Normally the library functions expect to find a NUL byte at the end of a string, and the compiler is happy to add it for you automatically except you've told it that alphabet_big has only 26 bytes, essentially avoiding that extra NUL byte, so it combines with what's next.
Remove the 26 and let the compiler count for you.

printf() working without double quotes, prints random characters [duplicate]

This question already has answers here:
Behaviour of printf when printing a %d without supplying variable name
(6 answers)
Closed 4 years ago.
I stumbled upon this C code in a college test and when I tested it on Dev-C++ 5.11 compiler, it printed random characters. I can't understand how or why this code works. Can someone enlighten me?
int main() {
char a[10] = "%s" ;
printf( a ) ;
}
This question has two parts: the missing quotes and the random characters.
printf() is just a function. You can pass strings and other values to functions as arguments. You don't have to use a literal. You can use both char *a = "something"; printf(a) (passing a variable as an argument) and printf("something") (passing a string literal as an argument).
printf() is also a variadic function. This means it can accept any number of arguments. You can use printf("hello world"), printf("%s", "hello world") and even printf("%s %s", "hello", "world"). Some older compilers don't verify you actually passed the right number of arguments based on the first argument which is the format string. This is why your code compiles even though it's missing an argument. When the program runs the code goes over the format string, sees "%s" and looks for the second argument to print it as a string. Since there is no second argument it basically reads random memory and you get garbage characters.
printf function signature is:
int printf(const char *format, ...);
It expects format string as the first argument and variable number of arguments that are handled and printed based on the format specifiers in the format string. variable a in your question is providing it the format string. Reason for random characters is that the argument for format specifier %s is missing. Following will correctly print a string:
printf( a, "Hello World!" );
A list of format specifiers can be seen here https://en.wikipedia.org/wiki/Printf_format_string
Why does it compile?
Because variadic arguments accepted by printf are processed at run time. Not all compilers do compile time checks for validating arguments against the format string. Even if they do they would at most throw a warning, but still compile the program.
It's using the string "%s" as a format string, and using uninitialized memory as the "data".
The only reason it does "something" is because the compiler was apparently not smart enough to recognize that the format string required one parameter and zero parameters were supplied. Or because compiler warnings were ignored and/or errors were turned off.
Just an FYI for anybody who bumps into this: "Always leave all warnings and errors enabled and fix your code until they're gone" This doesn't guarantee correct behaviour but does make "mysterious" problems less likely.

explanation of the output of the following program [duplicate]

This question already has answers here:
How is printf statement interpreted?
(5 answers)
Closed 5 years ago.
#include<stdio.h>
void main()
{
printf(5+"good morning");/*need explanation for this line
return 0;
}
The output of the program is - morning
can anyone explain how?
Prototype of printf
int printf(const char *format, ...);
Here format is a type of const char* and point to address of first element of string literal. When you pass 5+"Good morning" in printf, what you are really passing is the memory address of the string plus 5. The plus 5 means printing will start 5 chars beyond the start of the string, and the space after the word "Good",counts as a char.
when you call with 5+"good morning" parameter is converted to pointer. That means there is string constant "good morning" stored somewhere in the executable and compiler pass its pointer. something like this:
const char txt[]="good morning\0";
printf(5+txt);
So the printf will obtain the evaluated pointer txt+5 which bypassed first 5 characters in the string (as one char is single BYTE and single memory address on 8bit WORD addressing machines).
The output of the program is - morning
printf(5+"good morning");
prints the string inside the " ", overpassing the first five characters. So the first four characters g, o, o, d and the fifth character, the space, will be overpassed and the rest of the string will be printed.
Printf() method, is used to print the text in ()
It prints only "morning" and 5+ bypassed the initial 5 characters that is "g" "o" "o" "d" and a " " (space)

Why does adding a space between two strings concat the strings in c? [duplicate]

This question already has answers here:
Why allow concatenation of string literals?
(10 answers)
Closed 6 years ago.
Sorry if I am going to ask a very basic question. I tried to search for it but I have been unable to find any answer.
When I run the following code:
#include <stdio.h>
int main() {
char *temp = "sai" "krishna";
printf("%s\n", temp);
return 0;
}
it prints saikrishna
Can you kindly specify why it happens? Should not we use strcat or other concatenation techniques?
Can you please refer to any documentation relating to it and where we can use this technique?
It's a language feature. C allows string literals to get concatenated at compile-time. It can be handy when you have very long string literals stretching over several lines, or when you want to break up string literals containing hex escape sequences. (For example puts("\x42AD") will translate to character 0x42AD, which is likely nonsense and unintended, as opposed to puts("\x42" "AD") which will print BAD.
strcat and strcpy are for string handling in run-time. If you have two string literals, they are compile-time constants, and may as well get concatenated by the compiler in advance, to save execution time.

Resources