1

The CreateList function must: 1. Ask the user for a grocery store name. 2. Ask the user to enter a list of items for this grocery store, until the user enters “done”. 3. Add the items to the vector of strings as they are entered. 4. Display: “Added item to grocery store name list.” after each item is entered, where “item” is the item entered and “grocery store name” is the name entered in Step 1 above.

void CreateList()
{   
    string store;
    string item;
    int count = 0;
    cout<<"What is the grocery store name"<<endl;
    cin>>store;
    vector<string> store;
    cout<<"Enter a list of items for this grocery store one at a time. When you are done, type done."<<endl;
    cin>>item;
    store[count] = item; //error saying no conversion?
    count++;
    cout<<"Added "<<item<<"to "<<store<<"list"<<endl;
    bool finished=true;
    while (finished = true)
    {
        cout<<"Enter a list of items for this grocery store one at a time. When you are done, type done."<<endl;
        cin>>item;

        if (item == "done")
        break;

        store[count] = item; //error saying no conversion?
        count++;
        cout<<"Added "<<item<<"to "<<store<<"list"<<endl;
}


}

Had a couple questions on my function, not sure where the no conversion error is coming from, and could this be implemented in a do while loop? Please try to keep your answers as simple as possible, this is my first attempt in C++ while transitioning from python. Thanks for your time.

user102817
  • 309
  • 3
  • 13

4 Answers4

2

You have a lot of errors in there. First of all as you can see you are repeating a big chunk of your code twice. That is a sign that you should refactor your code. Your intuition about the do {} while() is correct, you should definitely use that.

Second, you don't push new items into a vector via operator[] like you did in store[count]. You should use store.push_back(item) or store.emplace_back(item). A vector is a dynamic container, therefore once created it does not contain any element. Trying to access the first element with store[0] will cause undefined behavior and most likely a segmentation fault.

Third, as you can see you are not really using that finished variable either (in fact you were assigning it with finished = true and not checking if it was true, that would be finished == true). Because you are correctly exiting the loop with a break. Therefore you should definitely remove it.

Fourth, you named the store name store and used the same name to declare the store list vector. You should not use the same name for two different types within the same block of code.

Finally, I've seen that you are using something similar to using namespace std;. While this is ok for this kind of exercises, I think it is a good idea to get used to prefix standard library classes with std:: or, with caution, only "include" the namespaces you really need with:

using std::string;
using std::cout;
// ...

This mainly because "polluting" the global namespace is considered bad practice for all kind of reasons I'll not cover here.

Following the guidelines above you can get something similar to:

void CreateList() {  
    std::string store;
    std::string item;
    std::cout << "What is the grocery store name" << std::endl;
    std::cin >> store;

    std::vector<std::string> store_list;
    do {
        std::cout << "Enter a list of items for this grocery store one at a time. When you are done, type done." << std::endl;
        std::cin >> item;
        if (item == "done") break;
        store_list.emplace_back(item);
        std::cout << "Added " << item << "to " << store << "list" << std::endl;
    } while (true);
}
Community
  • 1
  • 1
Shoe
  • 74,840
  • 36
  • 166
  • 272
0

You have two variables called store. One is a string and one is a vector of string. You then appear to confuse the two, assigning item to store[count], which describes a character not a string, and later on trying to output the list of products as thought it was a single string.

Making the variable names make sense should fix your code:

void CreateList()
{   
    std::string storeName;
    std::cout << "What is the grocery store name" << std::endl;
    std::cin >> storeName;

    std::cout << "Enter a list of items for this grocery store one at a time. When you are done, type done." << std::endl;

    std::vector<std::string> products;
    while (true)
    {
        std::string product;
        std::cin >> product;

        if (product == "done")
            break;

        products.push_back(product);

        std::cout << "Added " << product << " to " << storeName << " list" << std::endl;
    }
}

There is an artefact of C programming inherited by C++ that allows you to "shadow" one variable with a different variable of the same name.

#include <iostream>

int i = 20;

int main() {
    int i = 10;
    for (int i = 0; i < 5; ++i) {
        std::cout << "loop i = " << i << std::endl;
    }
    std::cout << "i = " << i << std::endl;
}

Live demo: http://ideone.com/eKayzN

kfsone
  • 23,617
  • 2
  • 42
  • 74
  • In his case the variable was not *shadowed* at all. The two `stored` variables were declared in the same block of scope. Not like the example you showing there (in which the two `i`s are one in the `main` block of code and the other within the `for` loop. – Shoe Nov 01 '13 at 03:45
  • @Jefffrey That's still shadowing, but ideone's GCC options promote it to an error so I didn't bother re-demonstrating it. – kfsone Nov 01 '13 at 03:47
  • Also, there's a 3rd 'i' in my demo, the global one between the #include and main. See http://ideone.com/eJ3olP for promotion to a redeclaration. – kfsone Nov 01 '13 at 03:49
  • So you are saying that two variable with the same name in the same scope is *legal*? – Shoe Nov 01 '13 at 03:52
  • I can't speak to whether it's legal - I've just had to fix problems before where people had gotten away with it on their compiler. – kfsone Nov 01 '13 at 03:59
  • Also the second `i` shadows the global `i` and the third `i` shadows both the others. That doesn't prove anything. There's no "promotion" of any kind there. The standard (at § 3.3.10) explicitly says "A name can be hidden by an explicit declaration of that same name in a nested declarative region or derived class". Can you show me where does the standard says that two variables with the same name within the same scope are considered "hidden"/"shadowed" and/or legal? Hint: you can't. – Shoe Nov 01 '13 at 04:03
  • @Jefffrey I'm not sure what argument you're having here. I've not said that it was legal, and I didn't include it in my example. I conceeded that I don't know whether it's legal. As to noting that the global `i` is shadowed, yes, it's almost like I pointed that out in my second comment after you missed it in your first. – kfsone Nov 01 '13 at 04:31
0

First you got 2 different loops to read in your values but both are more or less broken and should really be one loop.

Also you got an assignment in your 2nd loop as well as declaring 2 different variables with the name store one being a string and the other being a vector<string>. You can't have 2 different variables with the same name in the same scope.

What I think that you actually wanna do would be something like that:

vector<string> CreateList()
{   
    string store;
    string item;
    cout<<"What is the grocery store name"<<endl;
    cin>>store;
    vector<string> store_list;
    cout<<"Enter a list of items for this grocery store one at a time. When you are done, type done."<<endl;

    while (cin>>item && item != "done") // read next item as long as input didn't fail and item isn't "done".
    {
        store_list.pushback(item); // using pushback for adding new item
        cout<<"Added "<< item <<"to "<< store << " list"<<endl;
    }

    return store_list

}

You also probably wanted to return the list of stores somehow.

AliciaBytes
  • 7,300
  • 6
  • 36
  • 47
0

Well, vector is a dynamic array but not like standard array and you can access the value of specified index by using [] operator because vector overloads the [] operator. But it returns the const data you require and you can't add or modify the data through []. You should use "store.push_back(item)" to add the item to the vector and you don't need to use a variable to save the total count, vector will save the current count for you. You just need to invoke "store.size()" to get the total count. If you want to modify the data of specified index, you can use "store.at(index) = value;" to modify it. Here is the correct code:

void CreateList()
{   
    string storename; // use another name because you use store again below.
    string item;
    int count = 0;
    cout<<"What is the grocery store name"<<endl;
    cin>>storename;
    vector<string> store;
    cout<<"Enter a list of items for this grocery store one at a time. When you are done, type done."<<endl;
    cin>>item;
    **store.push_back(item);** //error saying no conversion?
    count++;
    cout<<"Added "<<item<<"to "<<store<<"list"<<endl;
    bool finished=true;
    while (finished == true)  // Here is not correct, use == to compare, not =. In fact , you use break to quit the loop, so you can just use while(1) or while(true) here. 
    {
        cout<<"Enter a list of items for this grocery store one at a time. When you are done, type done."<<endl;
        cin>>item;

        if (item == "done")
        break;

        **store.push_back(item);** //error saying no conversion?
        count++;
        cout<<"Added "<<item<<" to "<<storename<<" list"<<endl;
    }
}
Maple Wan
  • 61
  • 1
  • 8