address book using classes

Hi,
the exercise is clear. Create a phone book with the name, last name and phone number. Please have a look on my script. I can't understand the view_friends() is not working :(. How to fix it?

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
#include <iostream>
#include <list>
using namespace std;
void add_friend();
void view_friends();
void print_menu();
void print_info();

    class Friend{
        public:
        string Name;
        string Last_name;
        string phone_number;

        void print_info(){
        cout<<Name<<""<<Last_name<<""<<phone_number<<endl;
        }

        void add_friend(){
        cout<<"Enter name: ";
        cin>>Name;
        cout<<"Enter last name";
        cin>> Last_name;
        cout<<"Enter phone number:";
        cin>>phone_number;
        }
    };

    list <Friend> list_of_friends;

    void print_menu(){
         char ch=0;
         string menu_string= "--- Select ---\n"
                            "1:add\n"
                            "2:View\n"
                            "3: Exit\n";
        do{
           cout<<menu_string;
           if (ch == '1') add_friend();
           else if (ch == '2') view_friends();
       }
       while((ch=cin.get()) !='3');
    }

    void view_friends(){
           for(Friend name: list_of_friends){
           cout<<name<<endl;
       }
    }


int main()
{
    print_menu();
    return 0;
}
try name.print_info() instead of cout << name
your attempt to cout name ... name lacks a friendly << operator or I missed it so you can't stream it. Instead of a convoluted friend stream operator, you can also have your object cast itself to string and then you can print it. you may have to say cout << (string)name if you do that, as those sometimes don't care to be implicit casts, but its another way to defur the feline.

also, range based for loops would do well with a reference:
for( Friend &name: ... ///avoids copy of a fat object every iteration! ideally also make it const.

also, global data is not good design in larger programs, move friends list to main and pass as a parameter and get used to that as a best practice /habit.

examples:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
struct derp
{
	int x;
	operator string() {return "my value is:"s + to_string(x);}
	 friend ostream& operator<<(ostream& os, const derp& d)
	 { os << d.x; return os; }
};

int main()
{
	derp d;
	d.x = 42;
	cout << (string)d << endl;
	cout << d;
}



my value is:42
42


while the stream operator is nice, I usually want a string.. I almost never output to a console, but I frequently output to a GUI widget... and its minor to use some sort of stringify for both while getting the string out of the stream is annoying (not hard, just cluttery).
Last edited on
@OP Your data model needs to be thought out more carefully than what you have. There are a numerous basic aspects that could be refined but this 'works':

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
#include <iostream>
#include <list>

using namespace std;

class Friend
{
public:
    string Name;
    string Last_name;
    string phone_number;
    
    void print_info()
    {
        cout << Name << "" << Last_name << "" << phone_number << endl;
    }
    
    void add_friend(){
        cout<<"Enter name: ";
        cin>>Name;
        cout<<"Enter last name";
        cin>> Last_name;
        cout<<"Enter phone number:";
        cin>>phone_number;
    }
};

list <Friend> list_of_friends;

void view_friends();

void print_menu()
{
    Friend temp;
    
    char ch=0;
    string menu_string= "--- Select ---\n"
    "1:add\n"
    "2:View\n"
    "3: Exit\n";
    do{
        cout<<menu_string;
        if (ch == '1')
        {
            temp.add_friend();
            list_of_friends.push_back(temp);
        }
        else if (ch == '2')
        {
            view_friends();
        }
    }
    while((ch=cin.get()) !='3');
}

void view_friends()
{
    for(Friend name:list_of_friends)
    {
        name.print_info();
    }
}

int main()
{
    print_menu();
    return 0;
}


Hi! thank you so much for the answers, it works much better but I did not get how to solve the printing menu every interaction. See my update code, I added a pointer & and it's still printing menu after every command:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
//h
#include <iostream>
#include <list>
using namespace std;
void add_friend();
void view_friends();
void print_menu();
void print_info();

    class Friend{
        public:
        string Name;
        string Last_name;
        string phone_number;

        void print_info(){
        cout<<Name<<" "<<Last_name<<" "<<phone_number<<endl;
        }

        void add_friend(){
        cout<<"Enter name: ";
        cin>>Name;
        cout<<"Enter last name: ";
        cin>> Last_name;
        cout<<"Enter phone number: ";
        cin>>phone_number;
        cout<<" ";
        }
    };

    list <Friend> list_of_friends;

    void print_menu(){

         Friend temp;
         char ch=0;
         string menu_string= "--- Select ---\n"
                            "1:add\n"
                            "2:View\n"
                            "3: Exit\n";
        do{
           cout<<menu_string;
           if (ch == '1'){
            temp.add_friend();
            list_of_friends.push_back(temp);
           }
           else if (ch == '2'){
            view_friends();

           }
       }
       while((ch=cin.get()) !='3');
    }

    void view_friends(){
           for(Friend &name: list_of_friends){
           name.print_info();
       }
    }


int main()
{
    print_menu();
    return 0;
}
it's still printing menu after every command:


because of L42. If you don't want that, then move that cout statement.
Topic archived. No new replies allowed.