さぁ、今回からC++で最も大事な機能、「クラス」についての話になります。先ずは、小難しいことは抜きにしてクラスを使ってみましょう。
では、今回の要点です。
では、いってみましょう。
さて、クラスは第1部第58章でやった構造体によく似ています。ただ、struct ではなく class というのを使います。
さて、クラスは本当に構造体とよく似ています。ということで、先ずは構造体と同じように使ってみましょう。手っ取り早いので、第1部第59章のプログラムの struct を class に変えてみることにします。
プログラム |
---|
// Class1.cpp #include <iostream.h> #define ELEM(array) (sizeof (array) / sizeof *(array)) class SStudent { char szName[16]; int nJapanese; int nMath; int nEnglish; }; void Disp(const SStudent& student) { cout << "名前 : " << student.szName << endl << " 国語 : " << student.nJapanese << " 点, " "数学 : " << student.nMath << " 点, " "英語 : " << student.nEnglish << " 点" << endl; } int main() { SStudent students[] = { { "赤井孝", 73, 98, 86, }, { "笠井大介", 64, 45, 40, }, { "吉田叶", 76, 78, 69, }, }; int i; for(i = 0; i < ELEM(students); i++) Disp(students[i]); return 0; } |
コンパイルエラー(ちょっと改変) |
Class1.cpp(16) : error C2248: 'szName' : private メンバにアクセスできません。 Class1.cpp(17) : 'nJapanese' : private メンバにアクセスできません。 Class1.cpp(18) : 'nMath' : private メンバにアクセスできません。 Class1.cpp(19) : 'nEnglish' : private メンバにアクセスできません。 Class1.cpp(25) : 'initializing' : 'char [7]' から 'class SStudent' に変換することはできません。 Class1.cpp(25) : 'initializing' : 'const int' から 'class SStudent' に変換することはできません。 Class1.cpp(25) : 'initializing' : 'const int' から 'class SStudent' に変換することはできません。 Class1.cpp(25) : 'initializing' : 'const int' から 'class SStudent' に変換することはできません。 Class1.cpp(25) : 直前のエラーを修復できません; コンパイルを中止します。 |
うわぁ、沢山エラーが出てきました。構造体と似ているなんてウソじゃないか!
と、クラスと構造体は確かに似ていますが、やっぱり構造体とはちょっと違うところがあるのです。メンバにアクセスするためには public: というものを書かなければならないのです。どこに書くかというと、メンバの宣言の前です。
class SStudent { public: char szName[16]; int nJapanese; int nMath; int nEnglish; };
これで無事コンパイルできるようになります。実行結果も同じになります。
このように、public:(公開された)というものを書いて初めて、メンバにアクセスできるようになるのです。
さて、クラスには構造体で話した以上の事ができます。何と、関数もメンバにできるのです。実は構造体でもできるのですが、それはC++だけの話です。C言語ではできません。
関数もメンバにできる、というのはいまいちピンとこないかも知れません。ということで、実際のプログラムを見てみましょう。
プログラム |
---|
// Class1b.cpp #include <iostream.h> #define ELEM(array) (sizeof (array) / sizeof *(array)) class SStudent { public: char szName[16]; int nJapanese; int nMath; int nEnglish; void Disp(); }; void SStudent::Disp() { cout << "名前 : " << szName << endl << " 国語 : " << nJapanese << " 点, " "数学 : " << nMath << " 点, " "英語 : " << nEnglish << " 点" << endl; } int main() { SStudent students[] = { { "赤井孝", 73, 98, 86, }, { "笠井大介", 64, 45, 40, }, { "吉田叶", 76, 78, 69, }, }; int i; for(i = 0; i < ELEM(students); i++) students[i].Disp(); return 0; } |
実行結果 |
名前 : 赤井孝 国語 : 73 点, 数学 : 98 点, 英語 : 86 点 名前 : 笠井大介 国語 : 64 点, 数学 : 45 点, 英語 : 40 点 名前 : 吉田叶 国語 : 76 点, 数学 : 78 点, 英語 : 69 点 |
赤い部分が上と違う部分です。先ず、クラスの宣言の中です。
void Disp();
こんなのが入ってますね。どうやら、プロトタイプ宣言のようです。そして、次はその実体の定義らしき部分があります。
void SStudent::Disp() { cout << "名前 : " << szName << endl << " 国語 : " << nJapanese << " 点, " "数学 : " << nMath << " 点, " "英語 : " << nEnglish << " 点" << endl; }
何やら関数名の前に SStudent:: というのがありますね。:: というのは第1部第68章でやったスコープ解決演算子みたいですね。
で、szName というメンバが、オブジェクトなしに使われています。なのにコンパイルエラーは出ず、きちんとプログラムは動いています。
さて、関数を使っているところではどうでしょうか?
students[i].Disp();
関数 Disp は SStudent のメンバなので、メンバ変数の時と同じように . を使ってメンバを使用しています。文法的にはあまり問題ないですが、この関数を呼ぶとどうなるんでしょうかね?
これらについては、次回にお話しします。どうなっているのか、次回を読む前にちょっと考えてみて下さいね。
今回は、これで終わりです。「あれ? ちょっと早いんでないの?」と思うかもしれませんが、ちょっとここでクラスの文法的な意味を推理してほしいのです。まぁ、推理しなくても次回を見ることはできますが、ちょっと推理してから見てほしいですね。
では、今回の要点です。
それでは、次回まで。
Last update was done on 2000.8.2
この講座の著作権はロベールが保有しています