/***************************************************************/
/* bowling.c　22:57 2006/11/27
/*
/* ボーリングのスコア計算を行う。
/*
/* ●現在の問題点
/* エラー処理がおざなり(アルファベットの入力でおかしくなる)
/* ガーターやストライクなどがひと目で分からない
/* 複数人のプレイに対応していない
/* 関数を使えていない
/***************************************************************/

#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>

/*-------------------------------------------------------------*/
/* プロトタイプ宣言 */
/*-------------------------------------------------------------*/
void input_error(void);
void pin_error(void);
int input_point(int frame);
int check_input(int *input);
int point_add(int *user_scoa, int frame, int flag);
void print_scoa(int *user_scoa, int *frame_scoa, int frame);


/*=============================================================*/
/* メイン関数始まり */
/*=============================================================*/
int main (void){


/*-------------------------------------------------------------*/
/* 変数の宣言 */
/*-------------------------------------------------------------*/
	int user_scoa[21] = {0};
	int frame_scoa[10] = {0};
	int frame, point, pin, input;
	int strike = 0;	int spear = 0; int w = 0;
	int count = 0;


//フレームが10を超えるまでループ
for(frame=0; frame<10; frame++){

	//ユーザの投球（１回目）
	pin = 10;
	input = input_point(frame);//倒した本数の入力
	pin -= input;
	point = input;
	if(pin < 0){//ピンを倒しすぎてる時エラー
		pin_error();
	}
	if(strike == 1){//ストライクの次の投球だったなら
		frame_scoa[frame-1] += point;
	}
	if(w == 1){//ダブルの次の投球だったなら
		frame_scoa[frame-2] += point;
		w = 0;//ダブルフラグの初期化
	}
	if(spear == 1){//スペアの次の投球だったなら
		frame_scoa[frame-1] += point;
		spear = 0;//スペアフラグの初期化
	}
	if(pin == 0){//もしストライクになったら
		if(strike == 1){//ストライクの次がストライクなら
			w = 1;//ダブルフラグを立てる
		}
		else{
			strike = 1; //ストライクフラグの設定
		}
		user_scoa[count] = point;
		count++;
		if(frame == 9){//10フレームでストライクが出たなら
			//ユーザの投球
			pin = 10;
			input = input_point(frame);
			pin -= input;
			point = input;
			if(pin < 0){//ピンを倒しすぎてる時エラー
				pin_error();
			}
			user_scoa[count] = point;
			
			frame_scoa[frame] += point;
			count++;
			//ポイントの加算
			frame_scoa[frame] = point_add(&user_scoa[0], frame, 0);
			if(pin != 0){
				input = input_point(frame);//倒した本数の入力
				pin -= input;
				point = input;
				if(pin < 0){//ピンを倒しすぎてる時エラー
					pin_error();
				}
				user_scoa[count] = point;
				if(w == 1){//ダブルだった時
					frame_scoa[frame-1] += user_scoa[count];
				}
				frame_scoa[frame] += point;
				//ポイントの加算
				frame_scoa[frame] = point_add(&user_scoa[0], frame, 1);
				//ポイントの表示
				print_scoa(&user_scoa[0], &frame_scoa[0], frame);
				return 0;
			}
			if(pin == 0){//10フレームの2投目ストライクが出たなら
				//ユーザの投球
				pin = 10;
				input = input_point(frame);//倒した本数の入力
				pin -= input;
				point = input;
				if(pin < 0){//ピンを倒しすぎてる時エラー
					pin_error();
				}
				user_scoa[count] = point;
				if(w == 1){//ダブルだった時
					frame_scoa[frame-1] += user_scoa[count];
				}
				frame_scoa[frame] += point;
				//ポイントの加算
				frame_scoa[frame] = point_add(&user_scoa[0], frame, 1);
				//ポイントの表示
				print_scoa(&user_scoa[0], &frame_scoa[0], frame);
				return 0;
			}
		}
		goto skip;//第2投目をスキップ
	}
	user_scoa[count] = point;	//スコア加算
	count++;

	//ユーザの投球（２回目）
	input = input_point(frame);//倒した本数の入力
	pin -= input;
	point = input;
	if(pin < 0){//ピンを倒しすぎてる時エラー
		pin_error();
	}
	if(strike == 1){//ストライクの次の投球だったなら
		frame_scoa[frame-1] += point;
		strike = 0;//ストライクフラグの初期化
	}
	if(pin == 0){//もしスペアになったら
		spear = 1; //フラグの設定
		if(frame == 9){//10フレーム目でスペアになったら
			//ポイントの加算
			user_scoa[count] = point;
			frame_scoa[frame] += point;
			count++;
			
			//ユーザの投球（３回目）ここに到達するのは10フレーム目でスペアをとった時
			pin = 10;
			input = input_point(frame);//倒した本数の入力
			pin -= input;
			point = input;
			if(pin < 0){//ピンを倒しすぎてる時エラー
				pin_error();
			}
			user_scoa[count] = point;
			frame_scoa[frame] += point;
			//ポイントの加算
			frame_scoa[frame] = point_add(&user_scoa[0], frame, 1);
			//ポイントの表示
			print_scoa(&user_scoa[0], &frame_scoa[0], frame);
			return 0;
		}
	}
	user_scoa[count] = point;

skip:
	count++;

	//ポイントの加算
	frame_scoa[frame] = point_add(&user_scoa[0], frame, 0);

	//ポイントの表示
	print_scoa(&user_scoa[0], &frame_scoa[0], frame);

}//10フレームのループ終わり

return 0;
}//メインの終わり


/***************************************************************/
/* input_error
/* 入力値が不正な場合にメッセージを表示する
/*
/* 引数：なし
/* 戻り値：なし
/***************************************************************/
void input_error(void){

		printf("不正な入力です 入力範囲は0〜10です\n");
}


/***************************************************************/
/* pin_error
/* 倒したピンの数が不正な場合にプログラムを終了させる
/***************************************************************/
void pin_error(void){
	printf("そんなにたくさんピンは存在しません\n");
	exit(0);
}


/***************************************************************/
/* input_point
/* 倒したピンの本数を入力させる
/*
/* 引数：現在のフレーム
/* 戻り値：入力された値
/***************************************************************/
int input_point(int frame){

	int input;
	int chk;

do{
	printf("%dフレーム：何本倒しましたか？ >", frame+1);
	scanf("%d", &input);
	chk = check_input(&input);
	
	if(chk == 1){
		input_error();
	}
}while(chk != 0);

	return input;
}


/***************************************************************/
/* check_input
/* 入力が妥当なものかチェックする
/*
/* 引数：チェックしたい入力のアドレス
/* 戻り値：正常時は0を、範囲外は1を返す
/***************************************************************/
int check_input(int *input){

	if(10 < *input || *input < 0){
		return 1;	
	}
	else{
		return 0;
	}
}


/***************************************************************/
/* point_add
/* ポイントの加算を行う
/* 引数：user_scoaのポインタ, 現在のフレーム, フラグ
/* 戻り値：加算された得点
/*
/* フラグが0の時は10フレーム目以外の処理
/* フラグが1の時は10フレーム目の処理
/***************************************************************/
int point_add(int *user_scoa, int frame, int flag){

	int sum;

	if(flag == 0){
		sum = *(user_scoa + frame * 2) + *(user_scoa + frame * 2 + 1);
	}
	else{
		sum = *(user_scoa + frame * 2) + *(user_scoa + frame * 2 + 1) + *(user_scoa + frame * 2 + 2);
	}

	return sum;
}


/***************************************************************/
/* print_scoa
/* 投球ごとのスコアとフレームスコアを表示する
/*
/* 引数：user_scoaのポインタ, frame_scoaのポインタ, 現在のフレーム
/* 戻り値：なし
/***************************************************************/
void print_scoa(int *user_scoa, int *frame_scoa, int frame){
	
	int	i = 0;
	int sum_scoa[10] = {0};
	int x;

	//フレームスコアとして表示する配列を作成	
	while(i <= frame){//現在のフレームまでのスコアを総和
		if(i==0)x=0;else x=1;//ゼロチェック
		//sum_scoa配列に前のスコア+今回のスコアを格納
		sum_scoa[i] = x*(sum_scoa[i-1]) + *(frame_scoa + i);
		i++;
	}
	i = 0;
	
	while(i < 21){
		printf("%2d,", *(user_scoa + i));
		i++;
	}
	i = 0; printf("\n");
	
	while(i < 10){
		printf("%5d,", sum_scoa[i]) ;
		i++;
	}
	printf("\n");
}


