______________________________________________________________________ Annex C (informative) Compatibility [diff] ______________________________________________________________________ 1 This Annex summarizes the evolution of C++ since the first edition of The C++ Programming Language and explains in detail the differences between C++ and C. Because the C language as described by this Inter national Standard differs from the dialects of Classic C used up till now, we discuss the differences between C++ and ISO C as well as the differences between C++ and Classic C. 2 C++ is based on C (K&R78) and adopts most of the changes specified by the ISO C standard. Converting programs among C++, K&R C, and ISO C may be subject to vicissitudes of expression evaluation. All differ ences between C++ and ISO C can be diagnosed by a processor. With the exceptions listed in this Annex, programs that are both C++ and ISO C have the same meaning in both languages. C.1 Extensions [diff.c] 1 This subclause summarizes the major extensions to C provided by C++. C.1.1 C++ features available in 1985 [diff.early] 1 This subclause summarizes the extensions to C provided by C++ in the 1985 version of its manual: 2 The types of function parameters can be specified (_dcl.fct_) and will be checked (_expr.call_). Type conversions will be performed (_expr.call_). This is also in ISO C. 3 Single-precision floating point arithmetic may be used for float expressions; _basic.fundamental_ and _conv.double_. This is also in ISO C. 4 Function names can be overloaded; _over_. 5 Operators can be overloaded; _over.oper_. 6 Functions can be inline substituted; _dcl.fct.spec_. 7 Data objects can be const; _dcl.type_. This is also in ISO C. 8 Objects of reference type can be declared; _dcl.ref_ and _dcl.init.ref_. 9 A free store is provided by the new and delete operators; _expr.new_, _expr.delete_. 10Classes can provide data hiding (_class.access_), guaranteed initial ization (_class.ctor_), user-defined conversions (_class.conv_), and dynamic typing through use of virtual functions (_class.virtual_). 11The name of a class or enumeration is a type name; _class_. 12A pointer to any non-const and non-volatile object type can be assigned to a void*; _conv.ptr_. This is also in ISO C. 13A pointer to function can be assigned to a void*; _conv.ptr_. 14A declaration within a block is a statement; _stmt.dcl_. 15Anonymous unions can be declared; _class.union_. C.1.2 C++ features added since 1985 [diff.c++] 1 This subclause summarizes the major extensions of C++ since the 1985 version of this manual: 2 A class can have more than one direct base class (multiple inheri tance); _class.mi_. 3 Class members can be protected; _class.access_ . 4 Pointers to class members can be declared and used; _dcl.mptr_, _expr.mptr.oper_. 5 Operators new and delete can be overloaded and declared for a class; _expr.new_, _expr.delete_, _class.free_. This allows the "assignment to this" technique for class specific storage management to be removed to the anachronism subclause; _diff.this_. 6 Objects can be explicitly destroyed; _class.dtor_. 7 Assignment and initialization are defined as memberwise assignment and initialization; _class.copy_. 8 The overload keyword was made redundant and moved to the anachronism subclause; _diff.anac_. 9 General expressions are allowed as initializers for static objects; _dcl.init_. 10Data objects can be volatile; _dcl.type_. Also in ISO C. 11Initializers are allowed for static class members; _class.static_. 12Member functions can be static; _class.static_. 13Member functions can be const and volatile; _class.this_. 14Linkage to non-C++ program fragments can be explicitly declared; _dcl.link_. 15Operators ->, ->*, and , can be overloaded; _over.oper_. 16Classes can be abstract; _class.abstract_. 17Prefix and postfix application of ++ and -- on a user-defined type can be distinguished. 18Templates; _temp_. 19Exception handling; _except_. 20The bool type (_basic.fundamental_). C.2 C++ and ISO C [diff.iso] 1 The subclauses of this subclause list the differences between C++ and ISO C, by the chapters of this document. C.2.1 Clause _lex_: lexical conventions [diff.lex] Subclause _lex.trigraph_ 1 Change: C++ style comments (//) are added A pair of slashes now introduce a one-line comment. Rationale: This style of comments is a useful addition to the lan guage. Effect on original feature: Change to semantics of well-defined fea ture. A valid ISO C expression containing a division operator fol lowed immediately by a C-style comment will now be treated as a C++ style comment. For example: { int a = 4; int b = 8 //* divide by a*/ a; +a; } Difficulty of converting: Syntactic transformation. Just add white space after the division operator. How widely used: The token sequence //* probably occurs very seldom. Subclause _lex.key_ 2 Change: New Keywords New keywords are added to C++; see _lex.key_. Rationale: These keywords were added in order to implement the new semantics of C++. Effect on original feature: Change to semantics of well-defined feature. Any ISO C programs that used any of these keywords as iden tifiers are not valid C++ programs. Difficulty of converting: Syntactic transformation. Converting one specific program is easy. Converting a large collection of related programs takes more work. How widely used: Common. Subclause _lex.ccon_ 3 Change: Type of character literal is changed from int to char Rationale: This is needed for improved overloaded function argument type matching. For example: int function( int i ); int function( char c ); function( 'x' ); It is preferable that this call match the second version of function rather than the first. Effect on original feature: Change to semantics of well-defined fea ture. ISO C programs which depend on sizeof('x') == sizeof(int) will not work the same as C++ programs. Difficulty of converting: Simple. How widely used: Programs which depend upon sizeof('x') are probably rare. C.2.2 Clause _basic_: basic concepts [diff.basic] Subclause _basic.def_ 1 Change: C++ does not have "tentative definitions" as in C E.g., at file scope, int i; int i; is valid in C, invalid in C++. This makes it impossible to define mutually referential file-local static objects, if initializers are restricted to the syntactic forms of C. For example, struct X { int i; struct X *next; }; static struct X a; static struct X b = { 0, &a }; static struct X a = { 1, &b }; Rationale: This avoids having different initialization rules for built-in types and user-defined types. Effect on original feature: Deletion of semantically well-defined fea ture. Difficulty of converting: Semantic transformation. In C++, the ini tializer for one of a set of mutually-referential file-local static objects must invoke a function call to achieve the initialization. How widely used: Seldom. Subclause _basic.scope_ 2 Change: A struct is a scope in C++, not in C Rationale: Class scope is crucial to C++, and a struct is a class. Effect on original feature: Change to semantics of well-defined fea ture. Difficulty of converting: Semantic transformation. How widely used: C programs use struct extremely frequently, but the change is only noticeable when struct, enumeration, or enumerator names are referred to outside the struct. The latter is probably rare. Subclause _basic.link_ [also _dcl.type_] 3 Change: A name of file scope that is explicitly declared const, and not explicitly declared extern, has internal linkage, while in C it would have external linkage Rationale: Because const objects can be used as compile-time values in C++, this feature urges programmers to provide explicit initializer values for each const. This feature allows the user to put const objects in header files that are included in many compilation units. Effect on original feature: Change to semantics of well-defined fea ture. Difficulty of converting: Semantic transformation How widely used: Seldom Subclause _basic.start_ 4 Change: Main cannot be called recursively and cannot have its address taken Rationale: The main function may require special actions. Effect on original feature: Deletion of semantically well-defined fea ture Difficulty of converting: Trivial: create an intermediary function such as mymain(argc, argv). How widely used: Seldom Subclause _basic.types_ 5 Change: C allows "compatible types" in several places, C++ does not For example, otherwise-identical struct types with different tag names are "compatible" in C but are distinctly different types in C++. Rationale: Stricter type checking is essential for C++. Effect on original feature: Deletion of semantically well-defined fea ture. Difficulty of converting: Semantic transformation The "typesafe link age" mechanism will find many, but not all, of such problems. Those problems not found by typesafe linkage will continue to function prop erly, according to the "layout compatibility rules" of this International Standard. How widely used: Common. Subclause _conv.ptr_ 6 Change: Converting void* to a pointer-to-object type requires casting char a[10]; void *b=a; void foo() { char *c=b; } ISO C will accept this usage of pointer to void being assigned to a pointer to object type. C++ will not. Rationale: C++ tries harder than C to enforce compile-time type safety. Effect on original feature: Deletion of semantically well-defined fea ture. Difficulty of converting: Could be automated. Violations will be diagnosed by the C++ translator. The fix is to add a cast. For exam ple: char *c = (char *) b; How widely used: This is fairly widely used but it is good programming practice to add the cast when assigning pointer-to-void to pointer-to- object. Some ISO C translators will give a warning if the cast is not used. Subclause _conv.ptr_ 7 Change: Only pointers to non-const and non-volatile objects may be implicitly converted to void* Rationale: This improves type safety. Effect on original feature: Deletion of semantically well-defined fea ture. Difficulty of converting: Could be automated. A C program containing such an implicit conversion from (e.g.) pointer-to-const-object to void* will receive a diagnostic message. The correction is to add an explicit cast. How widely used: Seldom. C.2.3 Clause _expr_: expressions [diff.expr] Subclause _expr.call_ 1 Change: Implicit declaration of functions is not allowed Rationale: The type-safe nature of C++. Effect on original feature: Deletion of semantically well-defined fea ture. Note: the original feature was labeled as "obsolescent" in ISO C. Difficulty of converting: Syntactic transformation. Facilities for producing explicit function declarations are fairly widespread commercially. How widely used: Common. Subclause _expr.sizeof_, _expr.cast_ 2 Change: Types must be declared in declarations, not in expressions In C, a sizeof expression or cast expression may create a new type. For example, p = (void*)(struct x {int i;} *)0; declares a new type, struct x . Rationale: This prohibition helps to clarify the location of declara tions in the source code. Effect on original feature: Deletion of a semantically well-defined feature. Difficulty of converting: Syntactic transformation. How widely used: Seldom. C.2.4 Clause _stmt.stmt_: statements [diff.stat] Subclause _stmt.switch_, _stmt.goto_ (switch and goto statements) 1 Change: It is now invalid to jump past a declaration with explicit or implicit initializer (except across entire block not entered) Rationale: Constructors used in initializers may allocate resources which need to be de-allocated upon leaving the block. Allowing jump past initializers would require complicated run-time determination of allocation. Furthermore, any use of the uninitialized object could be a disaster. With this simple compile-time rule, C++ assures that if an initialized variable is in scope, then it has assuredly been ini tialized. Effect on original feature: Deletion of semantically well-defined fea ture. Difficulty of converting: S>Transfer interrupted!