I want to remove, if possible, the includes of both <vector> and <string> from my class header file. Both string and vector are return types of functions declared in the header file.
I was hoping I could do something like:
namespace std {
template <class T>
class vector;
}
And, declare the vector in the header and include it in the source file.
Is there a reference covering situations where you must include in the header, and situations where you can pull the includes into the source file?
You cannot safely forward declare STL templates, at least if you want to do it portably and safely. The standard is clear about the minimum requirements for each of the STL element, but leaves room for implemtation extensions that might add extra template parameters as long as those have default values. That is: the standard states that std::vector is a template that takes at least 2 parameters (type and allocator) but can have any number of extra arguments in a standard compliant implementation.
What is the point of not including string and vector headers? Surely whoever is going to use your class must have already included it since it is on your interface.
When you ask about a reference to decide when to include and when to forward declare, my advice would be: include everything that is part of your interface, forward declare internal details.
There are more issues here that plain compilation performance. If you push the include of a type that is in your public (or protected) interface outside of the header you will be creating dependencies on the order of includes. Users must know that they must include string before including your header, so you are giving them one more thing to worry about.
What things should be included in the implementation file: implementation details, loggers, elements that don't affect the interface (the database connectors, file headers), internal implementation details (i.e. using STL algorithms for your implementation does not affect your interface, functors that are created for a simple purpose, utilities...)
With a very few exceptions, you are not allowed to add things to the std:; namespace. For classes like vector and string, you therefore have no option but to #include the relevant Standard header files.
Also, notice that string is not a class, but a typedef for basic_string<char>.
This won't help for vector or string, but it might be worth mentioning that there is a forward reference header for iostream, called iosfwd.
Standard containers often have additional default template parameters (allocators, etc.) so this will not work. For example, here's a snippet from GNU implementation:
template<typename _Tp, typename _Alloc = std::allocator<_Tp> >
class vector : protected _Vector_base<_Tp, _Alloc>
{ ... };
This was something I was trying to do earlier too, but this is not possible due to templates.
Please see my question: Forward Declaration of a Base Class
As such headers don't change during your development it's not worth optimizing that anyway...
There is no simple obvious way to do it (as others have explained it very well).
However these headers should be seen as being part of the language (really!), so you can let them in your own headers without any problem, nobody will ever complain.
If your concern is compilation speed, I encourage you to use pre-compiled header instead and put these std headers in it (among other things). It will significantly increase your compilation speed.
Sorry the for the "real winner is the one who avoid the fight" kind of answer.
Just include the header in any file where you reference an STL collection.
As others have mentioned, there's not a way to reliably forward declare the STL classes, and even if you find one for your particular implementation, it will probably break if you use a different STL implementation.
If the compilation units don't instantiate the classes, it won't make your object files any bigger.
If string and vector are used only in signatures of non-public members of you class, you could use the PImpl idiom:
// MyClass.h
class MyClassImpl;
class MyClass{
public:
MyClass();
void MyMethod();
private:
MyClassImpl* m_impl;
};
// MyClassImpl.h
#include <vector>
#include <string>
#include <MyClass.h>
class MyClassImpl{
public:
MyClassImpl();
void MyMethod();
protected:
std::vector<std::string> StdMethod();
};
// MyClass.cpp
#include <MyClass.h>
#include <MyClassImpl.h>
void MyClass::MyMethod(){
m_impl->MyMethod();
}
You are always including vector and string in the header file, but only in the implementation part of your class; files including only MyClass.h will not be pulling in string and vector.
WARNING
Expect that doing this will cause uproar.
The language allows you to derive your own classes:
// MyKludges.h
#include <vector>
#include <string>
class KludgeIntVector : public std::vector<int> {
// ...
};
class KludgeDoubleVector : public std::vector<double> {
// ...
};
class KludgeString : public std::string {
// ...
};
Change your functions to return KludgeString and KludgeIntVector. Since these are no longer templates, you can forward declare them in your header files, and include MyKludges.h in your implementation files.
Strictly speaking, derived classes do not inherit base class constructors, destructors, assignment operators, and friends. You will need to provide (trivial) implementations of any that you're using.
// LotsOfFunctions.h
// Look, no includes! All forward declared!
class KludgeString;
// 10,000 functions that use neither strings nor vectors
// ...
void someFunction(KludgeString &);
// ...
// Another 10,000 functions that use neither strings nor vectors
// someFunction.cpp
// Implement someFunction in its own compilation unit
// <string> and <vector> arrive on the next line
#include "MyKludges.h"
#include "LotsOfFunctions.h"
void someFunction(KludgeString &k) { k.clear(); }
Maybe you would better use the pimpl idiom: it appears to me that you don't want to expose the implementation of your class to client code. If the vector and string objects are aggregated by value, the compiler needs to see their full declarations.
With the exception of adding overloads to std::swap (the only exception I can think of right now), you are generally not allowed to add anything to the std namespace. Even if it were allowed, the actual declaration for std::vector is a lot more complicated than the code in the OP. See Nikolai N Fetissov's answer for an example.
All that aside, you have the additional problem of what your class users are going to do with functions that return a std::vector or std::string. The C++ Standard section 3.10 says that functions returning such objects are returning rvalues, and rvalues must be of a complete type. In English, if your users want to do anything with those functions, they'll have to #include <vector> or <string> anyway. I think it would be easier to #include the headers for them in your .h file and be done with it.
I assume your objective here is to speed up compile times? Otherwise I'm not sure why you would want to remove them.
Another approach (not pretty but practical) is to use macro guards around the include itself.
e.g.
#ifndef STDLIB_STRING
#include <string>
#define STDLIB_STRING
#endif
Although this looks messy, on large codebases it does indeed increase the compile times. What we did is create a Visual Studio macro that will automatically generate the guards. We bind the macro to a key for easy coding. Then it just becomes a company coding standard (or habit).
We also do it for our own includes as well.
e.g.
#ifndef UTILITY_DATE_TIME_H
#include "Utility/DateTime.h"
#endif
Since we have Visual Studio helpers to auto-generate the guards when we create our own header files, we don't need the #define. The macro knows it's a internal include because we always use the
#include ""
format for our own includes and
#include <>
for external includes.
I know it doesn't look pretty but it did speed up our compile times on a largish codebase by over 1/2 hour (from memory).
Related
I’m using std::chrono to track how much time is elapsed from the instantiation until every call to someMethod().
A minimal sample code looks like this:
#include <chrono>
class TestClass
{
public:
TestClass();
void someMethod();
private:
std::chrono::time_point<std::chrono::steady_clock> m_timeBegin;
};
TestClass::TestClass() :
m_timeBegin(std::chrono::steady_clock::now())
{
}
void TestClass::someMethod()
{
auto timeNow = std::chrono::steady_clock::now();
auto msSinceCreation =
std::chrono::duration_cast<std::chrono::milliseconds>(timeNow - m_timeBegin);
}
I want to get rid of the #include in the header.
Motivation
Beside compilation and link times, my main concern is about encapsulation. Using std:chrono is only relevant in the implementation. In order to use Testclass there is absolutely no need to use it or even know it’s involved.
Here is some possible scenario. If someone using the TestClass decide to use std::chrono, he can do it without add the #include. Then, if in the future the implementation of TestClass change stop using std:chrono (and in consequence removing the #include) the other code will stop compiling with no reason.
Obviously the guy who forgot to add the include did it wrong. But also obviously this will occur we like it or not.
Additional info
As it is possible that it is relevant for certain solutions, SomeMethod() is called frequently and performance is important in my scenario.
Your problem would be solved if time_point was a custom type, because then you could just forward declare it, change the member to a (unique) pointer, and move the include to the .cpp file. However, forward declaration of std types is undefined behavior, so that is not possible. This leaves you basically with the following options:
Wrap the std::chrono::time_point<std::chrono::steady_clock> in a custom class. Then you can safely forward declare that type, change the member to a (unique) pointer, and move the include of the custom class (which includes <chrono>) into the .cpp file.
Use the pimpl idiom and move the whole implementation of your class into the .cpp file.
I understand your motivation. Still, while your scenario that someone uses <chrono> and forgets to include it is not far fetched, it is a problem of that someone, not yours. So you should think about whether it is really necessary to introduce some complexity, just to hide the <chrono> header. The standard library includes usually dont hurt, especially because they do not introduce rebuild impact.
As others have noted, using a smart pointer for the pimpl idiom or the forward declared type would introduce another include, namely <memory>. Even though this is usually a more common header than <chrono> you just exchanged one include for another. So if you really want to avoid additional includes, you may want to use a raw pointer. But then you have to take care of other problems, such as copy and move operations.
I am a bit confused about this line of code class TreeItem;. class TreeItem; is defined in other files not included in this file.
I would must look this question up in a book, but I am sure answer for this question is very simple.
#ifndef TREEMODEL_H
#define TREEMODEL_H
#include <QAbstractItemModel>
#include <QModelIndex>
#include <QVariant>
class TreeItem; //here, what does this do??
//! [0]
class TreeModel : public QAbstractItemModel
{
...
public:
...
private:
...
};
//! [2]
#endif // TREEMODEL_H
It is a forward declaration, and it is useful to enable to have pointers to TreeItem-s in some internal structures, etc.
Forward declarations are notably needed when you have co-recursive definitions; e.g. a struct foo containing pointers to struct bar which contains pointers to struct foo, etc... You might even declare these struct-s and define the functions operating on them in different translations units.
It is common practice, both in C and in C++, to forward declare some struct (or class) and to have variables which are pointers to it, and declare (and possibly call) functions handing such pointers.
Of course, some other file (or translation unit) would declare such opaque data structures and implement operations on it.
This is a common way to implement abstract data types.
BTW, there generally is a very common example of that in standard C. The FILE type from <stdio.h> is quite often some opaque (or at least, well hidden by many header files) struct (and you obviously don't need to know the internals of it to use <stdio.h> functions like fprintf)
In your (Qt's) case, you don't want to #include <QTreeItem> -or whatever header file is declaring class TreeItem- in this QTreeModel header file. If you did, that would add an additional header dependency (you don't need to recompile TreeModel code when TreeItem implementation has changed!) and would slow down compilation.
In smaller software projects, you might simply have a single header file and define all the struct inside.
It is called forward declaration.
Wikipedia says as follows:
In C++, classes can be forward-declared if you only need to use the
pointer-to-that-class type (since all object pointers are the same
size, and this is what the compiler cares about). This is especially
useful inside class definitions, e.g. if a class contains a member
that is a pointer to another class; to avoid circular references (i.e.
that class might also contain a member that is a pointer to this
class), we simply forward-declare the classes instead.
Forward declaration of a class is not sufficient if you need to use
the actual class type, for example, if you have a member whose type is
that class directly (not a pointer), or if you need to use it as a
base class, or if you need to use the methods of the class in a
method.
I have a class Foo, which I do not implement directly, but wrap external libraries (e.g FooXternal1 or FooXternal2 )
One way that I have seen to do this, is using preprocessor directives as
#include "config.h"
#include "foo.h"
#ifdef _FOOXTERNAL1_WRAPPER_
//implementation of class Foo using FooXternal1
#endif
#ifdef _FOOXTERNAL2_WRAPPER_
//implementation of class Foo using FooXternal2
#endif
and a config.h is used to define these preprocessor flags (_FOOXTERNAL1_WRAPPER_ and _FOOEXTERNAL2_WRAPPER_).
I have the impression this is frowned upon by the C++ programmer community because it uses preprocessor directives, is hard to debug, etc. Further, it does not allow for the parallel existence of both implementations.
I thought about making Foo a base class and inheriting from it to allow for both implementations to exist in parallel with each other. But I ran into two problems:
Pure virtual functions: cannot instatiate an object of type 'Foo', which I need during use.
Virtual functions run the risk of running an object with no (proper) implementation.
Am I missing something? Is there a cleaner way to do this?
EDIT : To summarize, there are 3(.5?!) ways to doing the wrapping- 2(.5) are given by icepack, and the last by Sergey
1- Use factory methods
2- Use preprocessor directives
2.5- Use makefile or IDE to effectively do the work of the preprocessor directives
3.5- Use templates suggested by Sergay
I am working on an embedded system where resources are limited, I decided to use template<enum = default_library>, with template specialization. It is easy to understand for later users; at least thats what I think
If all method names of external implementations are similar, you can use templates. Let external implementations look like:
class FooX1
{
public:
void Met1()
{
std::cout << "X1\n";
}
};
class FooX2
{
public:
void Met1()
{
std::cout << "X2\n";
}
};
Then you can use several variants.
Variant 1. You can declare member of a template type and wrap all calls to external implementation, even with some preparations before the call. Don't forget to delete impl in ~Foo destructor.
template<typename FooX>
class FooVariant1
{
public:
FooVariant1()
{
impl=new FooX();
}
void Met1Wrapper()
{
impl->Met1();
}
private:
FooX *impl;
};
Usage:
FooVariant1<FooX1> bar;
bar.Met1Wrapper();
Variant 2. You can inherit from a template parameter. In this case you don't declare any members, but just call implementation's methods by their names.
template<typename FooX>
class FooVariant2 : public FooX
{
};
Usage:
FooVariant2<FooX1> bar;
bar.Met1();
A disadvantage of using templates is that there is no easy way to change implementations in runtime. But in return you get much more optimal code, because types are generated in compile-time and there is no table of virtual functions, which can make the program slower.
If you want the 2 implementations to coexist at runtime, interface is the way to go (for example, you can use a factory method design pattern to instantiate the concrete object, like #n.m. has suggested).
If you can decide at compilation time what is the implementation that you need, you have several options:
Still use interface. This will allow an easy transition if in the future you'll need both implementations at runtime.
Use preprocessor directives. There is nothing wrong here as far as C++ is considered. It's a pure design issue.
Put the implementations in different files and configure your compiler to compile either one of them according to settings - this is actually similar to using preprocessor directives but it's cleaner and doesn't add garbage to your code (since the flags are in the solution/makefile/whatever your compiler uses).
The only thing I'd frown upon is including both implementations in the same source file. That might get confusing. Otherwise, this is one of the things preprocessor flags are good at, especially if you're not linking both libraries at the same time. It's just like supporting multiple operating systems. Provide a consistent interface in all cases and hide the implementation details somewhere else.
Does type Foo need to hold any information specific to each library? If not, you might be able to get away with this:
#include "Foo.h"
#if defined _FOOXTERNAL1_WRAPPER_
#include "Foo_impl1.cpp"
#elif defined _FOOXTERNAL2_WRAPPER_
#include "Foo_impl2.cpp"
#else
#error "Warn about a missing define here"
#endif
This way you don't have to bother with virtual functions or inheritance and you still prevent any member functions from going unimplemented.
Keep Foo abstract. Provide a factory method
Foo* MakeFoo();
that allocates a new object of either type FooImpl1 or FooImpl2, and returns its address.
Wikipedia on Factory Method pattern.
I need to add a few methods to c++'s class.
I'm creating a new class using inheritance called "Super_list" that will inherit all of list's methods and allow my to add my own.
#ifndef SUPER_LIST_H
#define SUPER_LIST_H
#include "my_containter.h"
#include <list>
using namespace std;
class My_Container;
class Super_list: public list<My_Container>
{
public:
void new_func1();
void new_func2();
void new_func_3();
};
#endif
This is where I'm using my newly made class:
#ifndef my_container_H
#define my_container_H
#include <list>
#include "super_list.h"
using namespace std;
class Super_list;
class My_container
{
private:
Super_list buddy;
};
#endif
I'm getting a bunch of error relating to the inheritance not being done correctly.
I would appreciate any help or other ideas from completing this task.
Thanks :)
You have a cyclic dependency: MyContainer needs so know about Super_list and vice versa. You need to find a way to break this dependency. Note that in your code, the forward declarations are completely superfluous.
Note also that standard library containers aren't designed to be inherited from publicly.
Concerning the dependency, you need to modify at least one of your classes such that it does not need the full definition of the other. Pretending for a moment that publicly inheriting from std::list is OK, then the only option would be for My_Container not to need the full definition of SuperList by having it hold a (preferably smart) pointer:
class My_container
{
private:
Super_list* buddy;
};
This would allow you to remove the super_list.h include.
One unrelated warning: it is not good to put using namespace std in header files, since it will impose that using directive on all code that, directly or indirectly, includes your header. This can lead to all kind of trouble. I usually go farther and say you shouldn't use it anywhere. Not everyone agrees with me on that one.
I would ask if you really do need to inherit to gain additional functionality. Try using a list as a member of your class. Not only will it make your class easier to change, but it means that code that uses your class won't care about whether its a list or not.
Here is more information
Can't say much without the error messeages.
1) You probably want to define some constructors in Super_list which forward their arguments to the std::list constructors.
2) Every time I tried to do something like this (or worked with something like this) it turned out to be a BAD idea. To keep incapsulation, what you probably want is some global functions:
template<class T>
new_func1(std::list<T> &l)
template<class T>
new_func2(std::list<T> &l)
etc.
I know it's possible to do class implementation in more than one file(yes, I know that this is bad idea), but I want to know if it's possible to write class definition in separate files without getting a redefinition error (maybe some tricks, or else...)
No, not the same class, but why would you?
You could define two classes with the same name in the same namespace (the same signature! That will actually be the same class at all, just defined in two ways) in two different header files and compile your program, if your source files don't include both headers. Your application could even be linked, but then at runtime things won't work as you expect (it'll be undefined behavior!), unless the classes are identical.
See Charles Bailey's answer for a more formal explanation.
EDIT:
If what you want is to have a single class defined by more than one file, in order to (for example) add some automatically generated functions to your class, you could #include a secondary file in the middle of your class.
/* automatically generated file - autofile.gen.h */
void f1( ) { /* ... */ }
void f2( ) { /* ... */ }
void f3( ) { /* ... */ }
/* ... */
/* your header file with your class to be expanded */
class C
{
/* ... */
#include "autofile.gen.h"
/* ... */
};
Not as nice and clean as the partial keyword in C#, but yes, you can split your class into multiple header files:
class MyClass
{
#include "my_class_aspect1.h"
#include "my_class_aspect2.h"
#include "my_class_aspect3.h"
};
#include "my_class_aspect1.inl"
#include "my_class_aspect2.inl"
#include "my_class_aspect3.inl"
Well sort of ...
If you have 1 header file as follows
ClassDef1.h:
class ClassDef
{
protected:
// blah, etc.
public:
// more blah
and another as follows
ClassDef2.h:
public:
// Yet more blah.
};
The class will effectively have been defined across 2 files.
Beyond that sort of trickery .. AFAIK, no you can't.
Yes, you can. Each definition must occur in a separate translation unit but there are heavy restrictions on multiple definitions.
Each definition must consist of the same sequence of tokens and in each definition corresponding names must refer to the same entity (or an entity within the definition of the class itself).
See 3.2 [basic.def.odr] / 5 of ISO 14882:2003 for full details.
Yes. Usually, people put the declaration part in .h file and then put the function body implementations in .cpp file
Put the declarations in a .h file, then implement in as many files as you want, but include the .h in each.
But, you cannot implement the same thing in more than one file
I know this is a late post, but a friend just asked me a similar question, so I thought I would post our discussion:
From what I understand you want to do ThinkingStiff, it's not possible in C++. I take it you want something like "partial class" in C#.
Keep in mind, "partial class" in .NET is necessary so you don't have to put your entire implementation in one big source file. Unlike C++, .NET does not allow your implementation to be separate from the declaration, therefore the need for "partial class". So, Rafid it's not a nice feature, it's a necessary one, and a reinvention of the wheel IMHO.
If your class definition is so large you need to split it across more than one source file, then it can probably be split into smaller, decoupled classes and the primary class can use the mediator design pattern that ties them all together.
If your desire is to hide private members, such as when developing a commercial library and you don't wish to give away intelectual property (or hints to that affect), then you can use pure abstract classes. This way, all that is in the header is simple class with all the public definitions (API) and a factory function for creating an instance of it. All the implementation details are in your source file(s).
Another alternative is similar to the above, but uses a normal class (not a pure virtual one), but still exposes only the public interface. In your source file(s), you do all the work inside a nameless namespace, which can include friend functions from your class definition when necessary, etc. A bit more work, but a reasonable technique.
I bolded those things you might want to lookup and consider when solving your problem.
This is one of the nice features of C#, but unfortunately it is not supported in C++.
Perhaps something like policy based design would do the trick? Multiple Inheritience gives you the possiblity to compose classes in ways you can't in other languages. of course there are gotchas associated with MI so make sure you know what you are doing.
The short answer is yes, it is possible. The correct answer is no, you should never even think about doing it (and you will be flogged by other programmers should you disregard that directive).
You can split the definitions of the member functions into other translation units, but not of the class itself. To do that, you'd need to do preprocessor trickery.
// header file with function declarations
class C {
public:
void f(int foo, int bar);
int g();
};
// this goes into a seperate file
void C::f(int foo, int bar) {
// code ...
}
// this in yet another
void C::g() {
// code ...
}
There must be a reason why you want to split between two headers, so my guess is that you really want 2 classes that are joined together to form components of a single (3rd) class.