I read in a lot of books the claim that "C is a subset of C++".
Actually some (good?) books say: "C is a subset of C++ except the little Details".
I am interested what these details are. I've never seen one.
I read in a lot of books the claim that "C is a subset of C++".
Actually some (good?) books say: "C is a subset of C++ except the little Details".
I am interested what these details are. I've never seen one.
There are plenty of things. Just a simple example (it should be enough to prove C is not a proper subset of C++):
int* test = malloc(100 * sizeof(int));
should compile in C but not in C++.
Wikipedia has a good summary of the differences: Compatibility of C and C++
In C, sizeof('a')
is equal to sizeof(int)
.
In C++, sizeof('a')
is equal to sizeof(char)
.
#include <stdio.h>
int new (int n) {
return n/2;
}
int main(void) {
printf("%d\n", new(10));
return 0;
}
See also the C++ FAQ entry.
C++ has new keywords as well. The following is valid C code but won't compile under C++:
int class = 1;
int private = 2;
int public = 3;
int virtual = 4;
The single biggest difference I think is that this is a valid C source file:
int main()
{
foo();
}
Note that I haven't declared foo
anywhere.
Aside from language differences, C++ also makes some changes to the library that it inherited from C, e.g. some functions return const char *
instead of char *
.
One of the original design goals of C++ was to be a superset of C so every valid C program will be a valid C++ program (the only reason C++ is based on the C syntax is to provide an easy migration path from the then most popular programing language).
but that was a long time ago and both the C and C++ standards have advanced a long way and in different directions - so it's no longer true
A full detailed list, with citations to the various C and C++ standards, can be found here: Incompatibilities between ISO C and ISO C++.
In C++, if you declare a struct
, union
, or enum
, its name is immediately accessible without any qualifiers:
struct foo { ... };
foo x; // declare variable
In C, this won't work, because types thus declared live in their own distinct namespaces. Thus, you have to write:
struct foo { ... };
struct foo x; // declare variable
Notice the presence of struct
there on the second line. You have to do the same for union
and enum
(using their respective keywords), or use the typedef
trick:
typedef struct { ... } foo;
foo x; // declare variable
Consequently, you can have several types of different kinds named the same in C, since you can disambiguate:
struct foo { ... };
typedef enum { ... } foo;
struct foo x;
foo y;
In C++, however, while you can prefix a struct
name with keyword struct
whenever you reference it, the namespaces are merged, and so the above C snippet isn't valid. On the other hand, C++ specifically makes an exception to allow a type and a typedef for that type to have the same name (obviously with no effect), to allow the use of typedef
trick unchanged from C.
C compilers generally allowed a little corner cutting that C++ doesn't. C++ is much more strict than C. And generally, some of these differences are compiler-dependant. g++ allows some things that the Intel C++ compiler doesn't, for instance. Even fairly well written C code won't compile with a modern C++ compiler.
This also depends on what variety of C you're using. Stroustrup made C++ as compatible as he could, and no more compatible, with the 1989 ANSI and 1990 ISO standards, and the 1995 version changed nothing. The C committee went in a somewhat different direction with the 1999 standard, and the C++ committee has changed the next C++ standard (probably out next year or so) to conform with some of the changes.
Stroustrup lists incompatibilities with C90/C95 in Appendix B.2 of "The C++ Programming Language", Special Edition (which is 3rd edition with some added material):
'a' is an int
in C, a char
in C++.
The sizeof an enum is int
in C, not necessarily in C++.
C++ has // comments to end of line, C doesn't (although it's a common extension).
In C++, a struct foo {
definition puts foo
into the global namespace, while in C it would have to be referred to as struct foo
. This allows a struct
definition to shadow a name in an outer scope, and has a few other consequences. Also, C allows larger scope for struct
definitions, and allows them in return type and argument type declarations.
C++ is fussier about types in general. It won't allow an integer to be assigned to an enum
, and void *
objects cannot be assigned to other pointer types without a cast. In C, it's possible to provide an overlarge initializer (char name[5] = "David"
where C will discard the trailing null character).
C allows implicit int
in many contexts, and C++ doesn't. This means that all functions must be declared in C++, while in C it was often possible to get by with assuming int
for everything applicable in the function declaration.
In C, it's possible to jump from outside a block to inside using a labeled statement. In C++, this isn't allowed if it skips an initialization.
C is more liberal in external linkage. In C, a global const
variable is implicitly extern
, and that's not true in C++. C allows a global data object to be declared several times without an extern
, but that's not true in C++.
Many C++ keywords are not keywords in C, or are #define
d in standard C headers.
There are also some older features of C that aren't considered good style any more. In C, you can declare a function with the argument definitions after the list of arguments. In C, a declaration like int foo()
means that foo()
can take any number of any type of arguments, while in C++ it's equivalent to int foo(void)
.
That seems to cover everything from Stroustrup.
You cannot compare languages only by syntax. If you do that maybe you can see C as a subset of C++. In my opinion the fact that C++ is OO (and C isn't) is enough to say that C and C++ are different languages.
If you use gcc, you can use the warning -Wc++-compat
to give you warnings about C code which is dubious in C++ in some way. Its currently used in gcc itself, and its gotten a lot better recently (maybe try a nightly version to get the best you can).
(This doesn't strictly answer the question, but folk might like it).
A number of the answers here cover syntax differences that would cause C++ compilers to fail on C89 (or C99) source code. However, there are some subtle language differences that are legal in both languages but that would produce different behavior. The sizeof (char)
difference that Naveen mentioned is one example, but http://stackoverflow.com/questions/2038200/write-a-program-that-will-print-c-if-compiled-as-an-ansi-c-program-and-c/ lists some others.