回答編集履歴
3
気づいた点を追加
answer
CHANGED
|
@@ -79,7 +79,7 @@
|
|
|
79
79
|
ans = calc(num1, num2, op);
|
|
80
80
|
|
|
81
81
|
```
|
|
82
|
-
演算子直前の空白はどうすべきか、エラーチェックなどまだまだ不完全・・・ですが、流れがシンプルで見通しがよくなったと思います。
|
|
82
|
+
演算子直前の空白はどうすべきか、エラーチェックなどまだまだ不完全・・・ですが、流れがシンプルで見通しがよくなったと思います。この線で私なりの完成形を作ることができました。
|
|
83
83
|
|
|
84
84
|
> その他何か、お気づきの点があれば
|
|
85
85
|
|
|
@@ -99,4 +99,6 @@
|
|
|
99
99
|
2. 繰り返すことを見越してループの最後で num1 〜 countnum に0を代入していますが、**初期値の代入はループに入った先頭で行うべき**です。
|
|
100
100
|
さらに、main() の先頭は ``` int num1; ``` と変数定義だけにして、初期化は不要です。不要なことは書かない。一箇所でできることは一箇所で行ったほうがよい。
|
|
101
101
|
|
|
102
|
-
- STRLEG は string length を短縮したのだと思いますが、LEG だと長さではなく「脚」になって良くない(脚にも長さあるがw)。重箱の隅のようだけど、格好悪いし、名前は案外大事だということで。6文字ならSTRLENかな。
|
|
102
|
+
- STRLEG は string length を短縮したのだと思いますが、LEG だと長さではなく「脚」になって良くない(脚にも長さあるがw)。重箱の隅のようだけど、格好悪いし、名前は案外大事だということで。6文字ならSTRLENかな。
|
|
103
|
+
|
|
104
|
+
- ```#define STRLEG 16``` ですが、int 型が 32bit なら10進数で10桁まで扱えるので、16文字では少ないと言えます。fgets()で入力するなら \n と \0 の2文字分を含めて、最低でも 10 + 1 + 10 + 2 = 23 文字、さらに空白文字の分もあったほうが良いでしょうね。
|
2
説明を一文追加
answer
CHANGED
|
@@ -14,7 +14,7 @@
|
|
|
14
14
|
|
|
15
15
|
と、**今見ているものをif文で区別しながら処理する必要があるので、それだけでもインデントは1〜2段深くなる**のです。私には諸悪の根源に思えてきました(笑)。
|
|
16
16
|
|
|
17
|
-
そこで、こんなふうに組み直したらどうか(まずは、空白は無い、エラーチェックも要らないと仮定し、正常な処理の本筋だけを考えてみる)。
|
|
17
|
+
要は、入力した文字列から2つの数字と演算子を切り出すことです。そこで、こんなふうに組み直したらどうか(まずは、空白は無い、エラーチェックも要らないと仮定し、正常な処理の本筋だけを考えてみる)。
|
|
18
18
|
|
|
19
19
|
```C
|
|
20
20
|
p = str; // 入力した行の先頭から見ていく
|
1
str2num() を conv2num() に。他、少し表現を修正。
answer
CHANGED
|
@@ -4,9 +4,9 @@
|
|
|
4
4
|
|
|
5
5
|
> 帳尻合わせのデクリメントを対処する方法
|
|
6
6
|
|
|
7
|
-
p--; が必要になる理由は、``` for (p = str; *p != '\n'; p++)``` というループの中で数字やら演算子やらを切り出しているからです。ですから Chironian さんが
|
|
7
|
+
p--; が必要になる理由は、``` for (p = str; *p != '\n'; p++)``` というループの中で数字やら演算子やらを切り出しているからです。ですから Chironian さんがおっしゃるように、``` for (p = str; *p != '\n'; ) ``` とする手もあるでしょうが、、、
|
|
8
8
|
|
|
9
|
-
もうひとつ、Chironianさん
|
|
9
|
+
もうひとつ、Chironianさんご指摘の、インデントが深いことも考慮する必要があります。インデントが深いほど理解しにくく、メンテナンスしにくくなるのだから。
|
|
10
10
|
インデントが深くなる原因は、関数化していないことに加えて、``` for (p = str; ...)``` という大きなループの中で処理していることです。このforループの中で
|
|
11
11
|
- ひとつめの数字
|
|
12
12
|
- 演算子
|
|
@@ -42,7 +42,7 @@
|
|
|
42
42
|
return ptr; // 次の文字位置を返す
|
|
43
43
|
}
|
|
44
44
|
|
|
45
|
-
char *
|
|
45
|
+
char *conv2num(char *ptr, int *num) // 数字に変換する
|
|
46
46
|
{
|
|
47
47
|
int result = 0;
|
|
48
48
|
|
|
@@ -68,9 +68,9 @@
|
|
|
68
68
|
break;
|
|
69
69
|
|
|
70
70
|
p = str; // 入力行の先頭から
|
|
71
|
-
p =
|
|
71
|
+
p = conv2num(p, &num1); // 数字ひとつめ
|
|
72
72
|
op = *p++; // 演算子
|
|
73
|
-
p =
|
|
73
|
+
p = conv2num(p, &num2); // 数字ふたつめ
|
|
74
74
|
|
|
75
75
|
if (op == '/' && num2 == 0) { // 0除算しない
|
|
76
76
|
// 0除算エラー
|
|
@@ -79,7 +79,7 @@
|
|
|
79
79
|
ans = calc(num1, num2, op);
|
|
80
80
|
|
|
81
81
|
```
|
|
82
|
-
エラーチェックなどまだまだ不完全
|
|
82
|
+
演算子直前の空白はどうすべきか、エラーチェックなどまだまだ不完全・・・ですが、流れがシンプルで見通しがよくなったと思います。
|
|
83
83
|
|
|
84
84
|
> その他何か、お気づきの点があれば
|
|
85
85
|
|
|
@@ -99,4 +99,4 @@
|
|
|
99
99
|
2. 繰り返すことを見越してループの最後で num1 〜 countnum に0を代入していますが、**初期値の代入はループに入った先頭で行うべき**です。
|
|
100
100
|
さらに、main() の先頭は ``` int num1; ``` と変数定義だけにして、初期化は不要です。不要なことは書かない。一箇所でできることは一箇所で行ったほうがよい。
|
|
101
101
|
|
|
102
|
-
- STRLEG は string length を短縮したのだと思いますが、LEG だと長さではなく「脚」
|
|
102
|
+
- STRLEG は string length を短縮したのだと思いますが、LEG だと長さではなく「脚」になって良くない(脚にも長さあるがw)。重箱の隅のようだけど、格好悪いし、名前は案外大事だということで。6文字ならSTRLENかな。
|