How to code my program to has flexibility to receive custom allocator in advance?
I coded some allocators, but not sure whether I will really need it.
However, I know for sure that if my custom allocator will be plugged-in, I want to use it in some certain parts.
Example
For example, int* B::db should use custom allocator (myNew/myDelete),
while all std::vector should use standard allocator.
While I still don't plug my custom allocator, I wish my program will use standard new/delete as default.
#define myNew new
#define myDelete delete
class B{ //B should not be a template class
int* db=nullptr;
std::vector<float> something; //<- let it use default new/delete
public: B(){
db=myNew int[5]; //work like "db=new int[5];"
}
public: ~B(){
myDelete[] db; //work like "delete[] db;"
}
};
If I want plug a custom allocator later, I can just change the #define.
Note: B should not be a template class.
Question
I am not sure if this is a correct way. I am still very new to allocator.
I also want to avoid macro if possible.
Is it a good solution? Are there solutions without macro?
I can let my program just use new/delete as default, and I can refactor it later.
However, it will probably be a mental-breaking work in the future.
Note: Most Q/A seem to focus on overloading the global new/delete. That is not what I want. :-
overloading new/delete
How to properly replace global new & delete operators
Using operator new and operator delete with a custom memory pool/allocator
Sorry if this question is too newbie.
I haven't found any good tutorial/information about using allocator in real practice.
I have also read (they are just theory of allocator + code) :-
https://www.gamedev.net/resources/_/technical/general-programming/c-custom-memory-allocation-r3010
http://allenchou.net/2013/05/memory-management-part-3-of-3-stl-compatible-allocators/
http://www.drdobbs.com/cpp/improving-performance-with-custom-pool-a/184406243?pgno=1
B may have to stay a non-template. But it doesn't mean you can't write a template to help. And you may as well facilitate RAII while you're at it.
template<typename T>
class my_new_heap_array {
T *ptr;
public:
operator T*() const { return ptr; }
my_new_heap_array(std::size_t sz)
: ptr(myNew T[sz])
{}
~my_new_heap_array() { myDelete[] ptr; }
};
class B { //B should not be a template class
my_new_heap_array<int> db;
std::vector<float> something; //<- let it use default new/delete
public:
B()
:db(5)
{ }
};
In general, so long as you program with separation of concerns in mind, you'd find it easier to change behaviors more easily. B needs to decide on what allocator to use, but it shouldn't be concerned with how to use it. That concern falls on the helper class. And if B needs to use another allocator some day, then just switch out the helper class for another.
Related
Let's say I go against all the advice I found on this site and elsewhere online, and do something like this:
#include <vector>
#include <array>
#include <iostream>
using PointType = std::array<double, 3>;
class Point
:
public PointType
{
public:
using PointType::PointType;
Point(const Point& copy)
:
PointType(copy)
{
std::cout << "Point(const Point&)" << std::endl;
}
Point(Point&& rval)
:
PointType(rval)
{
std::cout << "Point(Point&&)" << std::endl;
}
// Prevent PolygonType* p = new Polygon; delete p;
template<typename ...Args>
void* operator new (size_t, Args...) = delete;
};
using PolygonType = std::vector<PointType>;
class Polygon
:
public PolygonType
{
public:
using PolygonType::PolygonType;
Polygon(const Polygon& copy)
:
PolygonType(copy)
{
std::cout << "Polygon(const Polygon&)" << std::endl;
}
Polygon(Polygon&& rval)
:
PolygonType(rval)
{
std::cout << "Polygon(Polygon&&)" << std::endl;
}
// Prevent PolygonType* p = new Polygon; delete p;
template<typename ...Args>
void* operator new (size_t, Args...) = delete;
};
If I am happy with never using new with Point or Polygon or similar types, the deletion of the new operator takes care of the problem of the undefined behavior:
std::array<double, 3> a = new Point({1., 2., 3.})
delete a;
The conditions on std::vector<PointType> imposed by algorithms that work on it are the same: the algorithms check if the public interface fits what is done in the algorithm. This is a problem if I want an algorithm (function template) to view this vector of points as an open chain of line segments, or a closed polygon. This excludes relying on the implicit interface when resolving function template candidates. Also, concepts do not help me when they arrive, because again, the conditions on the containers are the same, what I want the algorithms to do to them differs. So using concrete types like this and tagging them, on the other hand, makes tag dispatching trivial if I do the tag dispatching with SFINAE using the new metafunctions from type_traits to check if the template argument has been tagged with a specific tag.
Also the old problem of re-typing constructors is gone with the C++11 constructor inheritance.
So, what still explodes when inheriting from STL in such a way that the constructors are inherited and the new operator is deleted? There must be something I am not seeing.
If your object will always be statically- or automatically- allocated (no new), then it will be destructed in the same manner, so you don't need a virtual destructor, so this will work as intended.
Deriving from standard containers isn't outright prohibited, it's just dangerous. You seem to have largely mitigated the danger by eliminating the dangerous use case.
Note that if you did permit dynamic allocation then delete through a pointer-to-base, you'd still have UB even if the derived class held no state of its own (i.e. had no members). Object lifetime is a lot more complex than just counting data members.
You could still permit dynamic allocation and just never delete through a pointer-to-base, but whether that's logistically appropriate for you, not to mention sufficiently protective, simply depends on the context.
Anecdote: I have occasionally inherited from vector/map in "library code" not intended to be further expanded by anyone else. It's not open-source software, it's a proprietary codebase under my control, so with the liberal use of comments that's fine. Composition is a bit of a pain if you want to pass through the container's entire interface.
I am designing a wrapper class (a bit similar to std::autoPtr but I have different purpose) for scalar values:
template <typename T>
class ScalarPtr
{
private:
T* m_data;
...
public:
ScalarPtr(T *data): m_data(data)
{ ... }
T& operator* ();
T* operator -> ();
~ScalarPtr()
{
if(m_data)
delete m_data; ...
}
};
Now the problem is that when I also want to use this class for stack-allocated memory objects like this:
float temp=...
ScalarPtr<float> fltPtr(&temp);
The naive way is to pass boolean in constructor to specify whether to deallocate or not but is there any better way?
I am not sure if there is a better approach other than the boolean flag.
As you are aware(and hence ask the Q)this makes the interface rather non-intutive to the end user.
The purpose of the wrapper/resource managing class is to implement an RAII, where the resource itself takes care of releasing its resources(in this case dynamic memory) implicitly. Given that the stack variables are automatically destroyed beyond their scopes,its seems rather odd to use a resource managing wrapper for them. I would rather not prefer to do so.
But, Given that you want to maintain a uniform acess to your class through this wrapper class, the simplest yet not so elegant way seems to be the boolean flag.
If I have the following hypothetical class:
namespace System
{
template <class T>
class Container
{
public:
Container() { }
~Container() { }
}
}
If I instantiate two Containers with different T's, say:
Container<int> a;
Container<string> b;
I would like to create vector with pointers to a and b. Since a and b are different types, normally this wouldn't be possible. However, if I did something like:
std::stack<void*> _collection;
void *p = reinterpret_cast<void*>(&a);
void *q = reinterpret_cast<void*>(&b);
_collection.push(a);
_collection.push(b);
Then later on, I can get a and b back from _collection like so:
Container<string> b = *reinterpret_cast<Container<string>*>(_collection.pop());
Container<int> a = *reinterpret_cast<Container<int>*>(_collection.pop());
My question is, is this the best way for storing a collection of unrelated types? Also would this be the preferred way of storing and retrieving the pointers from the vector (the reinterpret cast)? I've looked around and seen that boost has a nicer way of solving this, Boost::Any, but since this is a learning project I am on I would like to do it myself (Also I have been curious to find a good reason to use a reinterpret_cast correctly).
Consider boost::any or boost::variant if you want to store objects of heterogeneous types.
And before deciding which one to use, have a look at the comparison:
Boost.Variant vs. Boost.Any
Hopefully, it will help you to make the correct decision. Choose one, and any of the container from the standard library to store the objects, std::stack<boost::any>, std::stack<boost::variant>, or any other. Don't write your own container.
I repeat don't write your own container. Use containers from the standard library. They're well-tested.
While it is possible to cast to void * and back, the problem is knowing which type you're popping. After all, you give the example:
Container<string> b = *reinterpret_cast<Container<string>*>(_collection.pop());
Container<int> a = *reinterpret_cast<Container<int>*>(_collection.pop());
However, if you were to accidentally do:
Container<int> a = *reinterpret_cast<Container<int>*>(_collection.pop());
Container<string> b = *reinterpret_cast<Container<string>*>(_collection.pop());
Now you've got pointers to the wrong type, and will likely see crashes - or worse.
If you want to do something like this, at least use dynamic_cast to check that you have the right types. With dynamic_cast, you can have C++ check, at runtime (using RTTI), that your cast is safe, as long as the types being casted (both before and after) have a common base type with at least one virtual method.
So, first create a common base type with a virtual destructor:
class ContainerBase {
public:
virtual ~ContainerBase() { }
};
Make your containers derive from it:
template <typename T>
class Container : public ContainerBase {
// ...
}
Now use a std::stack<ContainerBase *>. When you retrieve items from the stack, use dynamic_cast<Container<int> >(stack.pop()) or dynamic_cast<Container<string> >(stack.pop()); if you have the types wrong, these will check, and will return NULL.
That said, heterogeneous containers are almost always the wrong thing to be using; at some level you need to know what's in the container so you can actually use it. What are you actually trying to accomplish by creating a container like this?
For one of my classes, I'm writing a program that's going to be using a templated memory pool structure to handle the allocation of new instances of a class while keeping them together. It is currently declared as follows:
template<typename T, unsigned int N>
class MemoryPool
{
//Stuff
};
Where T is the class to create this pool for and N is the maximum number of elements that can be placed in the pool. I want to overload new for the created type to make interactions with the pool a bit easier if it's a reasonable thing to do--but I'm not sure if it is.
My thoughts, currently, are that if it's possible to overload new as a friend function for Twithin MemoryPool that it should be doable from there but I'm not sure. And, I'm not sure of the best way to start setting that up. I've tried a few different ways to just declare the overloaded new and I'm getting errors before even implementing it.
Is this a reasonable way to ensure that new is overridden for any class that uses MemoryPool?
Is doing so even possible?
Is doing so even a good idea?
How would I set up the function declaration to accomplish this?
In case it matters, I'm using Visual Studio 2010.
Note, the specific use of templates and overloading new are not part of the homework assignment. It's just how I want to implement it if possible to make the rest of the assignment easier to read for the future. So, if there's no reasonable way to do it, I just use member functions within MemoryPool to accomplish the same goal.
Thanks!
Example implementation:
MemoryPool<Object, MAX_OBJECTS> objectPool; //Pool to store objects
Object* allObjects[MAX_OBJECTS]; //Locations of objects
//Make a new object (this is how I'd like to do it)
allObjects[0] = new Object(/*args*/);
//(If I can't do the above, this would be the alternative)
allObjects[0] = objectPool.AllocateNewSlot();
allObjects[0]->Initialize(/*args*/);
In this example, the use of the MemoryPool takes care of the actual implementation of new ensuring the Object is created in its pool instead of just anywhere on the heap (to ensure all the Objects are in a centralized, more controllable location.
It is possible to overload the new operator, however I would advice against it.
I think you are going in the wrong direction. You don't want to hide things and make users unsure what is happening. In this case you should be explicit that you are allocating through a pool.
Here is what you could do.
template<typename T, unsigned int N>
class MemoryPool
{
T* malloc()
{
return ... // your pool impl
}
void free(T* ptr)
{
... // your pool impl
}
void destory(T* ptr)
{
ptr->T::~T(); // call destructor
free(ptr);
}
};
int main()
{
MemoryPool<my_class> pool;
my_class* instance = new (pool.malloc()) my_class(/*args*/); // in-place new
return 0;
}
You should also take a look at how boost pool is implemented.
Is there any template available in boost for RAII. There are classes like scoped_ptr, shared_ptr which basically work on pointer. Can those classes be used for any other resources other than pointers. Is there any template which works with a general resources.
Take for example some resource which is acquired in the beginning of a scope and has to be somehow released at the end of scope. Both acquire and release take some steps. We could write a template which takes two(or maybe one object) functors which do this task. I havent thought it through how this can be achieved, i was just wondering are there any existing methods to do it
Edit: How about one in C++0x with support for lambda functions
shared_ptr provides the possibility to specify a custom deleter. When the pointer needs to be destroyed, the deleter will be invoked and can do whatever cleanup actions are necessary. This way more complicated resources than simple pointers can be managed with this smart pointer class.
The most generic approach is the ScopeGuard one (basic idea in this ddj article, implemented e.g. with convenience macros in Boost.ScopeExit), and lets you execute functions or clean up resources at scope exit.
But to be honest, i don't see why you'd want that. While i understand that its a bit annoying to write a class every time for a one-step-aquire and one-step-release pattern, you are talking about multi-step-aquire and -release.
If its taken multiple steps, it, in my opinion, belongs in an appropiately named utility class so that the details are hidden and the code in place (thus reducing error probability).
If you weigh it against the gains, those few additional lines are not really something to worry about.
A more generic and more efficient (no call through function pointer) version is as follows:
#include <boost/type_traits.hpp>
template<typename FuncType, FuncType * Func>
class RAIIFunc
{
public:
typedef typename boost::function_traits<FuncType>::arg1_type arg_type;
RAIIFunc(arg_type p) : p_(p) {}
~RAIIFunc() { Func(p_); }
arg_type & getValue() { return p_; }
arg_type const & getValue() const { return p_; }
private:
arg_type p_;
};
Example use:
RAIIFunc<int (int), ::close> f = ::open("...");
I have to admit I don't really see the point. Writing a RAII wrapper from scratch is ridiculously simple already. There's just not much work to be saved by using some kind of predefined wrapper:
struct scoped_foo : private boost::noncopyable {
scoped_foo() : f(...) {}
~scoped_foo() {...}
foo& get_foo() { return f; }
private:
foo f;
};
Now, the ...'s are essentially the bits that'd have to be filled out manually if you used some kind of general RAII template: creation and destruction of our foo resource. And without them there's really not much left. A few lines of boilerplate code, but it's so little it just doesn't seem worth it to extract it into a reusable template, at least not at the moment. With the addition of lambdas in C++0x, we could write the functors for creation and destruction so concisely that it might be worth it to write those and plug them into a reusable template. But until then, it seems like it'd be more trouble than worth. If you were to define two functors to plug into a RAII template, you'd have already written most of this boilerplate code twice.
I was thinking about something similar:
template <typename T>
class RAII {
private:
T (*constructor)();
void (*destructor)(T);
public:
T value;
RAII(T (*constructor)(), void (*destructor)(T)) :
constructor(constructor),
destructor(destructor) {
value = constructor();
}
~RAII() {
destructor(value);
}
};
and to be used like this (using OpenGL's GLUquadric as an example):
RAII<GLUquadric*> quad = RAII<GLUquadric*>(gluNewQuadric, gluDeleteQuadric);
gluSphere(quad.value, 3, 20, 20)
Here's yet another C++11 RAII helper: https://github.com/ArtemGr/libglim/blob/master/raii.hpp
It runs a C++ functor at destruction:
auto unmap = raiiFun ([&]() {munmap (fd, size);});