程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> C++的一個語法問題

C++的一個語法問題

編輯:C++入門知識

今天看到《C++ primer》上說:可以用派生類對象初始化基類對象,根據是派生類對象可以賦值給基類的對象的引用。這裡我覺得有個語義上的問題:派生類在繼承基類的時候,基類的private成員是不可見的,那麼基類初始化private對象的時候,就用了派生類的不可見成員去初始化它了。
先貼段測試代碼:
 1 #include<iostream>
 2 using namespace std;
 3 class A
 4 {
 5       int mem1,mem2;
 6 public:
 7        A(const A& a);
 8        A(int a, int b):mem1(a),mem2(b){}
 9        int fun1(){return mem1;}
10        int fun2(){return mem2;}
11 };
12 A::A(const A& a)
13 {
14            mem1 = a.mem1;
15            mem2 = a.mem2;
16            cout << "A's copy constructor called"<<endl;
17 }
18 class B : public A
19 {
20       int mem3;
21 public:
22   B(int a, int b, int c): A(a,b),mem3(c){}
23     int fun3(){return fun1()};
24 };
25 int main()
26 {
27     B b(1,2,3);
28     A aob(b);
29 }
30
這段代碼輸出:A's copy constructor called(這是用G++編譯器的,DEV C++ 編譯通過,可是運行沒有輸出)
確實如書上說的派生類對象可以賦值給基類的對象的引用,所以調用了拷貝構造函數。其實根據《inside the C++ object model》的說法,派生類的對象中將會保存基類的non-static數據成員的,那麼即使不可見,可以用來初始化也在情理之中。
可是再看被初始化對象調用其成員函數的代碼:
 1 #include<iostream>
 2 using namespace std;
 3 class A
 4 {
 5       int mem1,mem2;
 6 public:
 7        A(const A& a);
 8        A(int a, int b):mem1(a),mem2(b){}
 9        int fun1(){return mem1;}
10        int fun2(){return mem2;}
11 };
12 A::A(const A& a)
13 {
14            mem1 = a.mem1;
15            mem2 = a.mem2;
16            cout << "A's copy constructor called"<<endl;
17 }
18 class B : public A
19 {
20       int mem3;
21 public:
22   B(int a, int b, int c): A(a,b),mem3(c){}
23     int fun3(){return fun1()};
24 };
25 int main()
26 {
27     B b(1,2,3);
28     A aob(b);
29     cout <<aob.fun1() << aob.fun2();//the //difference
30 }
31
這就編譯錯誤了:tess.cpp:28:36: error: request for member ‘fun2’ in ‘aob’, which is of non-class type ‘A(B)’這在兩個上述編譯器都是這樣的結果。那麼這個對象就無法調用基類的函數了。
我個人膚淺的推斷:A(B)將被編譯器認為是一種新的類型對待,那麼怎麼確定這種類型的接口函數呢?這不就有問題了嗎?
我再多此一舉的實驗下如下代碼:
 1 #include<iostream>
 2 using namespace std;
 3 class A
 4 {
 5       int mem1,mem2;
 6 public:
 7        A(const A& a);
 8        A(int a, int b):mem1(a),mem2(b){}
 9        int fun1(){return mem1;}
10        int fun2(){return mem2;}
11 };
12 A::A(const A& a)
13 {
14            mem1 = a.mem1;
15            mem2 = a.mem2;
16            cout << "A's copy constructor called"<<endl;
17 }
18 class B : public A
19 {
20       int mem3;
21 public:
22   B(int a, int b, int c): A(a,b),mem3(c){}
23     int fun3(){return fun1();}
24 };
25 int main()
26 {
27     B b(1,2,3);
28     A aob(b);
29     cout <<aob.fun3();// the difference
30 }
31
結果是編譯錯誤:‘class A’ has no member named ‘fun3’這一點也不意外,那麼這樣的對象不就真的沒有了接口了?小弟我虛心等待大牛們的解答,希望能在原理上給俺個解釋,不勝感激!

 

摘自  no_rain 

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved