2012-11-09 96 views
0

可能重複:
Can inner classes access private variables?
Inner class accessing outer classC++內部類不能訪問外部類的成員

我有嵌套,使他們能夠有沒有額外的輸入變量相互作用的一些簡單的類,但我的編譯器給我一個錯誤。我如何允許它們在不使用&時間作爲函數輸入或具有變量&時間在Vect類中進行交互?

我試過使用相同的邏輯,您可以在代碼中訪問數據,但只能在函數原型的相同位置訪問,而不是包裝在類中。這適用於我除了其他類以外的任何事情。誰能解釋爲什麼?

我已經標記了使用有問題時間變量的地方,並在定義之前使用了註釋行。

/*********/ 
#define MAX_POLY 3 

class Container 
{ 
public: 
    Container(void); 
    ~Container(void); 

    float time;/*********/ 
    class Vect 
    { 
     float P[MAX_POLY],iT; 
    public: 
     Vect(void){iT = 0.0f;P = {0,0,0};} 
     ~Vect(void); 

     float GetPoly(int n){return P[n];} 
     float Render(void) 
     { 
      float t = time - iT;/*********/ 
      float temp[2] = {0,0}; 
      for(int n=0;n<MAX_POLY;n++) 
      { 
       temp[0] = P[n]; 
       for(int m=0;m<n;m++) 
        temp[0] *= t; 
       temp[1] += temp[0]; 
      } 
      return temp[1]; 
     } 
     void SetPoly(int n,float f) 
     { 
      float t = time-iT;/*********/ 
      P[0] = P[2]*t*t + P[1]*t + P[0]; 
      P[1] = 2*P[2]*t + P[1]; 
      //P[2] = P[2]; 
      P[n] = f; 
      iT = time;/*********/ 
     } 
    }X; 
}; 

int main() 
{ 
    Container Shell; 
    Shell.X.SetPoly(0,5); 
    Shell.X.SetPoly(1,10); 
    Shell.X.SetPoly(2,-1); 
    for(int n=0;n<10;n++) 
    { 
     Shell.time = (float)n; 
     cout << n << " " << Shell.X.Render() << endl; 
    } 
    system("pause"); 
    return 0; 
} 
+0

你的編譯器給你_what_錯誤? –

+0

爲什麼嵌套類? –

+0

看看這個:http://stackoverflow.com/questions/486099/can-inner-classes-access-private-variables –

回答

2

你得到一個錯誤的原因(我設法弄清楚,即使你沒有張貼實際的錯誤,請不要在未來),是你居然沒有一個實例Container類裏面的Vect類的功能。你或許應該思考的設計在這裏,但要迅速解決它(「髒」),你可以添加它設置一個Container例如在子類中的函數:

class Container 
{ 
    ... 

    class Vect 
    { 
     Container *container; 

    public: 
     void SetContainer(Container &container) 
      { this->container = &container; } 

     float Render(void) 
      { 
       float T = container->time - iT; 
       ... 
      } 

     ... 
    } X; 
}; 

int main() 
{ 
    Container Shell; 
    Shell.X.SetContainer(Shell); 
    Shell.X.SetPoly(0,5); 
    ... 
} 

編輯:更好的辦法是設置父對象的引用(感謝juanchopanza的想法)使用構造函數:

class Container 
{ 
    ... 

    Container() 
     : X(*this) 
     { ... } 

    class Vect 
    { 
     Container& container; 

    public: 
     Vect(Container& cont) 
      : container(cont) 
      { } 

     float Render(void) 
      { 
       float T = container.time - iT; 
       ... 
      } 

     ... 
    } X; 
}; 

我仍然認爲這是怎樣的一個骯髒的解決方案的(但不是髒我的第一個),而且你應該考慮改變設計。

+0

我試圖避免使用額外的數據訪問調用,但我想這是我不能避免,所以我會爲它寫一個訪問函數。謝謝您的幫助! –

+0

@JoeKessler可能更適合嵌套類來保存父對象的引用,並在其構造函數初始化列表中初始化它,因爲嵌套類沒有父類沒有意義。 – juanchopanza

+0

@JoeKessler增加了如何使用juanchopanza的想法。它更乾淨,更「髒」。 –

0

大部分基本上,類是對等的類。在OOP原則中,每個類都被封裝。那麼內部類如何直接訪問另一個類的成員。它違反了OOP的基本原則。

2

「...嵌套類的成員對封閉類的成員以及對封閉類授予友誼的類或函數沒有特殊訪問權限;應遵守通常的訪問規則(第11章) 。封閉類的成員對嵌套類的成員沒有特殊訪問權限;應遵守通常的訪問規則(第11章)......「

因此,讓他們成爲朋友。

1

內部類無法訪問外部類的非靜態變量。這是C++,我們必須在使用它的非靜態成員數據之前實例化對象。所以如果你想使用你的設計,你有兩種選擇:

  1. 改變變量(你的情況下的時間)爲靜態。但是,對於所有Container類,您只有一個時間副本。

  2. 讓嵌套類包含指向父類的指針。以下代碼與Joachim的解決方案類似,但我們不需要明確設置父項。

class Container { 

    public: 
     Container() : X(this) {} 
     float time; 

     class Vect { 
     public: 
     Vect(Container* parent) : parent_(parent) {} 
     void foo() { 
      myT = parent->time; 
     } 
     private: 
     Container * parent_; 
     } X; 
    };