You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C程序传参触发Segmentation fault问题排查求助

问题分析与解决

核心错误原因

段错误的直接原因是**isdigit(argv[i])的调用完全错误**:

  • isdigit函数的参数要求是单个字符(准确说是unsigned char类型的值,需强制转换避免负数字符的未定义行为),而argv[i]是指向字符串的指针(char*类型)。你直接把指针传入isdigit,函数会把这个指针的地址值当作字符的ASCII码去处理,相当于尝试访问一个非法的内存地址,必然触发段错误。

修正方案

要实现“检查参数是否为纯数字(支持负号可额外处理)”,需要遍历每个参数字符串的每一个字符,逐一检查是否为数字(或负号,若允许负数):

  1. 对每个argv[i],先判断是否为空字符串(避免空参数的异常)
  2. 若字符串以'-'开头,从第二个字符开始检查是否全为数字;否则从第一个字符开始检查
  3. 遍历过程中只要发现非数字字符,立即输出Error并退出

修正后的代码

#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>

int main(int argc, char *argv[])
{
    int i, j;
    int sum = 0;

    if (argc == 1) {
        printf("0\n");
        return 0;
    }

    for (i = 1; i < argc; i++) {
        // 处理空参数的情况
        if (argv[i][0] == '\0') {
            printf("Error\n");
            return 1;
        }
        // 检查第一个字符是否是负号或数字
        j = 0;
        if (argv[i][j] == '-') {
            j++;
            // 如果只有负号,没有后续数字,也算非法
            if (argv[i][j] == '\0') {
                printf("Error\n");
                return 1;
            }
        }
        // 遍历剩余字符,检查是否全为数字
        for (; argv[i][j] != '\0'; j++) {
            // 强制转成unsigned char,避免负数字符的未定义行为
            if (!isdigit((unsigned char)argv[i][j])) {
                printf("Error\n");
                return 1;
            }
        }
        sum += atoi(argv[i]);
    }

    printf("%d\n", sum);
    return 0;
}

额外说明

  • 原代码的循环条件i < argc是没问题的,确实能保证访问argv的合法范围
  • 如果你的需求不允许负数,直接去掉负号的判断逻辑即可,从第一个字符开始检查是否全为数字

内容的提问来源于stack exchange,提问作者fromesoli

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 22:37:24