C constructs that still don't work in C++
3 days ago
- #cross-language compatibility
- #C programming
- #C++
- C++ is not a superset of C, and compatibility between them requires specifying the language mode (e.g., C17, C23, C++17, C++20, C++23).
- Designated initializers in C++20 are available but more constrained than C's versions (e.g., they require direct members and declaration order, no mixing with positional clauses).
- C23 changed void f() to behave as void f(void), closing a gap with C++ where it means different things (no parameters in C++).
- Implicit conversion from void* to object pointer works in C (e.g., from malloc) but not in C++, requiring explicit casting.
- C++20 repaired some object lifetime issues with malloc for implicit-lifetime types, but malloc is still not idiomatic C++ due to lack of constructors and ownership management.
- Discarding const requires explicit casting in C++ (const_cast), but writing to actually-const objects remains undefined behavior.
- Enums in C23 have more explicit typing, but C++ enums are distinct types and require casting from integers (prefer enum class for C++ APIs).
- The restrict keyword is standard in C but not in C++, with compiler-specific extensions available.
- Flexible array members are not standard in C++ (use vector or span instead, but keep C layouts at ABI boundaries).
- Migration advice includes treating malloc as storage only, preserving C layouts at edges, using C++ constructs for clear ownership/lifetime, and isolating compiler extensions.