ページ 11

どこがダメなのかわかりませんT_T

Posted: 2011年3月14日(月) 16:38
by mizugori
ゲームプログラマになるために覚えておきたい技術という本の最初のゲームを自分なりに書いてみたんですが
実行しようとすると動作が停止してしまいます。
もしよかったらどこがいけないのか教えてくださいT_T
あと初心者なんでできるだけわかりやすくおねがいしますm(__)m
わがままいってすいません
#include<iostream>




using namespace std;

const char DATA[]="\
########\n\
# .. p #\n\
# oo #\n\
# #\n\
########";

const int TAKASA=5;
const int HABA=8;



enum Objact{
O_kabe,
O_kuukan,
O_gole,
O_hito,
O_ghito,
O_nimotu,
O_gnimotu,

O_siran,
};

int x=0;

int y=0;



void syokika(Objact* stage,int haba,int takasa,const char* data);
void draw(const Objact* stage,int haba,int takasa);
bool check(const Objact* stage,int haba,int takasa);
void up( Objact* stage,int haba,int takasa,char imput);


void syokika(Objact* stage,int haba,int takasa,const char* data)
{

const char* d = data;



Objact t;










while(*d!='\0')
{
switch(*d)
{
case '#':t=O_kabe;break;
case ' ':t=O_kuukan;break;
case '.':t=O_gole;break;
case 'p':t=O_hito;break;
case 'P':t=O_ghito;break;
case 'o':t=O_nimotu;break;
case 'O':t=O_gnimotu;break;
case '\n':t=O_siran;
x=0;++y;break;

default:t=O_siran;
break;};

++d;

if(t!=O_siran){
stage[y*haba+x]=t;
++x;}

};

};

void draw(const Objact* stage,int haba,int takasa)
{
const char Font[]={'#',' ','.','p','P','o','O'};

Objact o;

for(y=0;y<=takasa;y++)
{
for(x=0;x<=haba;x++)
{
o=stage[y*haba+x];
cout<<Font[o];
}
cout<<endl;
}

}


bool check(const Objact* stage,int haba,int takasa)
{

int t;
for(t=0;t<=haba*takasa;t++)
{


if(stage[t]==O_nimotu)
{return false;}


}

return true;
}


void up( Objact* stage,int haba,int takasa,char imput)
{
int x;
int y;
int g=0;
int tx=0;
int ty=0;
int xx=0;
int yy=0;

int i;
Objact o;

for(i=0;i<=haba*takasa;i++)
{
o=stage;

if(o==O_hito||o==O_ghito)
break;
};

x=i%haba;
y=i/haba;



switch(imput)
{
case 'u':g=-1;break;
case 's':g=+1;break;
case 'm':g=+1;break;
case 'h':g=-1;break;
default :break;
}


tx=g+x;
ty=g+y;

if(tx<=0||ty<=0||haba<=tx||takasa<=ty)
{tx=x;ty=y;};

int p=ty*haba+tx;


if(stage[p]==O_gole||stage[p]==O_kuukan)
{
if(stage[p]==O_gole)
{stage[p]=O_ghito;}
else{stage[p]=O_hito;}

}

xx=2*g+x;
yy=2*g+y;


if(stage[p]==O_nimotu)
{
if(xx<=0||yy<=0||haba<=xx||takasa<=yy)
{ xx=tx;
yy=ty;
tx=x;ty=y;}

if(stage[yy*haba+xx]==O_kuukan)
{
stage[yy*haba+xx]=O_nimotu;
stage[ty*haba+tx]=O_hito;
}else if(stage[yy*haba+xx]==O_gole)
{
stage[yy*haba+xx]=O_gnimotu;
stage[ty*haba+tx]=O_hito;
}else
{xx=tx;
yy=ty;
tx=x;ty=y;stage[yy*haba+xx]=O_nimotu;
stage[ty*haba+tx]=O_hito;
}


}



if(stage[p]==O_gnimotu)
{
if(xx<=0||yy<=0||haba<=xx||takasa<=yy)
{ xx=tx;
yy=ty;
tx=x;ty=y;}

if(stage[yy*haba+xx]==O_kuukan)
{
stage[yy*haba+xx]=O_nimotu;
stage[ty*haba+tx]=O_ghito;
}else if(stage[yy*haba+xx]==O_gole)
{
stage[yy*haba+xx]=O_gnimotu;
stage[ty*haba+tx]=O_ghito;
}else
{xx=tx;
yy=ty;
tx=x;ty=y;stage[yy*haba+xx]=O_gnimotu;
stage[ty*haba+tx]=O_hito;
}


}

}

int main()
{
char imput;
Objact* stage=new Objact[HABA*TAKASA];
syokika(stage,HABA,TAKASA,DATA);


while(true)
{
draw(stage,HABA,TAKASA);

if(check(stage,HABA,TAKASA))break;


cout<<"右 m,;左 h;上 u;下 s";
cin>>imput;



up(stage,HABA,TAKASA,imput);

}


cout<<"オメデトウ!!"<<endl;


delete []stage;

stage=0;
while( true ){
;
}
return 0;

}

Re: どこがダメなのかわかりませんT_T

Posted: 2011年3月14日(月) 17:19
by h2so5
これだけが原因では無いと思いますが、例えばここなどは明らかに配列の範囲外へのアクセスをしています。

コード:

for(i=0;i<=haba*takasa;i++)
{
o=stage[i];
TAKASA=5
HABA=8

の場合、配列 stage の要素数は5*8=40 で添え字に取れる数値は 0~39 です。
i<=haba*takasa という条件の指定だと i は 0~40 の数値を取ります。

あと、開発環境と、これがどういうルールのゲームなのかを教えてください。

Re: どこがダメなのかわかりませんT_T

Posted: 2011年3月14日(月) 17:25
by tk-xleader
プログラムコードを貼り付ける際は、フォーラムのルールに則って、codeタグ(とでもいえばよいのでしょうか…)で囲ってください。
ところで、とりあえず整形して表面的に追ってみました。そして、文法的に引っかかりそうなところには修正してコメントをつけてあります。
それと、いくつか気になったところにもコメントを記してあります。

コード:

#include<iostream>

using namespace std;

const char DATA[]="\
########\n\
# .. p #\n\
# oo #\n\
# #\n\
########";


const int TAKASA=5;
const int HABA=8;


/*
Objact は Object のタイプミスでしょうか?
*/
enum Objact{
	O_kabe,
	O_kuukan,
	O_gole,
	O_hito,
	O_ghito,
	O_nimotu,
	O_gnimotu,

	O_siran,
};

int x=0;

int y=0;



void syokika(Objact* stage,int haba,int takasa,const char* data);
void draw(const Objact* stage,int haba,int takasa);
bool check(const Objact* stage,int haba,int takasa);
void up( Objact* stage,int haba,int takasa,char imput);


void syokika(Objact* stage,int haba,int takasa,const char* data)
{

	const char* d = data;



	Objact t;










	while(*d!='\0')
	{
		switch(*d)
		{
			case '#':t=O_kabe;break;
			case ' ':t=O_kuukan;break;
			case '.':t=O_gole;break;
			case 'p':t=O_hito;break;
			case 'P':t=O_ghito;break;
			case 'o':t=O_nimotu;break;
			case 'O':t=O_gnimotu;break;
			case '\n':t=O_siran;
			x=0;++y;break;

			default:t=O_siran;
			break;
		}; // ;はいらないです。(有っても特に問題は有りませんが…)

		++d;

		if(t!=O_siran){
			stage[y*haba+x]=t;
			++x;
		}

	}; // ;はいらないです。(有っても特に問題は有りませんが…)

} //← ;はいらないです。(コンパイルエラー)

void draw(const Objact* stage,int haba,int takasa)
{
	const char Font[]={'#',' ','.','p','P','o','O'};

	Objact o;

	for(y=0;y<=takasa;y++)
	{
		for(x=0;x<=haba;x++)
		{
			o=stage[y*haba+x];
			cout<<Font[o];
		}
	cout<<endl;
	}

}


bool check(const Objact* stage,int haba,int takasa)
{

	int t;
	for(t=0;t<=haba*takasa;t++)
	{


		if(stage[t]==O_nimotu){return false;}


	}

	return true;
}


void up( Objact* stage,int haba,int takasa,char imput)
{
	int x;
	int y;
	int g=0;
	int tx=0;
	int ty=0;
	int xx=0;
	int yy=0;

	int i;
	Objact o;

	for(i=0;i<=haba*takasa;i++)
	{
		o=stage[i];

		if(o==O_hito||o==O_ghito)
			break;
	}; //ここも ; はいらないですよ(有っても特に問題はないが…)

	x=i%haba;
	y=i/haba;
	



	switch(imput)
	{
		case 'u':g=-1;break;
		case 's':g=+1;break;
		case 'm':g=+1;break;
		case 'h':g=-1;break;
		default :break;
	}


	tx=g+x;
	ty=g+y;

	if(tx<=0||ty<=0||haba<=tx||takasa<=ty){tx=x;ty=y;};

	int p=ty*haba+tx;


	if(stage[p]==O_gole||stage[p]==O_kuukan)
	{
		if(stage[p]==O_gole){stage[p]=O_ghito;}
		else{stage[p]=O_hito;}

	}

	xx=2*g+x;
	yy=2*g+y;


	if(stage[p]==O_nimotu)
	{
		if(xx<=0||yy<=0||haba<=xx||takasa<=yy)
		{ 
			xx=tx;
			yy=ty;
			tx=x;ty=y;
		}

		if(stage[yy*haba+xx]==O_kuukan)
		{
			stage[yy*haba+xx]=O_nimotu;
			stage[ty*haba+tx]=O_hito;
		}else if(stage[yy*haba+xx]==O_gole){
			stage[yy*haba+xx]=O_gnimotu;
			stage[ty*haba+tx]=O_hito;
		}else{
			xx=tx;
			yy=ty;
			tx=x;ty=y;stage[yy*haba+xx]=O_nimotu;
			stage[ty*haba+tx]=O_hito;
		}


	}



	if(stage[p]==O_gnimotu)
	{
		if(xx<=0||yy<=0||haba<=xx||takasa<=yy)
		{ 
			xx=tx;
			yy=ty;
			tx=x;ty=y;
		}

		if(stage[yy*haba+xx]==O_kuukan)
		{
			stage[yy*haba+xx]=O_nimotu;
			stage[ty*haba+tx]=O_ghito;
		}else if(stage[yy*haba+xx]==O_gole){
			stage[yy*haba+xx]=O_gnimotu;
			stage[ty*haba+tx]=O_ghito;
		}else{
			xx=tx;
			yy=ty;
			tx=x;ty=y;stage[yy*haba+xx]=O_gnimotu;
			stage[ty*haba+tx]=O_hito;
		}


	}

}

int main()
{
	char imput;
	Objact* stage=new Objact[HABA*TAKASA];
	syokika(stage,HABA,TAKASA,DATA);


	while(true)
	{
		draw(stage,HABA,TAKASA);

		if(check(stage,HABA,TAKASA))break;


		cout<<"右 m,;左 h;上 u;下 s";
		cin>>imput;



		up(stage,HABA,TAKASA,imput);

	}


	cout<<"オメデトウ!!"<<endl;


	delete []stage;

	stage=0;
	
	/*
		ここが無限ループとなっています。
	*/
	while( true ){
		;
	}
	return 0;

}
ちなみに、コンパイルしかしていません(gccにて、gcc -osample sample.cpp でチェック。)

Re: どこがダメなのかわかりませんT_T

Posted: 2011年3月16日(水) 12:33
by mizugori
質問に答えてくれた方ありがとうございます!!
おかげさまでなんとか作動するようになりましたm(__)m

ちなみにこれは荷物を動かして目的地に運ぶというものです

質問に答えてくださった方々の返信でいろいろなことを学ぶことができました!!
本当にありがとうございます!!