Link to home
Start Free TrialLog in
Avatar of smurf_killer
smurf_killer

asked on

printing a 2 dimensional array

hi im making a little program that should simulate what items are in a fridge and so on. i have made 3 items that should be in it, and after that you should be able to add more. please remember that this is only a simulation. im getting these errors:
2  In file included from koleskab.cpp
the items i have put into my array are not declared in this scope. honestly i must say that i have no idea what scope it means when it is from the header the error comes from.

7 koleskab.h too many initializers for `char[1]'
i have 3 of these errors which says the same

in function "int main()"
20 koleskab.cpp invalid conversion from `char' to `char (*)[1]'
20 koleskab.cpp   initializing argument 1 of `void udskriv(char (*)[1])'

and just for the record koleskab = refidgerator.

most of it is in english but there are still some danish in it.

and just so you know, this is not an assignment from a book or a class
#include <iostream>
#include "koleskab.h"
 
using namespace std;
 
int main()
{
    int valg = 0;
    
    cout<<"---------MENU:---------"<<endl<<endl;
    
    cout<<"Press 1 to view a list of products."<<endl;
    cout<<"Press 2 to change a product."<<endl;
    cout<<"Press 3 to add new products."<<endl<<endl;
    cin>>valg;
    
    switch(valg)
    {
                case 1:
                     udskriv(items[reakke][kolonne]);
                break;
}
    system("PAUSE");
    return 0;
}
 
void udskriv(char item[reakke][kolonne])
{
     for(char i = 0; i<19;i++)
     {
             for(int n = 0;n<1;n++)
             {
             cout<<item[i][n];
             }
     }
}
 
// and my header file koleskab.h:
const char reakke = 19;
const int kolonne  = 1;
char items[reakke] [kolonne]= {
                   {cheese, 0},
                   {water, 1},
                   {milk, 2}
};
void udskriv(char items[reakke] [kolonne]);
void change(char items[reakke] [kolonne]);
void new_product(char items[reakke] [kolonne]);
 
// i do know that i shouldn't use header files but it makes it easier for me ;)

Open in new window

Avatar of Infinity08
Infinity08
Flag of Belgium image

Why did you make reakke a char ?

        const char reakke = 19;

Make it an int like kolonne.


Btw, I think I already told you that it's a bad idea to define variables in a header file !

        char items[reakke] [kolonne]= {
                   {cheese, 0},
                   {water, 1},
                   {milk, 2}
        };

items is a 2D array of chars. 0, 1 and 2 can be interpreted as chars, but I'm not sure that's what you intended.
cheese, water and milk however are not defined ... What are they supposed to be ?

Did you intend something like this :

        char *items[num] = { "cheese", "water", "milk" };
Avatar of smurf_killer
smurf_killer

ASKER

i do know that its a bad idea to define variables in a header file, but i works better for me that way. that array is supposed to store some things you have in a fridge, example {cheese, 0} should put cheese into the row, and how many there are, in this case 0, into the column. is it possible to make something without pointers, i know it is basic knowledge but i really know nothing about them
ASKER CERTIFIED SOLUTION
Avatar of Infinity08
Infinity08
Flag of Belgium image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
thanks for the link.

i have tried it but now its saying something:

in function main()
20 koleskab.cpp cannot convert `FridgeItem' to `char (*)[1]' for argument `1' to `void udskriv(char (*)[1])'

koleskab.cpp In function `void udskriv(int*)':
33 koleskab.cpp invalid types `int[int]' for array subscript
although i am not sure about that typedef struct. is it some kind of template? ive looked briefly at cplusplus.com but weren't able to find anything
think i found a link
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Try creating these three files as I showed them, then compile and run ... See that it works, and then try to understand it. Any bit you don't understand, ask me !! I'll be happy to explain it.
it works thanks alot, though i do have some questions:

1) i really don't get how it finds koleskab.cpp

2) void udskriv(FridgeItem items[], const int num)  where does it get num from, now that its const. and also

3) std::cout << items[i].name do you have to write std, i mean when i write using namespace std; in main? and also, where does "name" come from?

i don't think there is more, i will have to look at it a little more.
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
aah yes ofcourse, i have read a bit of the tutorial, it all stands clearer now, thanks alot.
>> it all stands clearer now, thanks alot.

Don't hesitate to ask, no matter how easy/stupid/insignificant the question might seem.
is it okay that i leave this question open if i need more help with adding to an array, or should i make new questions for that?
You can keep it open for questions related to this program ;)
>>You can keep it open for questions related to this program ;)

ofcourse, would never use it for another program :D thanks
now i have made most on it, but i still need the one that adds new things to the array. but im not sure how to do it, cause i should have something that moved everything if it wasn't there. for example number 0 is cheese but there are 0 in the fridge, number 1 is water which there is 1 of, and number 2 is milk where there are 2 in the fridge. but there aren't any cheese so it should be deleted so that water will be on cheese's spot and milk will be on water's spot. i hope you understand what i mean, my code as it looks now:
//main.cpp:
 
#include <iostream>
#include "koleskab.h"
 
using namespace std;
 
int main()
{
        int valg = 0;
    
    FridgeItem fridge[19] = {                     // <--- move the fridge in the main
                                {"cheese", 0},
                                {"water", 1},
                                {"milk", 2}
                            };
    int fridgeNum = 3;                            // <--- there are currently 3 items in the fridge
 
 for(int i=0; i<100;i++
 )
 {
    cout<<"---------MENU:---------"<<endl<<endl;
    
    cout<<"Press 1 to view a list of products available in the fridge."<<endl;
    cout<<"Press 2 to change a product in the fridge."<<endl;
    cout<<"Press 3 to add new products to the fridge."<<endl;
    cout<<"Press 4 to close Fridge Control"<<endl;
    cout<<"Choose: ";
    cin>>valg;
    cout<<endl<<endl;
    switch(valg)
    {
                case 1 :
                     udskriv(fridge, fridgeNum);    // <-- pass the fridge array as well as the number of items currently in it
                     break;
                case 2 :
                     change(fridge, fridgeNum);
                     break;
                case 3 :
                     new_product(fridge, fridgeNum);
                     break;
                case 4 :
                     return 0;
                     break;
                default :
                     cout<<"Please press 1, 2, 3 or 4"<<endl;// some error message (invalid input)
                     break;
    }
    cout<<endl;
}
    system("PAUSE");
    return 0;
}
 
//koleskab.cpp:
 
#include "koleskab.h"
#include <iostream>
 
void udskriv(FridgeItem items[], const int num)        // <--- modify the parameter like this
{
     std::cout<<"Products in the fridge: "<<std::endl;
     for (int i = 0; i<num; i++)        // <--- use an int as array index
     {
             std::cout << items[i].name << " : " << items[i].amount << std::endl;  // <--- we output the name and amount of each item in the fridge
     }
}
 
void change(FridgeItem items[], int &num)
{
     int choice;
     int amount;
     std::cout<<"Enter the number of which item you want to change the status on: "<<std::endl;
     
     for (int i = 0; i<num; i++)
     {
         
         std::cout<<"Number "<<i<<" = "<<items[i].name<<" : "<<items[i].amount<<std::endl;
     }
     std::cin>>choice;
 
std::cout<<"You have chosen "<<items[choice].name<<". There are "<<items[choice].amount<<" in the fridge."<<std::endl;
std::cout<<"Enter the new amount of "<<items[choice].name<<", or the same amount to cancel: ";
std::cin>>amount;
items[choice].amount = amount;
std::cout<<"There are now "<<items [choice].amount<<" "<<items[choice].name<<" ."<<std::endl;
}
 
void new_product (FridgeItem items[], int &num)
{
     std::cout<<"Feature not yet implemented"<<std::endl;
 
}
 
//koleskab.h:
 
#ifndef KOLESKAB_H            // <--- add include guards !!!
#define KOLESKAB_H
 
#include <string>
 
typedef struct FridgeItem {     // <--- the struct is declared here
   std::string name;
   int amount;
} FridgeItem;
 
void udskriv(FridgeItem items[], const int num);
void change(FridgeItem items[], int &num);      // <--- needs to be implemented in koleskab.cpp
void new_product(FridgeItem items[], int &num); // <--- needs to be implemented in koleskab.cpp
 
#endif /* KOLESKAB_H */

Open in new window

>> but there aren't any cheese so it should be deleted so that water will be on cheese's spot and milk will be on water's spot. i hope you understand what i mean

Yes, I do. The easiest would be to use an STL vector instead of an array :

        http://www.cplusplus.com/reference/stl/vector/

Is that an option for you ?

If not, here are two options :

1) when removing the cheese item from the array, simple erase the fields, and don't move the other items. The erased fields will be seen as an empty entry, and will be ignored by the rest of the code. Doing it this way will mean certain changes in the rest of the code. It will also mean that the num parameter can be dropped from the function calls.

2) an alternative is to actually move the other items when the cheese item is removed from the array ... ie. shift the other items one place towards the front of the array.
i must admit, i have no idea how to work with templates or classes. so i am not sure it would be a good idea to jump out in vector coding.

>> 2) an alternative is to actually move the other items when the cheese item is removed from the array ... ie. shift the other items one place towards the front of the array.

that was kinda what my plan was, but the problem is that i have no idea how to do it, maybe some tips or code snippets?
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
yes the theory makes sence, but its more the code that's the problem, but im not sure what to write in the for loop
>> but im not sure what to write in the for loop

Nothing special, just copy an item from one position to another :

        items[i] = items[i + 1];
sry for the late answer, ill look in to it tomorrow
my code was probably not what you had in mind, but this is how ive tried but now it just sets all of it to 0
i forgot the code:
void remove_idle(FridgeItem items[], int &num)
{
     
for(int k=0; k<num;k++)
{
         if (items[k].amount = 0)
         {
              
                   for(int i=k; i<num; i++)
                   {
                   items[i] = items[i+1];
                   }
}
}
 
}

Open in new window

SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
ofcourse, don't know why i forgot ==.

also, i am not 100% sure about  2), but does this solve it?
void remove_idle(FridgeItem items[], int &num)
{
     
for(int k=0; k<num;k++)
{
         if (items[k].amount == 0)
         {
              
                   for(int i=k; i<num; i++)
                   {
                   items[i] = items[i+1];
                   }
         num--;
}
}
 
}

Open in new window

>> also, i am not 100% sure about  2), but does this solve it?

No. But if you put the num-- BEFORE the for loop (inside the if), then it would solve it ;)
thanks you, i hope that i can actually make a function myself that adds something to it without asking you :D but hopefully i'll learn someday
>> thanks you

No problem. If you show the function you have now, I'll give it a last look-over if you want ;)


>> i hope that i can actually make a function myself that adds something to it without asking you :D but hopefully i'll learn someday

You're doing fine !! Programming is not the easiest thing to do, and we've all needed help and guidance in the beginning.

The only thing I ask is that you try to understand the code I post, and the explanations I give. And whenever you're not sure about something or you need me to clarify something, don't hesitate to ask.
okay the thing with doing the add function didn't hold up ;)

for some reason, it doesn't put in my new value, but i can print it out in the for loop, but i don't get it when i choose to see all of them
void new_product (FridgeItem items[], int &num)
{
std::string name;
int amount;
     std::cout<<"Enter name of the product ";
     std::cin>>name;
     std::cout<<std::endl;
     std::cout<<"Enter the amount of "<<name<< " ";
     std::cin>>amount;
     
     for(int i=num; i<=num;i++) //num should tell me the number 2 (cause 1 has been deleted) so that should be free
     {
             items[i].name = name;
             items[i].amount = amount;
             std::cout<<items[i].name<<" "<<items[i].amount;
     }
 
}

Open in new window

>>      for(int i=num; i<=num;i++)

Look closely ... what does this do ? How many times will this loop ? Do you need this loop ?

Also, if you add an item, you'll have to increment num of course ...
>>Also, if you add an item, you'll have to increment num of course ...
tried to do that, got spam and error ;)

but no i don't need it, (doh me) so i took it out, but same thing happens. but the thing i really don't get is that it can print it inside the function, but not when i try it in the function ment to it (udskriv). can't i use num to tell it what place it should be in, it seems as it never gets to be in the array?
void new_product (FridgeItem items[], int &num)
{
std::string name;
int amount;
     std::cout<<"Enter name of the product ";
     std::cin>>name;
     std::cout<<std::endl;
     std::cout<<"Enter the amount of "<<name<< " ";
     std::cin>>amount;
     
             items[num].name = name;
             items[num].amount = amount;
             std::cout<<items[num].name<<" "<<items[num].amount;
    
 
}

Open in new window

>> it seems as it never gets to be in the array?

That's because you still haven't incremented num.

Say that num is 2 before you call the function. Then you will call the function, and it will add an item in the array, but it will NOT increment num, so it will still be 2.
Then if you want to show the contents of the array, it will only show the first two items (since num is 2), and NOT the item you just added.

So :

void new_product (FridgeItem items[], int &num) {
     if (num >= 19) return;      // <--- add this check so we don't write past the end of the array !!
 
     std::string name;
     int amount = 0;
 
     std::cout << "Enter name of the product ";
     std::cin >> name;
     std::cout << std::endl;
     std::cout << "Enter the amount of " << name << " ";
     std::cin >> amount;
 
     items[num].name = name;
     items[num].amount = amount;
     std::cout << items[num].name << " " << items[num].amount;
 
     ++num;            // <--- increment num here !!!    
}

Open in new window

Note that you also don't need those temporary values (unless you want to do some error checking on them), so this works as well :


void new_product (FridgeItem items[], int &num) {
     if (num >= 19) return;      // <--- add this check so we don't write past the end of the array !!
 
     std::cout << "Enter name of the product ";
     std::cin >> items[num].name;         // <--- write directly to the correct string
     std::cout << std::endl;
     std::cout << "Enter the amount of " << name << " ";
     std::cin >> items[num].amount;       // <--- write directly to the correct int
 
     std::cout << items[num].name << " " << items[num].amount;
 
     ++num;            // <--- increment num here !!!    
}

Open in new window

thanks, although im not sure why you have to increase num everytime?
>> thanks, although im not sure why you have to increase num everytime?

Did you understand my earlier explanation ? Repeated here :


Say that num is 2 before you call the function. Then you will call the function, and it will add an item in the array, but it will NOT increment num, so it will still be 2.
Then if you want to show the contents of the array, it will only show the first two items (since num is 2), and NOT the item you just added.


If not, then let me know, and I'll explain it differently ;)
ofcourse now i understand it. thanks, much appreciated
>> ofcourse now i understand it.

Good :)
Your udskriv function needs the num parameter to know how many items the fridge contains. It will only show the first num items (as it should).


If you want, you can post your complete code, so I can give it a look-over ...
what would be nice:
//main.cpp
#include <iostream>
#include "koleskab.h"
 
using namespace std;
 
int main()
{
        int valg = 0;
    
    FridgeItem fridge[19] = {                     // <--- move the fridge in the main
                                {"cheese", 0},
                                {"water", 1},
                                {"milk", 2}
                            };
    int fridgeNum = 3;                            // <--- there are currently 3 items in the fridge
 
 for(int i=0; i<100; i++)
 {
 remove_idle(fridge, fridgeNum);
    cout<<"---------MENU:---------"<<endl<<endl;
    
    cout<<"Press 1 to view a list of products available in the fridge."<<endl;
    cout<<"Press 2 to change a product in the fridge."<<endl;
    cout<<"Press 3 to add new products to the fridge."<<endl;
    cout<<"Press 4 to close Fridge Control"<<endl;
    cout<<"Choose: ";
    cin>>valg;
    cout<<endl<<endl;
    switch(valg)
    {
                case 1 :
                     udskriv(fridge, fridgeNum);    // <-- pass the fridge array as well as the number of items currently in it
                     break;
                case 2 :
                     change(fridge, fridgeNum);
                     break;
                case 3 :
                     new_product(fridge, fridgeNum);
                     break;
                case 4 :
                     return 0;
                     break;
                default :
                     cout<<"Please press 1, 2, 3 or 4"<<endl;
                     break;
    }
    cout<<endl;
}
    system("PAUSE");
    return 0;
}
 
 
//koleskap.cpp
 
#include "koleskab.h"
#include <iostream>
 
void udskriv(FridgeItem items[], const int num)        // <--- modify the parameter like this
{
     std::cout<<"Products in the fridge: "<<std::endl;
     for (int i = 0; i<num; i++)        // <--- use an int as array index
     {
             std::cout << items[i].name << " : " << items[i].amount << std::endl;  // <--- we output the name and amount of each item in the fridge
     }
}
 
void change(FridgeItem items[], int &num)
{
     int choice;
     int amount;
     std::cout<<"Enter the number of which item you want to change the status on: "<<std::endl;
     
     for (int i = 0; i<num; i++)
     {
         
         std::cout<<"Number "<<i<<" = "<<items[i].name<<" : "<<items[i].amount<<std::endl;
     }
     std::cin>>choice;
 
std::cout<<"You have chosen "<<items[choice].name<<". There are "<<items[choice].amount<<" in the fridge."<<std::endl;
std::cout<<"Enter the new amount of "<<items[choice].name<<", or the same amount to cancel: ";
std::cin>>amount;
items[choice].amount = amount;
std::cout<<"There are now "<<items [choice].amount<<" "<<items[choice].name<<" ."<<std::endl;
}
 
    void new_product (FridgeItem items[], int &num)
    {
if(num>19)return;
 
         std::cout<<"Enter name of the product ";
         std::cin>>items[num].name;
         std::cout<<std::endl;
         std::cout<<"Enter the amount of "<<items[num].name<< " ";
         std::cin>>items[num].amount;
         
         std::cout<<items[num].name<<" "<<items[num].amount;
        
    num++;
    }
 
 
 
void remove_idle(FridgeItem items[], int &num)
{
     
for(int k=0; k<num;k++)
{
         if (items[k].amount == 0)
         {
              num--;
                   for(int i=k; i<num; i++)
                   {
                   items[i] = items[i+1];
                   }
         
}
}
 
}
 
//koleskab.h
 
#ifndef KOLESKAB_H            // <--- add include guards !!!
#define KOLESKAB_H
 
#include <string>
 
typedef struct FridgeItem {     // <--- the struct is declared here
   std::string name;
   int amount;
} FridgeItem;
 
void udskriv(FridgeItem items[], const int num);// <---  implemented in koleskap.cpp
void change(FridgeItem items[], int &num);      // <---  implemented in koleskab.cpp
void new_product(FridgeItem items[], int &num); // <---  implemented in koleskab.cpp
void remove_idle(FridgeItem items [], int &num);// <---  implemented in koleskap.cpp
 
#endif /* KOLESKAB_H */

Open in new window

In your change function you have :

     std::cin>>choice;

What happens if the user enters an invalid value ? ie. a value smaller than 0 or larger than num. Be careful with this !!


The rest looks fine to me.

Take care of properly indenting your code though ... It makes debugging/modifying a lot easier.

        http://en.wikipedia.org/wiki/Indent_style
yes i know that with the

std::cin>>choice;

as far as i remember there is some code i can use to prevet this. just have to find it.
but im glad that it looks good
>> as far as i remember there is some code i can use to prevet this.

Just check whether the value the user entered is between 0 and 19 (not inclusive).
sorry it has taken a bit long, but went away a couple of days with no internet. anyway ill close this Q as good as i can. and thank you very very much for all the help you have provided. it really helped
thanks for all the help, i really appreciate it! i have tried to take those comments that helped me the most, and was most related to the question. but thanks alot again