-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathclasstemplates.cpp
109 lines (94 loc) · 3.03 KB
/
classtemplates.cpp
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
95
96
97
98
99
100
101
102
103
104
105
106
107
108
/*
* Given input:
* - string = concat
* - int|float = add
* x Line 1: n (int), how many additional lines
* x Line n: types (pair of ints|floats|strings)
*
* Output: Based on type use appropriate method
*
* Create template class AddElements with member add()
* - create specialization for string with member concatentate()
*
*/
#include <iostream>
#include <string>
// Forward declarations:
template <typename T> class AddElements;
template <typename T> std::istream& operator>>(std::istream&, AddElements<T>&);
template <typename T> std::ostream& operator<<(std::ostream&, const AddElements<T>&);
// General templated class
template <typename T>
class AddElements {
private:
T m_first;
T m_second;
public:
AddElements(T first=T(), T second=T()): m_first{first}, m_second{second} { }
T add() const { return m_first + m_second; }
// Note: AddElements cannot be const since sending values into it:
friend std::istream& operator>> <>(std::istream&, AddElements&);
/* Alternatively:
// Use this and can eliminate forward declarations:
friend std::istream& operator>>(std::istream& istr, AddElements& ae) {
istr >> ae.m_first >> ae.m_second;
return istr;
}
*/
// Note: AddElements must be const here or won't work:
friend std::ostream& operator<< <>(std::ostream&, const AddElements&);
};
template <typename T>
std::istream& operator>>(std::istream& istr, AddElements<T>& ae) {
istr >> ae.m_first >> ae.m_second;
return istr;
}
template <typename T>
std::ostream& operator<<(std::ostream& ostr, const AddElements<T>& ae) {
ostr << ae.add();
return ostr;
}
// string specialization of above templated class:
template<>
class AddElements<std::string> {
private:
std::string m_first;
std::string m_second;
public:
std::string concatenate() const { return m_first + m_second; }
friend std::istream& operator>> (std::istream&, AddElements&);
friend std::ostream& operator<< (std::ostream&, const AddElements&);
};
std::istream& operator>>(std::istream& istr, AddElements<std::string>& ae) {
istr >> ae.m_first >> ae.m_second;
return istr;
}
std::ostream& operator<<(std::ostream& ostr, const AddElements<std::string>& ae) {
ostr << ae.concatenate();
return ostr;
}
int main() {
std::size_t lines;
std::string line_types;
AddElements<int> mycol_ints;
AddElements<float> mycol_floats;
AddElements<std::string> mycol_strs;
std::cin >> lines;
for (size_t i = 0; i < lines; ++i) {
std::cin >> line_types;
if (line_types == "string") {
std::cin >> mycol_strs;
std::cout << mycol_strs << '\n';
} else if (line_types == "int") {
std::cin >> mycol_ints;
std::cout << mycol_ints << '\n';
} else if (line_types == "float") {
std::cin >> mycol_floats;
std::cout << mycol_floats << '\n';
} else {
std::cout << "Error: Unexpected type ``" << line_types << "''\n";
return -1;
}
}
return 0;
}