C++勉強中のメモ。あとqiitaに記事を上げる練習
結論
クラスにクラスを包含するときに、包含したクラスのコンストラクタに引数を渡したい場合は、初期化の際にコンストラクタを呼ぶ。
クラスのメンバ変数にクラスを持たせる
クラスのメンバ変数としてクラスを持たせた場合、なにもしなくてもデフォルトコンストラクタが呼ばれる。
test1.cpp
#include <iostream>
class Test1{
public:
Test1();
};
class Test{
public:
Test();
private:
Test1 test1;
};
Test1::Test1(){
std::cout << "Constructor:Test1" << std::endl;
}
Test::Test(){
std::cout << "Constructor:Test" << std::endl;
}
int main(){
Test test;
return 0;
}
実行結果
Constructor:Test1
Constructor:Test
また、コンストラクタは包含したクラスから呼ばれていることもわかる。
引数を持つクラスを包含する
先程のTest1クラスのコンストラクタに引数を設定してみる。
とりあえずなにも考えずこう書くとコンパイルはエラーを吐かなくなった。
test2.cpp
#include <iostream>
class Test1{
public:
Test1(int a);
};
class Test{
public:
Test();
private:
Test1 test1(int a);
};
Test1::Test1(){
std::cout << "Constructor:Test1" << std::endl;
}
Test::Test(){
std::cout << "Constructor:Test" << std::endl;
}
int main(){
Test test;
return 0;
}
が、実行してみるとこうなる。Test1のコンストラクタが呼ばれていない。
実行結果
Constructor:Test
冷静に考えると引数に渡しているaには実体がないので、これでTest1のコンストラクタが呼ばれても困る。
(コンパイラに怒って欲しかった。)
追記
コンパイルが通るのも当然で、ここで宣言しているのはコンストラクタではなくただのメンバ関数だった。
ちなみにこのように書くと、Test1クラスにはデフォルトコンストラクタがないぞとIDEも怒ってくれるしコンパイルは通らない。
test2.cpp
#include <iostream>
class Test1{
public:
Test1(int a);
};
class Test{
public:
Test();
private:
Test1 test1;
};
Test1::Test1(){
std::cout << "Constructor:Test1" << std::endl;
}
Test::Test(){
std::cout << "Constructor:Test" << std::endl;
}
int main(){
Test test;
return 0;
}
コンストラクタでクラスを初期化する
メンバとしてクラスなどのオブジェクトを持たせた場合でも、普通の変数と同様にコンストラクタで初期化ができる。
test3.cpp
#include <iostream>
class Test1{
public:
Test1(int a);
};
class Test{
public:
Test();
private:
Test1 test1;
};
Test1::Test1(int a){
std::cout << "Constructor:Test1" << " argument:" << a << std::endl;
}
Test::Test():
test1(1)//初期化でコンストラクタを呼ぶ
{
std::cout << "Constructor:Test" << std::endl;
}
int main(){
Test test;
return 0;
}
実行結果
Constructor:Test1 argument:1
Constructor:Test
コンストラクタが呼ばれた。引数を渡すこともできている。