輸入一個數字字符串,將其奇數索引位(0-based:第 1、3、5... 位)的字符逆序,偶數位保持原序,拼接生成新數字字符串輸出。
#include <stdio.h>
int main() {
char ch1[999], ch2[500];
int i, j;
gets(ch1); // 不安全,已棄用
for (i = 0, j = 0; ch1[i] != '\0'; i++)
if (i % 2) ch2[j++] = ch1[i], ch2[j] = '\0';
for (i = 0; ch1[i] != '\0'; i++)
if (i % 2) printf("%d", ch2[--j] - '0');
else printf("%d", ch1[i] - '0');
puts("");
return 0;
}
| 問題 | 改進 |
|---|---|
gets 無緩衝區保護,極易溢出 | 用 fgets(ch1, sizeof(ch1), stdin) 並去除換行符 |
| 固定大小數組,長度受限 | 動態分配或定義足夠大的常量 MAX_LEN |
| 邏輯雙循環,可合併 | 單次遍歷收集奇數位,再逆序輸出 |
| 無輸入驗證(非數字字符) | 增加 isdigit 檢查 |
| 直接打印數字字符,非數值 | 明確需求:輸出字符串即可,無需轉數值 |
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
#define MAX_LEN 1024
int main() {
char input[MAX_LEN];
if (!fgets(input, sizeof(input), stdin)) return 1;
input[strcspn(input, "\n")] = '\0'; // 去除換行
// 驗證全數字
for (int i = 0; input[i]; ++i)
if (!isdigit(input[i])) {
fprintf(stderr, "輸入必須為純數字\n");
return 1;
}
int len = strlen(input);
char *odd_chars = malloc((len/2 + 1) * sizeof(char));
int odd_cnt = 0;
// 收集奇數索引字符
for (int i = 1; i < len; i += 2)
odd_chars[odd_cnt++] = input[i];
odd_chars[odd_cnt] = '\0';
// 輸出結果
for (int i = 0, o = odd_cnt - 1; i < len; ++i) {
if (i % 2 == 1) putchar(odd_chars[o--]);
else putchar(input[i]);
}
putchar('\n');
free(odd_chars);
return 0;
}
輸入: 123456789
索引: 0 1 2 3 4 5 6 7 8
奇數位: 2 4 6 8 → 逆序: 8 6 4 2
輸出: 183654729
輸入: 0
輸出: 0
輸入: 12
輸出: 12 (無奇數位)
拒絕 gets,善用 fgets + strcspn 安全讀行;邏輯清晰分階段(收集→逆序→合併),代碼可讀性與健壯性並重。