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

C语言结构体操作触发Segmentation Fault错误求助

账户创建时Segmentation Fault问题排查

问题描述

你编写的C语言账户管理代码在菜单选择选项1创建账户,输入姓名后触发Segmentation Fault错误,错误发生在scanf(" %49s", ptr->name)行。即便将格式符从%50s改为%49s匹配数组大小,问题仍未解决。

原始代码

#include "stdio.h"

typedef struct
{
    char name[50];
    int money;
    char IBAN[50];
    char passoword[20];
    char email[30];
}account;

void create_account(account *ptr)
{
    printf("****Welcome to account resgister****\n");
    printf("Whats your name?: \n");
    scanf(" %49s",ptr->name);
    printf("Whats your email? : ");
    scanf(" %29s",ptr->email);
    printf("Type you password (from 4 to 20): ");
    scanf(" %19s",ptr->passoword);
}

int menu()
{
    char option = 0;
    while(option != '0' && option != '1' && option != '2')
    {
        printf("****MENU****\n");
        printf("0 - Exit\n");
        printf("1 - Create Account\n");
        printf("2 - Log in\n");
        printf("What you want to do: \n");
        scanf(" %c", &option);
    }
    return option;
}

int main (void)
{
    char option;
    account *ptr;

    while(option != '0')
    {
        option = menu();

        switch (option)
        {
        case '0':
            break;
        case '1':
            create_account(ptr);
            break;
        }
    }
}

问题根源

核心原因是指针ptr未初始化:
在main函数中,你仅声明了account *ptr;,但未给该指针分配有效的内存地址。此时ptr是一个野指针,指向内存中的随机区域。当create_account函数尝试通过ptr->name访问结构体成员时,本质是在访问非法内存空间,直接触发Segmentation Fault。

修复方案

方案1:使用栈上的结构体实例(简单场景推荐)

在main函数中声明栈上的account变量,让指针指向该变量的内存地址:

int main (void)
{
    char option;
    account acc; // 在栈上分配结构体实例
    account *ptr = &acc; // 让指针指向该实例的地址

    while(option != '0')
    {
        option = menu();

        switch (option)
        {
        case '0':
            break;
        case '1':
            create_account(ptr);
            break;
        }
    }
    return 0; // 补充符合C标准的返回值
}

方案2:动态分配内存(多账户/长期存储场景推荐)

通过malloc分配堆内存,使用完成后记得释放避免内存泄漏:

#include "stdio.h"
#include "stdlib.h" // 引入stdlib.h用于malloc和free

typedef struct
{
    char name[50];
    int money;
    char IBAN[50];
    char password[20]; // 修正拼写错误
    char email[30];
}account;

// 其余函数代码保持不变...

int main (void)
{
    char option;
    account *ptr = NULL;

    while(option != '0')
    {
        option = menu();

        switch (option)
        {
        case '0':
            if (ptr != NULL) {
                free(ptr); // 释放动态分配的内存
                ptr = NULL;
            }
            break;
        case '1':
            if (ptr != NULL) {
                free(ptr); // 若已有账户,先释放再重新分配
            }
            ptr = (account*)malloc(sizeof(account));
            if (ptr == NULL) { // 检查内存分配是否成功
                printf("内存分配失败\n");
                break;
            }
            create_account(ptr);
            break;
        }
    }
    return 0;
}

额外优化建议

  • 修正拼写错误:resgister改为register,passoword改为password
  • menu函数返回值类型改为char,与实际返回的option类型匹配
  • 所有scanf的格式符前的空格可以保留,用于跳过输入缓冲区的空白字符,是合理的写法

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.02 02:06:10