2

I have coded the following program in a borland c compiler.My doubt is why c compiler doesnot throw any error neither in compile time or run time.The program executes fine and the output is 2 4.

#include<stdio.h>
#include<conio.h>
int main(){
int a=2,b=4,c=6;
printf("%d%d",a,b,c);
getch();
return 0;
}

Even though there are less no of format specifiers than the number of arguments there is no error thrown.What is happening here.

Intriguing
  • 125
  • 3
  • 13
  • It just replaces the first two format specifiers with the first two variable values – Ahmed Salman Tahir Feb 09 '14 at 12:48
  • Get a better compiler: http://ideone.com/4cNhCg. – Oliver Charlesworth Feb 09 '14 at 12:49
  • That is why they say that enabling compiler warnings helps. – devnull Feb 09 '14 at 12:49
  • 1
    I think the important thing here is that `printf` is just a normal function, it (usually) doesn't get special treatment from the compiler. At it's core compiler doesn't have to make any association between format specifiers and arguments - all it sees is a string and a bunch of arguments that will get evaluated at run time - and will probably gladly accept things like trying to `printf` a `float` with `"%d"` etc. Though nowadays there are some compilers and code analysis tools that will warn you about this. – user2802841 Feb 09 '14 at 13:06
  • @user2802841 'printf' accepts 'float' value with a '%d' but for the following code the output is weird. 'float a=5.0; printf("%d",a); output is 0'. – Intriguing Feb 10 '14 at 01:41
  • Dup of [Passing too many arguments to printf](https://stackoverflow.com/questions/3578970/passing-too-many-arguments-to-printf) – Language Lawyer Jul 20 '20 at 22:33

5 Answers5

3

can there be less number of fomat specifier than the number of variables in a printf statement

Answer is yes. From the C Standard:

(c99, 7.19.6.1p2) "If the format is exhausted while arguments remain, the excess arguments are evaluated (as always) but are otherwise ignored."

ouah
  • 142,963
  • 15
  • 272
  • 331
2

That will work fine but may give a compiler error if your compiler is set to check printf varargs parameters.

The printf function is variadic, i.e. takes a variable number of arguments. The format string will dictate how many are used, and if you specify too many they will be ignored. The POSIX reference is: http://pubs.opengroup.org/onlinepubs/009695399/functions/printf.html which states:

If the format is exhausted while arguments remain, the excess arguments shall be evaluated but are otherwise ignored.

(the underlying C reference is C 2011 7.21.6.1 2 from http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf - thanks @EricPostpischil - but that's a 701 page PDF)

That is, however, rather obvious from how variadic functions work.

The opposite (having fewer variables than in your format specifier) is not permissible as the printf function will attempt to access variables that are not present on the stack, giving undefined behaviour.

abligh
  • 24,573
  • 4
  • 47
  • 84
  • That is not the C reference; it is a POSIX (IEEE 1003.1) reference. It is intended to be aligned with C but is not authoritative about C. A C reference is C 2011 7.21.6.1 2. – Eric Postpischil Feb 09 '14 at 13:53
  • @EricPostpischil - fair enough. In order to improve my answers, is there a better (i.e. HTML) reference to the C standard directly (as opposed to a derivative of it). I have http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf as referenced by http://www.open-std.org/jtc1/sc22/wg14/www/standards.html#9899 but as a 701 page PDF it's hardly friendly for pointing people at. – abligh Feb 09 '14 at 13:58
  • 1
    You can answer questions “informally” citing any source, as long as you do not say it is “the reference” for C. But I find the C standard to be quite readable for the most part. It is daunting at first, because it is organized differently from the way many people talk about C or even teach it in class, and it uses different terms (e.g., “objects” rather than “variables”). But those differences are useful because they are designed for technical precision. So it is worth becoming familiar with the standard. People teaching from the standard can help improve the knowledge of others. – Eric Postpischil Feb 09 '14 at 14:04
  • @EricPostpischil Thanks. *I've* no difficulty reading it. I was just hoping there was an HTML version online like the POSIX one so I could point people (who might be intimidated) directly at the relevant section, rather than pages of a PDF one needs to download. – abligh Feb 09 '14 at 14:07
  • Also, most of the 700 pages is the library and annexes. The core language is covered in the first 180 pages. – Eric Postpischil Feb 09 '14 at 14:12
  • The standards organizations control the C standard; it is copyright. As far as I know, they have not realized or given permission for an HTML version. – Eric Postpischil Feb 09 '14 at 14:14
1

Yes.

http://www.cplusplus.com/reference/cstdio/printf/

"There should be at least as many of these arguments as the number of values specified in the format specifiers. Additional arguments are ignored by the function."

cloudycliff
  • 299
  • 1
  • 8
  • That's the C++ standard, not the C standard. This is a C question. I realise the answer is the same. – abligh Feb 09 '14 at 12:53
  • @abligh: The C++ standard defers to the C standard for the definition of C standard-library functions. – Oliver Charlesworth Feb 09 '14 at 12:54
  • @OliCharlesworth I know. But given the questioner asked a question about C presumably under POSIX, not C++, isn't the correct answer to refer to the C standard (or POSIX standard) not the C++ one (even if it does defer to the C standard). I did not downvote the answer ... – abligh Feb 09 '14 at 12:57
  • @abligh: It is not even the C++ standard. It is some third-party site about C++, registered to Juan Soulie. – Eric Postpischil Feb 09 '14 at 13:51
0

Though you have provided three variables to printf() but only two format specifiers are there, so those two are replaced with the first two available variables.

Ahmed Salman Tahir
  • 1,783
  • 1
  • 17
  • 26
0

Because you have function that accepts a variable number of arguments

int printf ( const char * format, ... );

In C, it's mean that there is no arguments type checking and, even more, printf does not know how much arguments user pass to the function. There is a trick - printf counts the number of % and decide that it's the number of arguments. To understand how it work you can look to the va_list, va_start , va_end, va_arg. Try to run printf("%i,%i,%i", a); - Undefined Behavior.

grisha
  • 1,247
  • 1
  • 14
  • 20
  • Why would he want to run code that invokes undefined behavior? – Filipe Gonçalves Feb 09 '14 at 13:12
  • Amm, to understand that _printf_ (most variadic functions) focuses only on _format_ arg and thay don't know about real arguments count. Is it bad method to show this ? – grisha Feb 09 '14 at 13:23
  • For me it's a bad method, because any conclusions you draw from code with undefined behavior are invalid - by definition, undefined behavior means anything can happen. – Filipe Gonçalves Feb 09 '14 at 13:29
  • This answers the wrong question. The question asks about fewer conversion specifiers than arguments after the format string. `printf("%i", a, a)` does not have undefined behavior (assuming `a` has a suitable type). – Eric Postpischil Feb 09 '14 at 13:49
  • Latest C standard: 7.16.1.1 The va_arg macro: If there is no actual next argument, or if type is not compatible with the type of the actual next argument (as promoted according to the default argument promotions), the behavior is undefined – grisha Feb 09 '14 at 14:27