Reputation: 701
I am using a std::stack
to keep a list of possibilities in my program.
std::stack<int, std::deque<int> > myStack;
Now, for debugging purposes only, I want to have access to all the elements of my std::stack
(for instance as a std::deque
). But the following syntax is illegal:
std::deque<int> myDeque = myStack; // Does not compile
What is the simplest way to do it?
The way I would do it is:
std::stack<int, std::deque<int> > newStack = myStack;
std::deque<int> myDeque;
while(!newStack.empty()){
myDeque.push_back(newStack.top());
newStack.pop();
}
but it looks a bit ugly.
Upvotes: 5
Views: 2243
Reputation: 467
Adding to Maxim's answer (not enough rep to comment):
std::stack
doesn't have a virtual destructor, so attempting to delete
MyStack
from a base-class pointer to std::stack
is unsafe. You can decide to trust that your compiler will generate warnings in these cases, or use private inheritance to prevent this scenario in most cases.
template<class T, class C>
struct MyStack : private std::stack<T, C>
{
typedef std::stack<T, C> Stack;
using Stack::Stack;
using Stack::operator=;
using Stack::c; // expose as public
// Private inheritance, explicitly forward functions we need
using Stack::size;
using Stack::push;
using Stack::pop;
// etc
};
Upvotes: 2
Reputation: 136306
The underlying container of std::stack
is accessible as protected member c
. Hence:
template<class T, class C>
struct MyStack : std::stack<T, C>
{
typedef std::stack<T, C> Stack;
using Stack::Stack;
using Stack::operator=;
using Stack::c; // expose as public
};
And if you cannot change definitions and recompile, then:
template<class T, class C>
C& get_underlying_container(std::stack<T, C>& s) {
static_assert(sizeof s == sizeof(MyStack<T, C>), "Size mismatch.");
static_assert(alignof s == alignof(MyStack<T, C>), "Alignment mismatch.");
return static_cast<MyStack<T, C>&>(s).c;
}
Upvotes: 11