Let's consider this piece of code:
#include <iostream>
#include <sys/types.h>
#include <unistd.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
using namespace std;
int main(void) {
char hi[14] = "Hello world!\n";
if (write(1, hi, strlen(hi)) < 0) {
perror("write");
}
cout << "Done" << endl;
return 0;
}
Here, I'm mixing all kinds of C and C++ code to make something ... work. I'm writing on stdout directly and using some C headers like string.h and stdio.h. Is this considered bad? Could undefined behavior arise? Is C code "compatible" with C++ so I just include it and use it?
The program works just fine.
Hello world!
Done
Is this considered bad?
Some programmers consider it bad style to use C library functions when there are superior C++ library functions available. However, there are cases where it is better to use the C library functions.
Could undefined behavior arise?
Probably not. The C++ standard library incorporates almost the entire C standard library (with a few minor changes), so calls to C library functions from C++ are well-defined. As for functions such as write, their behaviour is defined by POSIX.
Is C code "compatible" with C++ so I just include it and use it?
For standard C library headers, yes. For implementation headers, typically yes; they are usually designed so that they can be validly included into C++ programs. For other headers... maybe. Not all C code is valid C++, but the degree of compatibility is high.
C++ forked from C a long time so, and the two languages have evolved independently.
The C++ standard describes deliberate incompatibilities that were introduced to C++ relative to the C standard from which it derived: http://eel.is/c++draft/diff.iso.
The mistake people make is in thinking this is a complete list of differences. C itself has evolved, and while parts of C99 were incorporated in recent versions of C++ not all have (VLAs, flexible array members, compound literals, ...).
C11 made the gap much wider, from small things like the removal of gets (still included in C++17) to things like bounds checking interfaces, threading support, and c-variants of c++ features like _the Static_assert keyword.
So for the most part you can get away with old-C-ish code in a C++ program, a few small changes that will cause compiler errors, a couple that might not, and nearly 20 years of C advances that you only have partial accesso to.
If you really want to write C-like code, consider writing C code and taking advantage of the full set of language improvements available in that language. The result will be much higher quality code than the rubbish you'll knock up restricting yourself to C++'s subset of C.
Gala,
Yes this is fine. C++ is a superset of C, you can blend the two with ease. In fact, many older programmers (like me) write C++ with a C style. In this style, printf, strcpy, no templates, RogueWave rather than stl, etc are used with C++ classes. Sometimes this is termed 'C with classes'.
--Matt
Related
For example, i want to see the code of function toupper() to understand how it works, is there any way? I have searched and opened string.h library, but didn't find anything.
From a strict language point of view, you cannot "see the code" of a standard function, because the C++ language standard only defines functions' prototypes and behaviours, not how they are implemented.
In fact, from a strict language point of view, a standard function like toupper does not even have to have source code, because a standard header, like <string.h> does not even have to be a file!
Of course, in practice, you will probably never encounter a C++ implementation in which standard headers are not files, because files are just a natural and simple implementation of headers. This means that in practice, for the header <string.h>, there is actually a C++ source file called "string.h" somewhere on your computer. Just find it and open it.
I have searched and opened string.h library, but didn't find anything.
Then you have not looked close enough. Hint: This file most likely includes one or more other header files.
Note that if you actually looked for toupper, that function is not in <string.h> anyway. Look in <ctype.h> instead. cppreference.com is a good online reference to tell you which headers contain which functions.
http://en.cppreference.com/w/c/string/byte/toupper
Again, this does not mean that the corresponding header file of your compiler contains that function directly, but it may directly or indirectly include some other file which contains it.
In any case, beware of what you will see inside of your compiler's header files. It will usually be a lot more complicated than you may think, and, more importantly, it will often use constructs you are not allowed to use in your own code; after all, the code in those files is internal to the compiler implementation, and the compiler has a lot of privileges you don't have, for example using otherwise forbidden identifiers like _STD_BEGIN. Also expect a lot of completely non-standard #pragmas and other non-portable stuff.
Another important thing to keep in mind is that you are not supposed to dig through a function's implementation to find out what it does. In badly written software, i.e. software with confusing interfaces and no documentation (which exists everywhere in the real world), you unfortunately have to do this, provided you have access to the source code.
But C++ standard functions are perfectly documented and have, with some arguable exceptions, well-designed interfaces. It may be interesting, and educating, and sometimes even necessary for debugging, to look into their implementation on your system, but don't let this possibility keep you from learning two important software-engineering skills:
Reading documentation.
Programming to interfaces, not to implementations.
Yes, of course, you could (not all realizations, maybe). For example, the glibc implementation defines toupper function as:
#define __ctype_toupper \
((int32_t *) _NL_CURRENT (LC_CTYPE, _NL_CTYPE_TOUPPER) + 128)
int
toupper (int c)
{
return c >= -128 && c < 256 ? __ctype_toupper[c] : c;
}
#include <stdio.h>
#include <stdlib.h>
void main ()
{
system("dir");
}
I have read in many C++ books where system() is used to execute command line programs. But when I tried the same command in C, it worked perfectly. So my question is whether its a standard C or C++ function? Please be liberal as I am new to C programming.
As system function is declared in stdlib.h, it can be considered a C function. But in C++, stdlib.h is merged into the std namespace and is located in the cstdlib include in this form. So the correct answer is "both".
It is both C and C++.
system : http://en.cppreference.com/w/c/program/system
std::system: http://en.cppreference.com/w/cpp/utility/program/system
Both: it's defined by the standard C library, and the standard C++ library contains the C library.
In C++, you should include the C++ style header, <cstdlib>, and refer to it as std::system. Including C headers directly is deprecated.
It's both. C defines many functions. C++ defines many functions that are exactly the same as in C, some that are subtly different from how they are in C, and a lot of functions and classes that aren't part of C at all. Knowing that a function is part of standard C++ says nothing about whether it is part of standard C, and knowing that a function is part of standard C says little about whether it is part of standard C++.
Both c and cpp support the function system as they have support for the stdlib.h that contains the prototype of system() function.
I tried googling this but I get different answers at different places. I want to know the cases wherein one should use one of the following:
#include <stdio>
#include <cstdio>
#include <iostream>
I cannot figure out the difference since in my case all my C++ programs seem to work if I use these interchangeably. That being said, iostream seems to support the stream of input and output by defining cin and cout etc. However, I maybe wrong. I would appreciate answers / credible citations for the usage of these with reference to the C++ standards. I wonder if there are any performance benefits involved in using one over the other.
Nonstandard Headers
<stdio> is not defined in any of the standards that I know of.
Standardized Headers for C
<stdio.h> is the c header containing functions like printf() and scanf().
Standardized Headers for C++
<stdio.h> is included in the c++ standard but is deprecated.
<cstdio> is the c++ header that includes things like printf() and scanf().
<iostream> is a c++ header that include things like std::cout, std::cerr and std::cin.
stdio is for standard IO in C. It should have a .h at the end. In C++, all C headers have been encapsulated in cxxxxxx headers (without .h). So, <stdio.h> is the same as <cstudio>. These offer functions, like printf and scanf, for simple IO.
iostream on the other hand is an IO library for C++, and offers streams like cin and cout, as you mentioned.
Depending on your application you can use them interchangeably for most of the time. The syntax is going to be different, obviously.
Formatting text can be easier using the C functions. For example:
printf("item %04d has a value of %+.6e\n", index, value);
is easier to write than (needs <iomanip> in addition to <iostream>):
std::cout << "item " << std::setw(4) << std::setfill('0') << index
<< "has a value of " << std::setprecision(6) << value << "\n";
However, you need to be more careful when using the first one. For example, the following line won't produce a compile error (but as sharth mentioned, you might get warnings when compiling) but will cause runtime issues:
printf("I wonder what will happen? %d\n");
I don't think there is a lot of difference in their performance as most of the stream "magic" happens in compile time, and they should produce similar results. I'm not 100% sure though, so correct me if I'm wrong.
there is no stdio (stdio.h and cstdio). the 'c' and the missing '.h' in the header name indicates that it's the C++ version of the C header.
check cstdio and iostream (references)
some compilers (including MSVC) include stl headers in other stl headers which leads to the effect you observed. this is not portable though!
if you are concerned with performance: use the C++ variants and check this
What should I include in C++ programs, stdio.h or cstdio? and Why?
Why two header files which provide the same functionality?
What does the standard say regarding this?
How should I go about including other such headers, Is there a base rule that I should follow?
Consider the following programs:
Sample 1:
#include<stdio.h>
int main()
{
printf("Hello World");
return 0;
}
Sample 2:
#include<cstdio>
int main()
{
printf("Hello World");
return 0;
}
Both work as expected. So which usage is more appropriate?
The answer is: Neither! Surprised? Read on.
The C++ Standard library provides all standard C headers for compatibility reason, while C++ as a language also provides all the equivalent headers. As a convention,
No C++ standard library headers(apart from ones include for C compatibility) have any file extensions, and
All C++ equivalent of C headers begin with cxxxxx.
The C++ Standard mentions this under Annex D (normative) Compatibility features:
§2 mentions the important distinguishing point. This rule applied to the examples above means:
Including cstdio imports the symbol names in the std namespace and possibly in the Global namespace.
Including stdio.h imports the symbol names in the Global namespace and possibly in the std namespace.
Let us apply this rule to our sample codes and measure the pros and cons:
Sample 1:
This brings all the symbols from stdio.h in the global namespace. Advantage is that you can use the symbols without any qualification since they are imported in the global namespace. Downside is that you end up polluting the global namespace with many symbol names that you will probably never use. This might lead to symbol name collision. In C++ always consider the global namespace as a minefield and avoid it as much as possible.
Sample 2:
This is a very bad practice because there is no guarantee that the implementation will put the symbols in global namespace, the standard simply does not demand to do so. We are simply relying on the behavior of one particular compiler implementation. We cannot and should not assume that all compilers will do so. So strictly speaking the program is not standard approved and this usage is not portable across all implementations.
So what is the correct usage?
The correct usage is to use cstdio and fully qualify the symbol names or else bring them in scope with using declarations. This guarantees all symbols we use are present in std namespace and we are not polluting the global namespace. Example of correct usage:
Sample 3:
#include<cstdio>
using std::printf;
int main()
{
printf("Hello World");
return 0;
}
Note that the directive using namespace std;, especially in a header, is not a good option and you should always use using declarations.
Note that we consider stdio.h vs. cstdio here just a sample use case, in practice it applies to all most cxxxx and xxxx.h headers, except a few like <math.h> and <cmath>.
Since this post is a bit old I wanted to share the following:
Looking at code:
Using X.h // Compatible with C language standard
---------------
#include <X.h>
int main() {
// Invoke X's corresponding function
return 0;
}
Using X // Not compatible with C language standard
--------------
#include <X>
int main() {
// Invoke X's corresponding function
return 0;
}
They both compile and execute ok!
Which one is better in C++?
Regarding C++11's and C++17's specification:
C.5.1 (section from C++17 document)
Modifications to headers [diff.mods.to.headers]
For compatibility with the C standard library, the C++ standard library provides the C headers enumerated in D.5, but their use is
deprecated in C++.
There are no C++ headers for the C headers <stdatomic.h>, <stdnoreturn.h>, and <threads.h>, nor are the C headers themselves
part of C++.
The C++ headers <ccomplex> (D.4.1) and <ctgmath> (D.4.4), as well as their corresponding C headers <complex.h> and <tgmath.h>, do not
contain any of the content from the C standard library and instead
merely include other headers from the C++ standard library.
D.5
C standard library headers [depr.c.headers]
For compatibility with the C standard library, the C++ standard library provides the C headers shown in Table 141.
Both C++11 and C++17 standard specifications documents state the use of <X.h> remains for compatibility with the C standard, although their use is regarded as deprecated.
Regarding C++ 20 standard proposal
They are reviewing "undeprecating" the use of the C library headers in C++20. <X.h> appear highlighted in green. C++11 and C++17 deprecation, as of now, is stated as a "weak recommendation" and a "tweak" for keeping the "C standard library headers (c.headers)" is displayed below:
"The basic C library headers are an essential compatibility feature, and not going anywhere anytime soon." (from C++ 20 review document)
D.5 C standard
library headers [depr.c.headers]
Weak recommendation: In addition to the above, also remove the
corresponding C headers from the C++ standard, much as we have no
corresponding <stdatomic.h>, <stdnoreturn.h>, or <threads.h>, headers.
As above, but with the following tweaks:
20.5.5.2.1 C standard library headers [c.headers]
For compatibility with the C standard library, the C++ standard
library provides the C headers shown in Table 141. Table 141 — C
headers
<assert.h> <inttypes.h> <signal.h> <stdio.h> <wchar.h>
<complex.h> <iso646.h> <stdalign.h> <stdlib.h> <wctype.h>
<ctype.h> <limits.h> <stdarg.h> <string.h>
<errno.h> <locale.h> <stdbool.h> <tgmath.h>
<fenv.h> <math.h> <stddef.h> <time.h>
<float.h> <setjmp.h> <stdint.h> <uchar.h>
The header <complex.h>
behaves as if it simply includes the header <complex>.
The header <tgmath.h> behaves as if it simply includes the headers <complex> and <cmath>.
Bjarne Stroustrup recommends maximising inter-operability between
the C and C++ languages, by reducing incompatibilities as much as
possible. Others argue otherwise, as it complicates things.
So, it seems <X.h> aren't going anywhere. Ultimately, you can use both. Personally, I would make the decision of which one I would use boil down to having your code backwards compatible with C code or not.
From a standards standpoint, should I use the following from the C++ <limits> header?
UCHAR_MAX which is the c implementation or
std::numeric_limits<unsigned char>::max() which is the C++ implementation.
The result is equivalent between the two versions but should I choose an implementation based on some standard or on readability and portability in this case. Note this implementation must be cross-platform compatible. I am writing C++ code.
If you want the code to be able to compile as C, then you pretty much need to use <limits.h>. If you're writing C++, it's probably better to use the C++ <limits> header instead. The latter lets you write code that will work in templates that can't really be duplicated with the C header:
template <class T>
class mytemplate {
T x;
void somefunc() { x = std::numeric_limits<T>::max(); } // or whatever...
};
Know what language you're writing in, and write in that language. If you're writing C++, use the standard C++ ways of doing things.
Standard C++ is normally cross-platform compatible (there are exceptions, like export, but export is being removed from the C++ Standard anyway). It's usually more readable to stick with C++ constructs than to switch between C and C++ constructs.
You should use <limits> to stay consistant.
On the windows platform, if you include <windows.h>, you might also want to
#define NOMINMAX
to avoid a name conflict with min and max.
When you are using C, std::numeric_limits obviously isn't available.
In C++ it depends on what you want to do - std::numeric_limits<T>::max() is not a constant expression with the current C++ standard.
In these cases an alternative to the C-ish macros would be to use something like Boost.Integers integer traits const_min/const_max which also works in templated contexts.