C++ Primer 从入门到放弃-第七章 类 基础概念

C++ Primer 从入门到放弃-第七章 类 基础概念

《C++ Primer》从入门到放弃第七章 类[基础概念&访问控制]

定义抽象数据类型:

初始栗子 Sales_data 类

struct Sales_data {
  // 成员函数
  std::string isbn() const { return bookNo; }
  // 成员函数声明
  Sales_data& combine ( const Sales_data& );
  double avg_price() const;
  // 数据成员
  std::string bookNo;
  unsigned units_sold = 0;
  double revenue = 0.0;
};

// Sales_data 非成员函数声明
Sales_data add(const Sales_data&,const Sales_data& );
std::ostream &print(std::ostream&,const Sales_data& );
std::istream &read(std::istream, Sales_data& );

类内部定义的函数都是隐式的inline函数

引入this:

当调用成员隐式的我们相当于替某个对象调用它,与js类似,c++的this指向调用它的对象,所以函数成员isbn也可以这样定义。

std::string isbn() const { return this.bookNo; }

引入const成员函数

:默认情况下是this的类型是指向类类型非常量版本的常量指针。上面函数中this的默认类型是Sales_data *const.
把const放在参数列表之后,紧跟在后面的const表示this是一个指向常量的指针。这样的函数叫做常量成员函数。
相当于const 指针 指向 this(非常量对象),隐式改变了this对象的类型。

double s = 3.14;
const double *ptr = &s; // 合法
*ptr = 1; // const 保护赋值失败
// 在上述栗子中,const member function 其实就是隐式的把this(Sales_data *const)转换为了const Sales_data *const类型。
std::string isbn() const {  this->bookNo="dfsfdsf"; return this->bookNo; }
// 报错,const 保护, 不可对其进行修改.

类作用域与成员函数:

编译器先编译成员声明然后编译成员函数体,所以无需在意函数体内对编译成员的调用出现次序。

在外部定义成员函数:

必须保持声明匹配。在类外部定义的成员名字必须包含他所属的类名。

// 定义在类外部隐式使用this的成员
double Sales_data::avg_price() const {
  if(units_sold)
    return revenue/units_sold;
  else
    return 0;
}

定义返回this对象的函数:

Sales_data& Sales_data::combine(const Sales_data& rhs){
    units_sold += rhs.units_sold;
    revenue += rhs.revenue;
    return *this;
}

构造函数:

每个类都定义了构造函数,无论何时只要类的对象被创建就会执行构造函数。与其他函数不一样,构造函数没有返回类型。不同于其他构成员函数,constructor 不能被声明为const函数.

我们的demo中没有使用构造函数因为我们执行了默认初始化,使用了默认的构造函数.编译器提供的又被成为合成默认构造函数。

ps: 只有成员全部被赋予了默认值,才适合使用默认的构造函数。

struct Sales_data {
  // 构造函数
  Sales_data(const std::string &s,unsign n,douple p):books(s),units_sold(n),revenue(p*n){}
  // 显式默认构造函数
  Sales_data() = default;
}
// 外部初始化
Sales_data::Sales_data(){

}

新标准规定当我们需要默认行为则使用"=default",内部inline,外部非内联.

当使用内部构造函数时,当参数不足时,其他参数将使用默认初始化.构造函数体为空是因为我们只进行初始化,并没有其他操作.

访问控制与封装:

在C++中使用访问控制符(access specifiers)加强访问控制.
public,说明符在程序内可以访问. 定义在private说明成员可以被类的成员函数访问.在类内部访问控制符可以出现任意次,作用范围到下一个控制符出现为止.

使用class和struct关键字:

使用class和struct的区别之一就是默认访问权限,注意struct也可以使用访问控制符,区别在于默认struct是public而class默认为private.

友元函数:

对于非类的成员函数,就无法访问类内部的成员了,我们可以在类内定义友员函数.

class Box
{
    double width;
    friend void printWidth( Box box );
};
// 此函数不属于Box的成员函数
void printWidth( Box box )
{
   /* 因为 printWidth() 是 Box 的友元,它可以直接访问该类的任何成员 */
   cout << "Width of box : " << box.width <<endl;
}


禽兽一只:《C++ Primer》从入门到放弃zhuanlan.zhihu.com图标


后记: 最近竟然有新手一起来搞事情了,c++一时爽但是没有守望屁股爽,我会每天提醒你们打守望先锋的 .

编辑于 2018-07-23