const成员
? ? ? ? const数据成员:const类型的变量是不可修改的,只读模式。必须采用初始化参数列表方式进行初始化
? ? ? ? const对象: const修饰的对象,常对象只能调用常成员函数
? ? ? ? const成员函数:const写在函数后面,就是const成员函数(常成员函数),常成员函数不能修改数据成员,只能读取数据成员。可与普通函数同时存在(函数的重载),普通对象调用普通函数,也可以调用常成员函数,但const对象无法调用普通函数。
????????
#include<iostream>
#include<string>
using namespace std;
class Student
{
public:
Student(string name,int age):age(age) //用构造函数初始化参数列表初始化
{
Student::name = name;
//Student::age = age; //Student中的age被const修饰,只能读取不能修改
}
void print()
{
cout << name << "\t" << age << endl;
}
void printData1()
{
cout << "普通函数" << endl;
}
void print()const
{
cout << "常成员函数" << endl;
}
void printData2()const
{
cout << "常成员函数" << endl;
}
protected:
string name;
const int age;
};
int main()
{
Student stu1("小明",16);
stu1.print(); //普通函数和常成员函数同时存在,普通对象调用普通函数
stu1.printData2(); //在没有普通函数时,可以调用常成员函数
const Student stu2("李丽",15);
stu2.print(); //普通函数和常成员函数同时存在,常对象调用常成员函数
stu2.printData2(); //常对象调用常成员函数
//stu2.printData1(); //报错,常对象无法调用普通函数
return 0;
}
static成员
? ? ? ? static成员不属于对象,是属于类的,意味着static成员是所有对象的共有的,并且可以不用对象调用
? ? ? ? static成员依旧受权限限定
? ? ? ? static数据成员:必须在类外初始化,不再需要static修饰,但需要类名限定。并且static不能在类中初始化以及初始化参数列表方式初始化
? ? ? ? static成员函数:在函数前写static就是static成员函数。static函数调用非静态成员,必须要制定对象
? ? ? ? static对象在程序结束前释放
#include<iostream>
#include<string>
using namespace std;
class Student
{
public:
static int num;
Student(string name = ""):name(name)
{
num++;
}
static void print();
static void printData(Student&stu)
{
//静态成员函数调用非静态成员数据,必须要制定对象
cout << stu.name << '\t' << num << endl;
}
protected:
string name;
}
//类外初始化时不需要static修饰,但需要类名限定
int Student::num = 1;
void Student::print()
{
//静态成员函数调用静态数据没有要求
cout << num << endl;
}
int main()
{
cout << Student::num << endl; //静态数据成员的访问可以不需要对象
//共有
Student stu("小明"); //num = 2
Student* pstu = new Student("newstu"); //num = 3
Student arrstu[4]; //num = 7
//num的值都一样说明调用的num是共有的
cout << stu.num << endl; //num = 7
cout << Student::num << endl; //num = 7
cout << pstu->num << endl; //num = 7
//静态成员函数的调用
Student::print();
stu.print();
Student::printData(stu);
return 0;
}
????????
友元
友元:friend描述的关系。友元只是提供一个场所,赋予对象具有打破类中的权限限定(无视权限)
友元函数:用friend修饰的函数。还可以以另外一个成员函数充当友元函数
#include<iostream>
using namespace std;
class MM
{
public:
MM(string name,int age):name(name),age(age){}
friend void printData()
{
//cout << name << age << endl; //报错,友元函数不属于类,不能直接访问成员
MM mm("girl",18);
//友元函数提供一个场地,让对象无视权限访问
cout << mm.name << "\t" << mm.age << endl;
}
protected:
string name;
private:
int age;
friend void printData2(MM& mm);
};
//类外实现友元函数不需要friend修饰,也不用类名限定
void printData2(MM& mm)
{
cout << mm.name << '\t' << mm.age << endl;
}
class A
{
public:
void printB();
protected:
string name;
};
class B
{
public:
friend void A::printB();
protected:
string name = "B";
};
void A::printB()
{
B b;
cout << b.name << endl;
}
int main()
{
printData(); //直接访问友元函数
MM mm("小芳",18);
printData2(mm);
A a;
a.printB();
return 0;
}
友元类?
#include<iostream>
using namespace std;
class MM
{
friend class GG;
public:
MM(string name,int age):name(name),age(age){}
protected:
string name;
int age;
};
class GG
{
public:
void print()
{
MM mm("baby",18);
cout << mm.name << '\t' << mm.age << endl;
}
void printMM(MM & mm)
{
cout << mm.name << '\t' << mm.age << endl;
}
MM& returnMM(MM& mm)
{
return mm;
}
protected:
};
//互为友元类的写法
class A
{
friend class B;
public:
void printData();
protected:
string data = "A";
};
class B
{
public:
friend class A;
void printData()
{
A a;
cout << a.data << endl;
}
protected:
string data = "B";
};
void A::printData()
{
B b;
cout << b.data << endl;
}
int main()
{
MM mm("mm",18);
GG gg;
gg.print();
gg.printMM(mm);
//cout << gg.returnMM(mm).name << endl; //只要出了友元类就没有权限
//互为友元
B b;
b.printData();
A a;
a.printData();
return 0;
}
this指针与explicit
????????explicit:修饰构造函数使用,不让隐式转换构造
????????this指针:避免形成名和数据成员同名,指向被调用函数中对象的地址。也可以充当函数返回值,返回对象本身。但是不能载static函数中使用。
#include<iostream>
using namespace std;
class MM
{
public:
explicit MM(string name = "",int num = 0):name(name),num(num){}
void initData(string name,int num)
{
//类名限定,帮助计算机去识别
MM::name = name;
this->num = num;
}
void print()
{
cout << name << "\t" << num << endl;
}
protected:
string name;
int num;
};
int main()
{
//MM mm = 23; //报错,已经被explicit修饰,不让隐式转换构造
MM mm(23);
mm.print();
mm.initData("莉丝",18);
mm.print();
return 0;
}
|