• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:クラス型配列を同じクラス内関数の引数に使えますか?)

クラス型配列を同じクラス内関数の引数に使えますか?

このQ&Aのポイント
  • クラス型の配列を同じクラス内関数の引数に使用する方法について質問します。
  • 配列を関数内で参照できない場合、どのようにしてクラス内メンバの値を保持するかを知りたいです。
  • ゲーム作成中で、クラス型の配列を引数として渡して関数内でメンバの値を変更したいです。

質問者が選んだベストアンサー

  • ベストアンサー
  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.3

このところ VisualStudio は使っていないので的を外しているかもしれませんが.... void Block::BlockTime(int no,Block* BB[],DWORD g_B_Time) にしろ void Block::Block_Add_End(int no,Block* BB[]) にしろ, 配列 BB はこれらの関数の仮引数になっています. つまり, これらの関数内で「BB」と書けば, それは Block* BB[BLOCK_ADD_MAX]; と定義した BB ではなく仮引数としての BB です. ということで, 「BBの中の要素数が表示されていた」という「別のクラス内」で「BB」が仮引数として使われているか確認してください. そちらで仮引数になっていないのであれば, 「仮引数になっているかどうか」が影響するのかもしれません. あと, 「プログラム上 (プログラムなりに) ちゃんと参照できている」んだけど「デバッガでは参照できていない」という可能性もありますね. この質問をするということは「関数内でメンバの値を変えたいと思ってプログラムを書いているにもかかわらずメンバの値が変わっていない」ということだと思うのですが, デバッガ以外でも「メンバの値がおかしい」ことは確認できていますか?

Uriaria
質問者

お礼

回答ありがとうございます! なるほど、そのまま実態を扱っている訳ではなく仮引数になっていたのですね。 「BBの中の要素数が表示されていた」そのBBの中を確認した場所は仮引数ではなく、 要素数が表示されていないところは仮引数でした。これが原因の元かもしれません。 原因についてなるべく自分で調べてみようと思います。的確な回答をありがとうございました。 関数内でメンバの値を変えたいと言うのはここの関数内で変えていて、書き忘れていました; やりたいことは落下するブロックが地面に触れて一定時間経過すると種類が変わるといった 処理を実装したいです。 for(int no=0; no<BLOCK_ADD_MAX; no++){ B->B_ChTime(no,BB,1000);  //1秒経過したら変化 if(BB[no]->B_ch_TF == true){     /*---------------------------------------      ここでB_ch_TFがtrueになっていないらしく      変化の処理が行われないのです;     ----------------------------------------*/         //変化等処理 } } /*--------------------------------------- ブロックチェンジタイム関数 ブロックが地面に触れてから変化 するまでの時間を計測する。 戻り値 なし 引数 番号、ブロック配列、変化の時間 ---------------------------------------*/ void Block::B_ChTime(int no,Block* BB[],DWORD B_ch_T){ if(BB[no]->B_ch_F == true){ /*----------------------------  ここまではブレークポイントで  止められ、通っていることが  確認できました。 ----------------------------*/ if(BB[no]->InitTime_ch == true){ BB[no]->LastTime_ch = timeGetTime(); BB[no]->InitTime_ch = false; } BB[no]->nowtime_ch = timeGetTime() - BB[no]->LastTime_ch; /*-------------------------------------------  ここから先にブレークポイント  を設けたところすべて関数の終わりに  位置が変更されうまくいかなくなっています; -------------------------------------------*/ if(BB[no]->nowtime_ch > B_ch_T && BB[no]->B_ch_TF == false){ if( BB[no]->B_ch_F == true ){ BB[no]->B_ch_TF == true; BB[no]->B_ch_F == false; } } } }//ブレークポイントの位置(デバッグ停止で元に戻る) class TimeControl{    public:      InitTime_ch   //計測開始      LastTime_ch   //計測した時間      nowtime_ch    //経過した時間 } class Block : public TimeControl {    public:      void B_ChTime(int no,Block* BB[],DWORD B_Ch_T);      bool B_ch_T;         //ブロックが地面に触れたか。      bool B_ch_TF; //ブロックが変化する時間を超えたか。       } デバッガ以外で確認する方法が思いつかず、if分で目的の値に指定して 中を通ったら― と思っているのですがうまくいきません; 一応B_ch_Fが通っているのでメンバの値全体がおかしいわけではないと思うのですが そうすると仮引数から値を書き換えていて問題がないことに・・・。

Uriaria
質問者

補足

すみません、自己解決しました。すごく単純なミスでした! BB[no]->B_ch_TF == true 代入の場所が==になっていておかしなことに なっていました!お恥ずかしい・・・。

その他の回答 (2)

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.2

「クラス型の配列」などどこにもいません (ある型とその型へのポインタとは全く別物) が.... さておき, こんな一部分だけ見せられてもどうにもならないので, そのような現象を起こす完全なプログラムを出してください. ああ, 「配列でクラス内メンバの値を保持する」ってのも, どういう意味で使っているのかわからん.

Uriaria
質問者

お礼

すみません。大事な部分が抜けていました; void Block::Block_Add_End(int no,Block* BB[]){   /*ここでブレークポイント    BBの中身をウォッチ式で    確認してみると要素が消えています;*/ BB[no]->B_add_F = false; BB[no]->B_add_TF = true; } 別のクラス内から参照した時はしっかりとBBの中の 要素数が表示されていたのですが何か関係があるのでしょうか?

Uriaria
質問者

補足

すみません。プログラムを人に見せたことがなくて; プログラムがなかったらわからない、当たり前でした。 ツールはVisualStudioを使っています #define BLOCK_ADD_MAX (100) TimeControl* g_Time; Block* B; Block* BB[BLOCK_ADD_MAX]; DWORD g_B_Time[] = {1.3, 1.8, 2.6, 3.5, 4.9, 6.3, 7.7, 8.9, 9.3, 10.2...}; //100個入ってます。 void Action::GameMain(void) { if(InitFlag){ InitGame(); } BlockWait(); void Action::InitGame(void){     g_Time = new TimeControl(); B = new Block(); for(int i=0;i < BLOCK_ADD_MAX; i++) BB[i] = new Block(); InitFlag = false; } /*-------------------------------- ブロックウェイト関数 ブロックを時間で出現させる。 戻り値 なし 引数  なし ---------------------------------*/ void Action::BlockWait(void){ for(int no=0;no<BLOCK_ADD_MAX;no++){ B->BlockTime(no,BB,g_B_Time[no]);//時間が経ったらブロックを出現 if(BB[no]->B_add_F == true){ if(no == 10) BB[no]->B_add_Gra = 1; //ブロックの落下速度増加 if(no == 20) BB[no]->B_add_Gra = 2; if(no == 30) BB[no]->B_add_Gra = 3; if( no == 40) BB[no]->B_add_Gra = 4; B->Block_Gravity_Set(no,true,BB); B->Block_Add_End(no,BB);             ... //その他画像、位置、当たり判定等をセット } } } /*------------------------------------------------- ブロックタイム関数 ブロックが出現するまでの 時間を計測する。 戻り値 なし 引数 配列番号、ブロックの配列、ブロック出現時間 --------------------------------------------------*/ void Block::BlockTime(int no,Block* BB[],DWORD g_B_Time){ if(BB[no]->InitTime == 1){ BB[no]->LastTime = timeGetTime(); BB[no]->B_add_T = g_B_Time; BB[no]->InitTime = 0; }     BB[no]->nowtime = timeGetTime() - BB[no]->LastTime; if(BB[no]->nowtime > BB[no]->B_add_T * 1000 && BB[no]->B_add_TF == false){ /*ここでブレーク  配列BBの中身を見ると  要素数が表示されていません・・・*/ BB[no]->B_add_F = true; //ブロック出現 } } /*-------------------------- タイムクラス ---------------------------*/ class TimeControl{ public: TimeControl(); ~TimeControl(); bool InitTime; DWORD LastTime; DWORD nowtime;       ... private: }; /*-------------------------   ブロッククラス --------------------------*/ class Block : public TimeControl { public: Block(); ~Block(); bool B_add_F; //ブロックが追加されたか。 bool B_add_TF; //ブロックが追加される時間が経過したか。 bool B_gra_F; //ブロックに重力がかかっているか。 int B_add_Gra;     //ブロックの重力を加速させるか。 void B_ChTime(int no,Block* BB[],DWORD B_ch_T); void BlockTime(int no,Block* BB[],DWORD g_B_Time); private: }; 「配列でクラス内メンバの値を保持する」と言うのは1個の配列で 時間などのメンバの値を持てたら便利かなと思って書きました。 紛らわしいことを書いてしまってすみません; 今やりたい処理があったのですがうまくいかず、 ブレークポイントを置いて調べようとしてみたところ勝手に場所が変わってしまいます。 その現象が起こる共通の部分がクラス内でクラス型配列を使っている部分でしたので もしかしたらと思って質問しました。

回答No.1

このソースだけだと、BもBBもポインタ変数が定義されているだけで、クラスのインスタンスがありません。 int* p; *p=1; がコンパイルエラーにはならないけど正しく動作しないのと同様です。 あと、グローバル変数を使うなら、同じ変数名を関数の引数に使用するのはやめた方がいいですよ。

Uriaria
質問者

お礼

すみません。インスタンスの生成を書き忘れていました; アドバイスありがとうございます!できるだけ引数では別の変数名を使うようにしようと思います。

関連するQ&A