On 10/28/2015 10:36 PM, Paul wrote:
> Is there any way of ascertaining (other than looking it up) whether objects are
> in the standard namespace? For example, INT_MIN from the <climits> header is
> not in the std namespace but cout from <iostream> is in the std namespace.
> How could one deduce that beforehand to avoid compile errors from writing
> std::INT_MIN?
As evident from the all uppercase name, INT_MIN is a macro.
A macro is not in any namespace: it is a text substitution rule.
> Is the rule that functions from header files are in the std namespace
> but variables from header files are not in the std namespace? Or is it
> subtler? Or something else I haven't thought of?
Generally,
* Identifiers from the pure C++ part of the standard library are in the
std namespace.
* Identifiers from the C standard library (which is mainly wholesale
adopted into the C++ standard library) can be in the std namespace, or
in the global namespace, or both, depending on which header you include.
Heads-up: the last point is COMPLICATED.
So, here's a concrete example.
In C the "<string.h>" header declares functions such as "strcpy".
In C++ the basic corresponding header is "<cstring>". Unlike C, when you
include "<cstring>" you're only guaranteed that "strcpy" is available in
the std namespace. C++ code that refers just to unqualified strcpy, may
fail to compile, while in C that's how it has to be expressed. But with
"<cstring>" the identifiers may also be placed in the global namespace,
so that unqualified name usage can compiler; it's just not guaranteed to
compile.
Originally for backwards-compatibility and leveraging existing
expertise, C++ also provides a header "<string.h>", which is distinct
from the original C "<string.h>". The effect of including "<string.h>",
like in C programming, is to get every name from "<cstring>" placed in
the global namespace, without necessarily being available in the std
namespace.
This means that when you include "<string.h>" in C++, you MAY get the
identifiers also available in the std namespace, and there's no way to
check that in the C++ code.
Effectively this means that there's no point in using "<cstring>": it
has negative utility because it presents possible portability issues,
with code that uses unqualified "strcpy" (for example) compiling nicely
with the original compiler, and then failing with some other compiler.
So, use "<string.h>".
And be aware that none of the three headers discussed above, namely C's
"<string.h>", C++'s "<cstring>", and C++'s "<string.h>", have ANYTHING
to do with C++' "<string>", which declared std::string and std::wstring
+ support.
Cheers & hth.,
- Alf