C++继承中成员变量关系及访问方法的深入探究
2016-05-31 10:11
483 查看
在用C++做工程时,继承是C++最常用的特性之一,因为它会使得工程复用性很高。但是现在存在一个问题,例如我们在使用MFC库时,往往会去继承库里面的一个类,但是我们并不去看父类里面的实现代码,所以在定义成员变量的时候可能会和父类里面的成员变量一样。但是这样会产生什么后果我们基本不怎么去关心,因为很多人都觉的无关紧要,都只是想着定义就行,并没有过关心它的原理及根本的东西。今天就来说说出现这样的问题会不会对程序产生影响。首先先看一段代码。
上面的程序打印结果为
Parent::i = 1
Child::i = 3
Parent::j = 4
毫无疑问,我们可以使用 “::” 作用域分辨符来区分子类和父类中的相同的成员变量,但是往往我们在类中访问成员变量时基本没有用过作用域分辨符,究竟在不使用的情况下会发生怎样的情况呢?下面我们来在看一段代码
所以默认如果不用作用域分辨符的话,编译器会使用本类中定义的那个变量
例如:i = a;j = b;
这里的赋值代表的就是
Child::i 和
Child::j 。如果真的要操作父类的 i、j那么就需要作用域分辨符“::”来确定。所以我们在定义变量的时候即使和父类同名也没关系,不会对程序造成影响,因为我们一般在类里面定义的成员变量本意都是在本类中使用
总结:当子类中有和父类一样名字的成员变量,在子类使用此变量时,当不使用作用域分辨符时,默认会使用子类的变量。
可以这样理解:当在类里面访问成员变量时,先看看自己有没有,自己有就直接用,如果自己没有,那么看老爸(父类)有没有,父类如果有就用父类的(前提这个变量在父类要是protected或者public,如果在父类这个成员变量是private,这个成员变量继承给子类,子类里面照样是不可访问的),父类如果没有程序就会报错。
所以我们在程序设计时,如果子类和父类出现两份一模一样的成员变量,要访问父类中的变量,必须使用作用域分辨符,如果不想使用作用域分辨符,那就在设计类的时候让两个名字不要冲突。
#include <iostream> using namespace std; // 定义了一个 Parent 类型的父类,里面有 i、j 两个成员变量(protected 表示成员变量只能在父类子类中被访问) class Parent { protected: int i; int j; }; // 定义一个子类 Child,它共有继承了 Parent 类,里面有一个和父类一样的成员变量 i class Child : public Parent { protected: int i; // f()函数的作用是打印 当前父子类中的 i、j void f() { cout << "Parent::i = " << Parent::i << endl; cout << "Child::i = " << Child::i << endl; cout << "Parent::j = " << Parent::j << endl; } public : // 子类的构造函数 Child(int i, int j) { Parent::i = i; // 把父类中的 i 赋值为参数 i Child::i = j; // 把子类中的 i 赋值为参数 i Parent::j = i + j; // 把父类中的 j 赋值为参数 j f(); // 条用 f() 函数 } }; int main() { // 定义一个 Child 类型的对象,参数为 1, 2 Child c1(1, 3); return 0; }
上面的程序打印结果为
Parent::i = 1
Child::i = 3
Parent::j = 4
毫无疑问,我们可以使用 “::” 作用域分辨符来区分子类和父类中的相同的成员变量,但是往往我们在类中访问成员变量时基本没有用过作用域分辨符,究竟在不使用的情况下会发生怎样的情况呢?下面我们来在看一段代码
#include <iostream> using namespace std; // 定义了一个 class Parent { protected: int i; int j; }; class Child : public Parent { protected: int i; int j; void f() { cout << "Parent::i = " << Parent::i << endl; cout << "Parent::j = " << Parent::j << endl; cout << "Child::i = " << Child::i << endl; cout << "Child::j = " << Child::j << endl; } public : Child(int a, int b) { i = a; j = b; f(); } }; int main() { Child c1(1, 3); return 0; } 运行结果为 Parent::i = -858993460 Parent::j = -858993460 Child::i = 1 Child::j = 3
所以默认如果不用作用域分辨符的话,编译器会使用本类中定义的那个变量
例如:i = a;j = b;
这里的赋值代表的就是
Child::i 和
Child::j 。如果真的要操作父类的 i、j那么就需要作用域分辨符“::”来确定。所以我们在定义变量的时候即使和父类同名也没关系,不会对程序造成影响,因为我们一般在类里面定义的成员变量本意都是在本类中使用
总结:当子类中有和父类一样名字的成员变量,在子类使用此变量时,当不使用作用域分辨符时,默认会使用子类的变量。
可以这样理解:当在类里面访问成员变量时,先看看自己有没有,自己有就直接用,如果自己没有,那么看老爸(父类)有没有,父类如果有就用父类的(前提这个变量在父类要是protected或者public,如果在父类这个成员变量是private,这个成员变量继承给子类,子类里面照样是不可访问的),父类如果没有程序就会报错。
所以我们在程序设计时,如果子类和父类出现两份一模一样的成员变量,要访问父类中的变量,必须使用作用域分辨符,如果不想使用作用域分辨符,那就在设计类的时候让两个名字不要冲突。
相关文章推荐
- HDU-1798 Tell me the area (C++和Java【水】两圆相交求公共面积)
- C语言预处理器(十五)
- C++ Primer 类 12.3-12.5 作用域,construtor,friend
- 【C语言】07-基本语句和运算
- leetcode #71 in cpp
- C++统计中英文大小写字母、数字、空格及其他字符个数的方法
- 多线程求行列式值
- 蒙特卡洛法多线程求圆周率
- 谈一谈C和c++中struct关键字
- 九度OJ--1163(C++)
- USACO5.3 IDDFS_强连通_二维树状数组_斐蜀定理_矩形切割
- 【VS开发】浅谈C/C++中的static和extern关键字
- leetcode #70 in cpp
- C++中的异常浅析
- C++入门基础知识:类和引用
- Google C++编程风格指南
- C++小里程
- C++实现将简单密码译回原文的方法
- c++获取本地ip
- c语言获取文件目录