2012-04-09 26 views
2

私は実際にファイルをテストしており、main.cppからクラスの保護されたメンバーの一部にアクセスする必要がある状況があります。私は、友人としてmain()を追加しようとしましたが、うまく動かず、働かないと学んだので、main()のすべてをtest()に移動し、test()を友人にしました。それでもエラーが表示されます。ベース::値が保護されています:友人機能は同じファイル内にある必要がありますか?

例は

//--File.hpp 

namespace Files { 

class File { 
      public: 
       File(long word_):word(word_) {} 
      protected: 
       long word; 
      private: 
       friend int test(); 
}; 
}//ns:Files 


//--List_File.hpp 

namespace Files { 
class List_File :public File { 
     public: 
       List_File() : File(sizeof(int) + sizeof(long)) {} 
     private: 
       friend int test(); 
}; 
}//ns:Files 



//--main.cpp 

    using namespace Files; 

    int test() { 

     File *pd = new List_File(); 
     assert(pd->word == 12); //LINE 34 
     return 0; 
    } 

    int main() { 
     test(); 
     return 0; 
    } 

//それはライン34上の誤差は言うだろう。ご意見をお聞かせください。

g++ -O -Wall -Wno-unused -o a.out File.cpp List_File.cpp Data_File.cpp    
    Free_List_File.cpp main.cpp 
    File.hpp: In function ‘int test()’: 
    File.hpp:30:7: error: ‘long int Files::File::word’ is protected 
    main.cpp:34:16: error: within this context 
    make: *** [a.out] Error 1 
+0

(G ++ 4.2の下で)私にとっては罰金コンパイル掲示コード私は派生クラス宣言を変更した後に、(それは言うべき「クラス派生:公共の基本」を、しかし: "公共の基地"がありません) –

+0

ええええええええええええええんはそこにあります..私は再び確認します。 – howtechstuffworks

+0

@JeremyFriesner上記のコードスニペットは、g ++ 4.4.5でコンパイルしたときに同じエラーが発生するのは不思議です。それは名前空間に関係するものですか?おそらく、 'test'を名前空間' Files'に実装するべきです。サウンドリファレンスを見つけることができないので、コメントだけです。 –

答えて

1

いいえ、それは間違いなく、同じファイルである必要はありませんが、それは明らかにクラスがすなわち、何であるかを「知る」ことがあります。クラス定義を持っているヘッダファイルに含まれなければなりません機能が実装されています。あなたのコードは、コメントされているようにうまくいくはずです。あなたには、いくつかのコンテキストを追加した後

あなたtest機能はFiles名前空間ではありません。グローバルコンテキストにしたい場合は、名前空間内で "::test"として扱う必要があります。そうしないと、 "Files::test"があなたの場合のように "::test"ではなく友人機能になるとコンパイラは予想します。正式な標準参照を見つけることができませんが、私はそうだと確信しています。ここでは前方宣言を行っているので、名前解決のスコープの上位レベルへのデフォルトのフォールバックはありません。

+0

ええ、まあまあ私は思った。確かに、なぜそのエラーを示しています。すぐにここに戻って他のものがアクセスできないかどうか確認してください。 – howtechstuffworks

+0

@howtechstuffworksは実際にエラーを引用するのにうれしいでしょう:-) – littleadv

+0

名前空間は何にも影響しますか?だから、私は公共の変数にアクセスすることができます。そうでなければ、特定の保護されたものまたは何かの下でアクセス指定子について言及する必要がありますか? – howtechstuffworks

1

派生クラスの継承宣言がありませんか?

class Derived : public Base { 

私は(継承宣言が含まれて)あなたのコードをテストしたのだが、私はあなたがファイルのクラス定義の範囲の外で保護された変数にアクセスしようとしていることを推測するエラー

+0

いいえ、私はこのコードを手入力しました。私のコードが大きすぎるので......しかし、ここではエラーがなぜ起こっているのかわかりません... – howtechstuffworks

-1

を生じませんでした。私はそれが呼び出されたときに変数の単語を返す関数を推奨し、クラス定義の外で保護された変数にアクセスしようとする代わりにその変数を使用します。私は間違っているかもしれませんが、保護された変数のスコープは何か(クラス宣言だけに制限されているのか、クラス定義外でアクセスできるのか)は分かりませんが、私は正しいと確信しています。保護された変数はプライベート変数のようなものです。クラススコープ内でのみアクセスできます。私が間違っているなら、私を訂正してください。

編集:ああ申し訳ありませんが、私はあなたが何をしていたのか分かりませんでした。 littleadvが正しいです、あなたの関数宣言はファイルの名前空間の中にありません。

+1

ええ、保護されたプライベート変数はクラス内でしかアクセスできません友達の機能のポイントは何ですか?私はまだそれを使用している私はエラーが発生しています。そうねぇ。私はまさにあなたが言ったことをしましたが、同じシナリオをやり直してデバッグします。一度この課題を終えると、皆さんにアップデートされます – howtechstuffworks

0

littedevが正しい! は... littedevのコメントによると、コードを更新しました

//--File.hpp 
namespace Files { 
    class File { 
     public: 
      File(long word_):word(word_) {} 
     protected: 
      long word; 
     private: 
      friend int test(); 
    }; 
}//ns:Files  

//--List_File.hpp 

namespace Files { 
    class List_File :public File { 
     public: 
      List_File() : File(sizeof(int) + sizeof(long)) {}   \ 
     private: 
      friend int test(); 
    };  
}//ns:Files  

//--main.cpp  

namespace Files{  
    int test() {   
     File *pd = new List_File(); 
     assert(pd->word == 12); //LINE 34 
     return 0; 
    } 

    int main() { 
     Files::test(); 
     return 0; 
    } 
} 
関連する問題