views:

101

answers:

5

The referenced vector to functions does not hold the information in memory. Do I have to use pointers?

Thanks.

#include <iostream>
#include <cstdlib>
#include <vector>
#include <string>

using namespace std;

void menu();
void addvector(vector<string>& vec);
void subvector(vector<string>& vec);
void vectorsize(const vector<string>& vec);
void printvec(const vector<string>& vec);
void printvec_bw(const vector<string>& vec);

int main()
{
    vector<string> svector;

    menu();

    return 0;
}
//functions definitions

void menu()
{
    vector<string> svector;
    int choice = 0;

        cout << "Thanks for using this program! \n"
             << "Enter 1 to add a string to the vector \n"
             << "Enter 2 to remove the last string from the vector \n"
             << "Enter 3 to print the vector size \n"
             << "Enter 4 to print the contents of the vector \n"
             << "Enter 5 ----------------------------------- backwards \n"
             << "Enter 6 to end the program \n";
        cin >> choice;

        switch(choice)
        {

                case 1:
                    addvector(svector);
                    menu();
                    break;
                case 2:
                    subvector(svector);
                    menu();
                    break;
                case 3:
                    vectorsize(svector);
                    menu();
                    break;
                case 4:
                    printvec(svector);
                    menu();
                    break;
                case 5:
                    printvec_bw(svector);
                    menu();
                    break;
                case 6:
                    exit(1);
                default:
                    cout << "not a valid choice \n";

            // menu is structured so that all other functions are called from it.
        }

}

void addvector(vector<string>& vec)
{
    //string line;

     //int i = 0;
        //cin.ignore(1, '\n');
        //cout << "Enter the string please \n";
        //getline(cin, line);
        vec.push_back("the police man's beard is half-constructed");    

}

void subvector(vector<string>& vec)
{
    vec.pop_back();
    return;
}

void vectorsize(const vector<string>& vec)
{
    if (vec.empty())
    {
        cout << "vector is empty";
    }
    else
    {
        cout << vec.size() << endl;
    }
    return;
}

void printvec(const vector<string>& vec)
{
    for(int i = 0; i < vec.size(); i++)
    {
        cout << vec[i] << endl;
    }

    return;
}

void printvec_bw(const vector<string>& vec)
{
    for(int i = vec.size(); i > 0; i--)
    {
        cout << vec[i] << endl;
    }

    return;
}
A: 

You need to either have svector be a global (declared outside any function) or pass it as a parameter to menu. C++ does not have dynamic scope for functions.

EDIT: You can also wrap all this up in a class and repeatedly call menu().

MSN
ouch... don't advise to go global...
xtofl
Nope. You can pass a reference to a local object on the stack. The problem is the recursion, which creates a new copy of svector each time menu is invoked.
Adrian McCarthy
@xtofl, giving good/bad implementation advice doesn't help when the semantics aren't even known. Of course a global variable in general wouldn't be a good idea, but in this case, with such a trivial program, it doesn't matter.And apparently my comment about dynamic scope didn't register with anyone.
MSN
@MSN: that is right. I am known to have no feet on the ground.
xtofl
+5  A: 

Your problem is that each call to menu() creates a new vector that hides the previous one, this is why it seems to you like they're empty. If you really want to be calling menu recursively, pass it the vector reference that you created in main.

All that being said, menu systems are rarely ever recursive. You probably want a loop around your call to menu() in main that loops until the user has chosen to quit.

Uri
Clear explanation. Being a nit-picker, though, I can't resist objecting against the term 'hiding'. The new vector doesn't hide anything, it's the previous stack frame that's lost.
xtofl
The previous stack frame isn't lost, it's just ignored…
Potatoswatter
How is this not hiding? The identifier is temporarily bound to a different object, causing the confusion about it supposedly being empty
Uri
ohh... I thought I was being so cool, coming up with that recursion. Thanks.
@kylepayne: Recursion is a great tool for solving problems in terms of smaller subproblems, but isn't a silver bullet. If a natural description of a task (e.g., do menu selections until you quit) does not lend itself to recursion, it's probably not a good match.
Uri
+4  A: 

Your menu function is recursive.

That means that every new call of menu will create it's own vector, and throw it away when it's done.

If you want to reuse the svector, you need to either use a plain loop for the menu, or pass the original svector, created in the main, to the menu using a pass-by-reference argument.

xtofl
+1  A: 

Problem is that you call another menu() which allocates new svector on stack (in some part of memory). Probably original code was void menu(vector<string>&svector)

ony
A: 

svector is shared (is that what s stands for?), and variables which are shared between different scopes in C++ must be declared extern, or you get two separate local variables.

int main()
{
    extern vector<string> svector;
    …


void menu()
{
    extern vector<string> svector;
    …

Just kidding. svector should be an argument. Or a global would suffice. But don't use globals like this.

Potatoswatter