to keep variables private I need a passthrough

I have achieved to overload operator <<, I have found out that It can not be a member of the function if I want to overload <<, so at the moment I have had to make public every member to make the variable accesible...but I would like to keep them private...I have read that I have to do something like a passthrough...I gues it must be a member function who is able to take the variable and send them to the operator but I dont know how...at the momento I have got this..


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
69
70
71
72
73
//Special members.

#include <stdio.h>
#include <iostream>

using namespace std; 

class integer{
public:
	int* ptr;
	int value;
	
		//default constructor
		integer():ptr(new int),value(0){};
		//destructor
		~integer(){delete ptr;}
		//constructor with int parameter
		integer (const int& x,const int& y):ptr ( new int(x)),value(y){}
		//copy constructor
		integer(const integer& x):ptr(new int ( x.content())),value(x.value){}
		//copy assignment
		integer operator=(const integer& x){
			delete ptr;
			ptr = new int(x.content());
			value = x.value;
			return *this;
		}
		//move constructor
		integer (integer&& x):ptr(x.ptr),value(x.value){x.ptr = nullptr;}
		//move assignament
		integer operator=(integer&& x){
			delete ptr; 
			ptr = x.ptr;
			x.ptr=nullptr;
			value = x.value;
			return *this;
			
		}
		
		//access content
		const int& content()const {
			return *ptr;
		}
		//addition
		integer operator+(const integer& x){
			return integer(content()+x.content(),this->value+x.value);
	
		
		}
		
		
		
};

		
		void operator<<(ostream &os,const integer& x){
			cout<<x.content()<< " "<<x.value;
		}
		

int main(){
	
	integer first = integer(5,4);
	integer second(2,5);
	integer third = second;
	cout<<third;
	cout<<"\n";
	first = second;
	second = third + first;
	cout<<second;
	cout<<"\n";
	return 0;
}

@Yanson

operator<< cannot be a member function of the class as the lefthand operand must be an ostream&, and that doesn't work for class members (the class is always the lefthand operand.)

@Winsu

As Yanson gave as an altenative, you can make the operator<< overload a friend of you class, then you can avoid making data members public.

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
#include <iostream>
using namespace std; 

// simplified class
class integer {
private:
    int value; // private!!
public:
    integer(int v = 0) : value(v) {}

    // make operator<< overload a friend so can access private members
    friend ostream& operator<<(ostream &os, const integer& x);
};

// should return ostream& ref (to support operator chaining,
// like cout << i << j << k << "\n")
ostream& operator<<(ostream &os, const integer& x){
    os << x.value; // write integer private data to os, not cout!!
    return os; // and return os
}

int main(){
    integer first(3);
    integer second(2);
    integer third(1);
    integer fourth; // default to zero

    // chained calls
    cout << first << ", " << second << ", " <<  third << ", " << fourth << "\n";

    return 0;
}


or you could provide a public method which writes to a stream, if this might be useful in other situations:

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
#include <iostream>
using namespace std; 

// simplified class
class integer {
private:
    int value; // private!!
public:
    integer(int v = 0) : value(v) {}

    // public write method
    ostream& write(ostream &os) const;
};

// could have a void return instead, but returning the ostream&
// might help with error handling
ostream& integer::write(ostream &os) const {
    os << value;
    return os;
}

ostream& operator<<(ostream &os, const integer& x){
    return x.write(os);
}

int main(){
    integer first(3);
    integer second(2);
    integer third(1);
    integer fourth; // default to zero

    // chained calls
    cout << first << ", " << second << ", " <<  third << ", " << fourth << "\n";

    return 0;
}


Andy
Last edited on
When you say that It might hel with error handling you mean once I have the ostream I can chech his error state, dont you?
I undertand how both code work completely, but I have question...., for example with operator + overloaded when you do this a + b...It's kind of equivalent to a.operator+(b).Knowking this I understand why operator << can not be a member...but when I think in the call for operator << when It's overloaded, it must be called with an ostream object...so thinking that a is an object of integer ( integer a) the equivalent of ...cout<<a, could be something like this.. os.operator<<(a)...so operator << always use os as a member os ostream and any type too....more than a question It has been an explanationof I understand and If there is something that I am missing..

Thanks
But trying to do it like your second suggestions I'am having an issue,the compiler launch me an errot which says: initializing argument 1 of 'std::ostream& operator<<(std::ostream, const integer&)' multiplicated by 3 because of 3 << in main...I dont knwo if doing that I have to change somethin in my constructor...this is my code...I paste everything..
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
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94

//Special members.

#include <stdio.h>
#include <iostream>

using namespace std; 

class integer{
private:
	int* ptr;
	int value;
	public:
		//default constructor
		integer():ptr(new int),value(0){};
		//destructor
		~integer(){delete ptr;}
		//constructor with int parameter
		integer (const int& x,const int& y):ptr ( new int(x)),value(y){}
		//copy constructor
		integer(const integer& x):ptr(new int ( x.content())),value(x.value){}
		//copy assignment
		integer operator=(const integer& x){
			delete ptr;
			ptr = new int(x.content());
			value = x.value;
			return *this;
		}
		//move constructor
		integer (integer&& x):ptr(x.ptr),value(x.value){x.ptr = nullptr;}
		//move assignament
		integer operator=(integer&& x){
			delete ptr; 
			ptr = x.ptr;
			x.ptr=nullptr;
			value = x.value;
			return *this;
			
		}
		
		//access content
		const int& content()const {
			return *ptr;
		}
		//addition
		integer operator+(const integer& x){
			return integer(content()+x.content(),this->value+x.value);
	
		
		}
	//	friend ostream& operator<<(ostream & os,const integer x);
			
		ostream& write(ostream& os)const;
		
		
		
};
		ostream& integer::write(ostream& os) const{
			os<<value<<*ptr;
			return os;
		}
					
		
		ostream& operator<<(ostream os,const integer& x){
			return x.write(os);
		}
		
		
			//ostream& operator<<(ostream & os,const integer x){
			
			//os<<"First parameter";
			//os<<x.value;
			//os<<"Second parameter";
			
			//os<<x.content();
			
			//os<<"\n";
		//	return os;
		//}
		

int main(){
	
	integer first = integer(5,4);
	integer second(2,5);
	integer third = second;
	cout<<third<<" "<<second<<" "<<first<<"\n";
	cout<<"\n";
	first = second;
	second = third + first;
	cout<<"\n";
	return 0;
}
You're missing the & -- operator takes an ostream& as its first param, not an ostream.

1
2
		ostream& operator<<(ostream& os,const integer& x){
                //               need this ^ 


Andy
Last edited on
That's true thank you!!
Topic archived. No new replies allowed.