Overloading Operators in a Template Class

I am simply trying to overload + operator in the friend method. The program works as expected when I don't use a template and simply replace everything with double. I noticed the problem is caused by b3 = b1 + b2 assignment in the main method and I don't know why. The error I keep getting is unresolved external symbol "class Balance<double> const __cdecl operator+(class Balance<double> const &,double)". And I am using Visual Studio. Thanks for all your help in advance.

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
#include <iostream>

using namespace std;

template <typename T>
class Balance {

	friend const Balance<T> operator+(const Balance<T>& b1, const Balance<T>& b2);

private:
	T val_;
public:
	Balance() : val_(0) {}
	Balance(T val) : val_(val) {}
	~Balance() {}
	
	Balance<T>& operator+=(const Balance<T>& b) {
		val_ += b.val_;
		return (*this);
	}

	Balance<T>& operator+=(T d) {
		val_ += d;
		return(*this);
	}

	T getValue() const { return val_; }
};

template <typename T>
const Balance<T> operator+(const Balance<T>& b1, const Balance<T>& b2){
	Balance<T> tmp(b1.val_ + b2.val_);
	return tmp;
}

int main() {
	
	Balance<double> b1(40);
	Balance<double> b2(23.5);
	Balance<double> b3;

	b1 += b2;
	
	// b1 is now 63.5
	cout << b1.getValue() << endl;

	b1 += (-14.5);

	// b1 is now 49.0
	cout << b1.getValue() << endl;

       // THE PROBLEM IS HERE
	b3 = b1 + b2;

	cout << "Should be 72.5: " << b3.getValue() << endl;


	system("pause");
	return 0;
}
Ok, I solved the problem. Unfortunately, the compiler here gives much more information than VS's own compiler in some cases. I forgot to declare the friend function in accordance with the template parameter.

It should be
1
2
friend const Balance operator+<T>(const Balance<T>& b1, 
            const Balance<T>& b2);

Last edited on
If you're friending the specialization for T, you could omit the T, it's a function template after all:

friend const Balance<T> operator+<>(const Balance<T>& b1, const Balance<T>& b2);

You may find it simpler to define an individual friend function for each Balance<T>

1
2
3
4
5
6
class Balance {
    friend const Balance<T> operator+(const Balance<T>& b1, const Balance<T>& b2)
    {
// ...
    }
//. ... 


but the proper solution is to define in terms of +=, in which case you don't need to friend it (unless you care about ADL-only use)

1
2
3
4
5
6
7
8
9
10
11
template <typename T>
class Balance {
private:
    T val_;
// ...
};

template <typename T>
const Balance<T> operator+(Balance<T> b1, const Balance<T>& b2){
    return b1 += b2;
}
Last edited on
Topic archived. No new replies allowed.