Twitterのほうで盛んに発言しまくっているのですが、クラス図作っただけでちょっと満足気になってる私です。。
てへぺろ
シーン管理などでデザインパターンを使いましたが、ゲームのプレイヤーキャラクターのステータス管理でもステートパターンを使用しないといけません、っぽいね^^
それはいいのですが、、、
よく分からない事が出てきました😅
static キーワードの謎です。
このキーワード、C言語を学習している時からずっとあったのですが、どうやらC++では意味が少し違うらしくその挙動に悩まされております。
とりあえずコード書いちゃいましょう。
#include <iostream>
class IBase {
private:
static int value;
public:
virtual ~IBase() = default;
void Setter(int val) { value = val; }
int Getter(void) { return value; }
};
int IBase::value; // !important
class Bell : public IBase {
public:
Bell() {}
~Bell() {}
void Printf(void) { std::cout << Getter() << std::endl; }
};
class Muska : public IBase {
public:
Muska() {}
~Muska() {}
void Printf(void) { std::cout << Getter() << std::endl; }
};
int main()
{
Bell a;
Muska b;
a.Setter(100);
a.Printf();
b.Setter(200);
b.Printf();
a.Printf();
return 0;
}
IBase(一応インターフェース的な・・・)クラスの中に独立したメンバを定義し、このクラスをそれぞれBellクラスとMuskaクラス(クラスの名前に意味はありません)が継承しています。
main関数の中でスタック定義したクラスのSetterメソッド(IBaseクラス)を使って値を書き込み、コンソールに出力します。
aから100を入れてaを表示。これで100が表示され、bから200を入れてbを表示。200が表示されるはずですよね。
ここまではいいです。
問題はbの表示直後のa表示です。
以下出力結果をご覧ください。
なんだこりゃ??
100、200…200?
え?😓100だろ?最後。。。
と思いきや、staticで宣言された変数は共有されている変数らしく、Bellクラス、Muskaクラスどこを経由しても同じメモリアドレスに書き込むようです。
ちょっとメモリ番地を直接覗いてみましょうかしら
上記はa.Setterメソッド実行直後のダンプ値ですよ。
これを見ると確かに100が入ったね。
じゃ次。
b.Setterメソッドを通過するとちょっとわかりづらいですが、200が入ってます。
あらま。
なんという事。
というか、どういう事?🙄
そういう動きをする機能がstaticなのかと理解せざるを得ない結果ですが、実を言うとその理由がよく分かってないです。。。
とりあえず上記の動きをするみたいだから、クラス図のほうでクラス間で値を共有する手段としてインターフェースを設ける仕組みにしようとしました。
それが正攻法なのかどうかが分からないですが、なんか抽象クラス使っとけばそれでいいんじゃない?(ちょっと雑)
コメント