namespaces and forward declarations

Started by
3 comments, last by Polymorphic OOP 18 years, 9 months ago
I've come to like using forward declarations in header files to reduce compile times, for example:

// dostuff.h

class foo;
void DoPtrStuff(foo*);
void DoRefStuff(foo&);
as opposed to:

// dostuff.h

#include "foo.h"
void dostuff(foo*);
void DoPtrStuff(foo*);
void DoRefStuff(foo&);
Since in the second example every file that includes "dostuff.h" also gets all the baggage associated with "foo.h". My question is, is there a way to get this to work when the class you are using the forward declaration for is in a namespace? I'll give a specific example of something I'm trying to do but can't get to work:

class std::string;
void foo( std::string& );
or:

namespace std{
   class string;
}
void foo( std::string& );
Neither of these compile ( in Visual Studio .NET 2003 ), and although I've tried several different variations I can't find one that will compile.
There are 10 types of people in the world: Those who know binary and those who don''t.
Advertisement
string is not a class, it's a typedef. basic_string is the class, and you could prototype that and provide the appropriate typedefs.

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.

I'm pretty sure there's probably something somewhere in the standard to say that fiddling with the defintions of standard types or the contents of the std namespace is either illegal or a bad idea. I wouldn't try doing this with standard types, or any classes that are outside the control of your system. The second method you gave should work. Try it again with a class you've defined. Eg, this should work:

namespace Foo{	class Bar;}void SomeFunc(Foo::Bar&){}
Quote:Original post by Nemesis2k2
I'm pretty sure there's probably something somewhere in the standard to say that fiddling with the defintions of standard types or the contents of the std namespace is either illegal or a bad idea.


Correct. That said, forward decleartions for pre-existing types should be OK AFAIK, especially considering (IIRC) that you're allowed to specialize certain pre-existing classes within the std:: namespace (I think).
Quote:Original post by MaulingMonkey
Quote:Original post by Nemesis2k2
I'm pretty sure there's probably something somewhere in the standard to say that fiddling with the defintions of standard types or the contents of the std namespace is either illegal or a bad idea.


Correct. That said, forward decleartions for pre-existing types should be OK AFAIK, especially considering (IIRC) that you're allowed to specialize certain pre-existing classes within the std:: namespace (I think).

Specializations are okay in the std namespace for all standard library templates as long as the specializations are dependant on user-defined names with external linkage and that they meet the requirements specified for the original template (17.4.3.1). Otherwise the behavior is undefined.

However, if you are to take a direct literal interpretation of the standard, I believe that declarations you provide in the std namespace, even if they are of names which exist in the standard library, result in undefined behavior.

Quote:Original post by The C++ Standard 17.4.3.1 Reserved Names Subsection 1
It is undefined for a C++ program to add declarations or definitions to namespace std or namespaces within namespace std unless otherwise specified. A program may add template specializations for any standard library template to namespace std. Such a specialization (complete or partial) of a standard library template results in undefined behavior unless the declaration depends on a user-defined name of external linkage and unless the specialization meets the standard library requirements for the original template.


If anyone can find a place in the standard which states that declarations of standard library names is okay, then please post the appropriate selection here. Until then, I'd have to say that the declaration suggestion for basic_string (or anything else from the standard library) results in undefined behavior.

This topic is closed to new replies.

Advertisement