Reputation: 1093
For some reason, I have to use a stack to achieve some function, but I need to reverse the output stack's elements. So I want to use stack<char,vector<char>
to achieve direct access, but there may be some error in my suggestion. Can anyone tell me how to efficiently reverse the output stack's elements in C++ using STL stack?
Upvotes: 0
Views: 5567
Reputation: 61259
In general you should not do this.
It's inappropriate to choose a container which is specifically designed to limit your access to its contents and then say that you really do want that access.
It's preferable to choose a container that's built to meet your needs. In this case using a deque
seems more appropriate.
But, if you reeaaaaallllyyyy want to do something kind of stupid, this is how you'd access the members of the stack directly (note that this does not use gobs of extra memory and time to build a temporary reverse stack, as some of the other answers have suggested):
#include <stack>
#include <deque>
#include <cstdlib>
#include <iostream>
using namespace std;
template <class T, class S>
S& Container(stack<T, S>& q) {
struct HackedStack : private stack<T, S> {
static S& Container(stack<T, S>& q) {
return q.*&HackedStack::c;
}
};
return HackedStack::Container(q);
}
int main()
{
stack<int> st;
deque<int> &mems = Container(st);
cout<<"Putting numbers into the stack"<<endl;
for(int i=0;i<20;i++){
int temp=rand();
cout<<temp<<endl;
st.push(rand());
}
cout<<endl<<"Reading numbers in the stack"<<endl;
for(deque<int>::iterator i=mems.begin();i!=mems.end();i++)
cout<<*i<<endl;
cout<<endl<<"Taking numbers out of the stack"<<endl;
while(!st.empty()){
int temp=st.top();
st.pop();
cout<<temp<<endl;
}
return 0;
}
And, yes, if you change all of the deque
references to vector
references, this will still work fine. But deque
is probably the preferable container to use with your stack.
Upvotes: 0
Reputation: 72241
If you want to access the elements in any order, why use a stack in the first place?
Use std::vector
or std::deque
directly, then iterate backwards like
for (auto iter = vec.rbegin(); iter != vec.rend(); ++iter) {
process(*iter);
}
If you really need to, there's a hackish-but-correct way to access the stack
's underlying container object.
See: how to print out all elements in a std::stack or std::queue conveniently
Upvotes: 1
Reputation: 6914
If you don't want to or you can't use stack
in desired way, first you should think that do you really need stack?
for example it might be better to use queue
or deque
in place of stack
, so you can control it better!
Upvotes: 1
Reputation: 48076
To reverse the output use this simple recursive function (pseudo code)
void recursiveWalk(Node* current)
{
if (current->next != NULL)
recusiveWalk(current->next);
// do stuff here
}
//call passing top
recursiveWalk(stack->top);
This will build up the stack in reverse order. When you're on the last element the call stack will start to unwind allowing you to operate on the stack from bottom to top.
Upvotes: -1
Reputation: 87959
Use a temporary stack.
// On exit the stack 's' will have it's elements reversed.
void reverse_stack(std::stack<int>& s)
{
std::stack<int> tmp;
while (!s.empty())
{
tmp.push(s.pop());
}
s.swap(tmp);
}
Upvotes: 3