/*****************************************************************************/ /* */ /* ジョブ名称 : n進計算機(オリジナルプログラム) */ /* */ /* 機能概要 : n進数の四則計算をする(モジュール分割) */ /* */ /* : */ /* */ /* 作成者 : 恒川 昭一(カーネルキャリアスクール) */ /* */ /* バージョン番号 01.20 日付 2005/06 備考 コメント削除版 */ /* */ /*****************************************************************************/ #include int adicinp(int *ntype); int numinp(int *num, int ntype); int opeinp(void); int add(int *ans, int num1, int num2); int sub(int *ans, int num1, int num2); int mul(int *ans, int num1, int num2); int div(int *ans, int num1, int num2); /* ----- 滅入ん ----- */ void main() { int ntype; int num1; int op; int num2; int ans; int (*opeptr[])(int *ans, int num1, int num2) = { add, sub, mul, div }; /* 関数ポインタの定義!(>_<)w */ printf("何進数で計算しますか? (2 進数〜 16 進数):"); /* 進数値の入力 */ if (adicinp(&ntype) == -1) { printf("進数値の入力が不正です!\n"); return; } printf("1番目の数値:"); /* 計算すべき値その1を入力 */ if (numinp(&num1, ntype) == -1) { printf("数値を入力して下さい!\n"); return; } printf("演算子は? (+, -, *, /):"); /* 四則演算子を入力 */ if ((op = opeinp()) == -1) { printf("演算子の入力が不正です!\n"); return; } printf("2番目の数値:"); /* 計算すべき値その2を入力 */ if (numinp(&num2, ntype) == -1) { printf("数値を入力して下さい!\n"); return; } if ((*opeptr[op])(&ans, num1, num2) == -1) { /* 関数ポインタで演算するる */ printf("たぶん 0 除算エラー!\n"); /* op の値にて関数配列を切り替える */ return; } printf("演算結果 (10 進数): %d\n", ans); /* 結果を表示でおつかれさま */ } /* ----- 関数定義 ----- */ /* キーボード入力を待ち結果をポインタ *ntype に格納する */ /* 返り値: -1 でエラー, 正常終了時は真数の値が返る */ int adicinp(int *ntype) { int ch; *ntype = 0; /* 初期化しておく */ while ((ch = getchar()) != '\n') { /* 改行が表れるまでキーボード入力を受け付ける */ if (ch >= '0' && ch <= '9') { /* 数字の範囲内? */ *ntype = *ntype * 10 + ch - '0'; /* 数字を表す文字を数値に変換 */ } else { return -1; /* 数字以外ならエラー */ } } if (*ntype < 2 || *ntype > 16) { /* 進数の範囲内? */ return -1; /* 範囲外ならエラー */ } return 1; /* 正常終了 */ } /* キーボード入力を待ち結果をポインタ *num に格納する */ /* 引 数:int *num (変換結果の値が入る), int ntype 進数 */ /* 返り値: -1 でエラー, それ以外は正常終了 */ int numinp(int *num, int ntype) { int ch; int sign = 1; *num = 0; /* 初期化しておく */ if ((ch = getchar()) == '\n') { /* 最初の 1 文字を読み込む */ return -1; /* 改行 (空入力) ならエラー */ } if (ch == '-') { /* 行頭が '-' か? */ sign = -1; /* それなら後でマイナス化しなきゃ */ ch = getchar(); /* 1 文字読み飛ばす */ } while (ch != '\n') { /* 改行が現れるまで繰り返し */ if (ntype <= 10) { /* 進数タイプが数字で表せれる? */ if (ch >= '0' && ch <= '9' - (10 - ntype)) { /* 進数範囲内の入力? */ *num = *num * ntype + ch - '0'; /* n 進数文字 → 10 進数数値変換 */ } else { return -1; /* 進数範囲外でエラー */ } } else { /* 進数表現にアルファベットが入りそうな処理はこちら */ if (ch >= '0' && ch <= '9') { /* 数字だけ */ *num = *num * ntype + ch - '0'; /* n 進数文字 → 10 進数数値変換 */ } else { if (ch >= 'a' && ch <= 'f' - (16 - ntype)) { /* 進数範囲内のアルファベット? */ *num = *num * ntype + ch - 'a' + 10; /* アルファベット版 n 進数文字 → 10 進数数値変換 */ } else { return -1; /* 進数範囲外でエラー */ } } } ch = getchar(); /* 1 文字取り込んで繰り返し */ } /* 正常に変換できたみたい */ *num *= sign; /* 符号を処理してみる */ return 1; /* 正常終了w */ } /* キーボード入力を待ち結果を文字コードで返す */ /* 返り値: -1 でエラー, + - * / はその文字コード */ int opeinp(void) { int op; op = getchar(); /* キーボードから 1 文字読み込み */ if (op != '+' && op != '-' && op != '*' && op !='/') { /* 四則演算子以外の入力? */ return -1; /* それならエラーだよ〜♪ */ } if (getchar() != '\n') { /* 改行以外の文字が入力されている? */ return -1; /* それもエラーだよ (-_-;) */ } switch (op) { case '+': return 0; /* 足し算 */ case '-': return 1; /* 引き算 */ case '*': return 2; /* 掛け算 */ case '/': return 3; /* 割り算 */ } return -1; /* なんか知らんけどここまでくるのはエラー (-_-#) */ } /* 四則演算の関数郡 */ /* 返り値: -1 でエラー(たぶん 0 除算エラー) */ int add(int *ans, int num1, int num2) /* 足し算関数 */ { *ans = num1 + num2; return 1; } int sub(int *ans, int num1, int num2) /* 引き算関数 */ { *ans = num1 - num2; return 1; } int mul(int *ans, int num1, int num2) /* 掛け算関数 */ { *ans = num1 * num2; return 1; } int div(int *ans, int num1, int num2) /* 割り算関数 */ { if (num2 == 0) { return -1; } *ans = num1 / num2; return 1; }