C++学习笔记(二)

时间:2022-12-25 22:33:45

C++重载(overloading)和其它编程语言中的重载概念基本上是一致的。C++重载包括操作符重载与函数重载,下面通过例子来说明。

操作符重载


操作符重载使用关键字operator。

操作符重载能够使同一个操作符具有不同的操作含义,满足更广泛范围的操作需要。例如,对于一个容器类my_list,你可以重载操作符+=号,重载的含义是对两个MyList使用+=执行相加,表示将两个my_list的内容合并到一起,下面实现my_list的操作符重载,代码如下所示:

#include <iostream>
#include <list>

using namespace std;

class my_list;
void test_my_list();

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

class my_list {
public:
my_list(list<int> &a_list):int_list(a_list) {
}
inline my_list& operator+=(const my_list& some_my_list) {
if(some_my_list.int_list.size()) {
int_list.merge(some_my_list.int_list);
}
return *this;
}
void print_list() {
cout<<"size("<<int_list.size()<<"):";
list<int>::iterator iter;
for(iter=int_list.begin(); iter!=int_list.end(); iter++) {
cout<<*iter<<" ";
}
cout<<endl;
}
private:
list<int> &int_list;
};

void test_my_list() {
list<int> ll;
ll.push_back(1);
ll.push_back(2);
ll.push_back(3);
my_list a(ll);
a.print_list();

list<int> new_list;
new_list.push_back(11);
new_list.push_back(12);
my_list b(new_list);
b.print_list();

a += b;
a.print_list();
}

上述代码中,a和b都是my_list类型,执行a+=b的结果是将b中包含的list的集合累加到a的的list集合中。

编译运行,输出运行结果:

[hadoop@localhost c++]$ g++ -Wall -o mynote02 mynote02.cpp 
[hadoop@localhost c++]$ ./mynote02
size(3):1 2 3
size(2):11 12
size(5):1 2 3 11 12
可见,实现了操作符重载,实现两个my_list集合的合并。

函数重载

函数重载都是为了能够共享同一个函数名称,而具有相同的函数名称的函数具有不同类型的参数,这些具有相同函数名称的函数就是通过重载而定义的。一定要明确,重载的函数或者具有不同类型的形参,或者具有不同个数的形参。例如,如果同时定义函数int getMax(int &x, int &y)与int getMax(int x, int y),这两个函数是不能够重载的,编译器无法辨认到底调用的是哪一个函数。
举个简单的例子:
#include <iostream>
#include <string>
#include <list>
#include <deque>

using namespace std;

string& get_max(list<string>& container);
string& get_max(deque<string>& container);
string& get_max(string& a, string& b);

string max_string("");

int main() {
list<string> container;
container.push_back("hello, a good day.");
container.push_back("bad boy.");
container.push_back("how flies!");
cout<<get_max(container)<<endl;

deque<string> deck;
deck.push_front("actions speak louder than words.");
deck.push_back("yeah!");
deck.push_front("summer rain.");
cout<<get_max(deck)<<endl;

string a("last night");
string b("so bad.");
cout<<get_max(a, b)<<endl;

return 0;
}

string& get_max(list<string>& container) {
list<string>::iterator iter;
for(iter=container.begin(); iter!=container.end(); iter++) {
if((iter->size()>max_string.size()) {
max_string = *iter;
}
}
return max_string;
}

string& get_max(deque<string>& deck) {
for(int i=0; i<deck.size(); i++) {
if(deck[i].size()>max_string.size()) {
max_string = deck[i];
}
}
return max_string;
}

string& get_max(string& a, string& b) {
max_string = a.size()>=b.size() ? a : b;
return max_string;
}

上面声明并定义了三个同名的函数,都是求最长的字符串,这三个函数是重载的例子:

函数string& get_max(list<string>& container);与函数string& get_max(deque<string>& container);重载,函数名称相同,参数个数相同,但是参数类型不同;

函数string& get_max(list<string>& container);与string& get_max(string& a, string& b);重载,函数名称相同,但是参数个数不同;

函数string& get_max(deque<string>& container);与string& get_max(string& a, string& b);重载,函数名称相同,但是参数个数不同;

编译运行,输出结果如下所示: 

[shirdrn@localhost 02]$ g++ -Wall -o mynote02 mynote02.cpp 
[shirdrn@localhost 02]$ ./mynote02
hello, a good day.
actions speak louder than words.
last night

可见,对于上面三个函数,编译器能够分辨出实际调用的是哪一个函数,因此是合法的函数声明和定义。