Abstract Base类作业中getInput函数触发段错误求助
问题分析与修复建议
你的代码存在两个核心问题,直接导致段错误和后续潜在崩溃:
1. getInput函数的野指针问题
原代码中char* name是未初始化的野指针,没有分配任何内存空间,std::cin.getline(name, INT_MAX)直接往无效地址写入数据,必然触发段错误。
修复方案:
优先用std::string替代C风格字符指针,无需手动管理内存,安全简洁:
#include <limits> // 需要引入这个头文件使用numeric_limits std::string getInput(std::string message) { std::string name; std::cout << message << std::endl; // 清除之前输入残留的换行符(如果前面用cin >> 读取过整数,必须加这行) std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n'); std::getline(std::cin, name); return name; }
如果一定要用C风格指针,必须手动分配内存(记得后续释放):
#include <limits> char* getInput(std::string message) { // 分配足够大的缓冲区,这里设为1024字节 char* name = new char[1024]; std::cout << message << std::endl; std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n'); std::cin.getline(name, 1023); // 留1字节存字符串结束符 return name; }
2. 局部对象指针存入vector导致悬空指针
addRecord里的Student student = Student();和Employee employee = Employee();是栈上的局部变量,代码块执行完毕后会被自动销毁。你把它们的地址存入vector,后续访问这些指针时会指向已释放的内存,引发未定义行为。
修复方案:
用new动态分配对象,将堆上的对象指针存入vector:
void addRecord(std::vector<Base*>& v) { std::cout << "--Records to Create--" << std::endl; std::cout << "1.) Student Record" << std::endl; std::cout << "2.) Employee Record" << std::endl; std::cout << "Please select from the above options: "; int sel = intInputLoop(1, 2); clearConsole(); if (sel == 1) { std::string name = getInput("What is the Student's name? "); float gradePointAverage = static_cast<float>(intInputLoop(0, 4)); // 动态分配Student对象,指针存入vector Student* student = new Student(); student->setName(name); // 若setName参数是char*,则传name.c_str() student->setGradePointAverage(gradePointAverage); v.push_back(student); std::cout << "Added Student record for " << name << " with a grade point average of " << gradePointAverage << std::endl; } else { std::string name = getInput("What is the Employee's name? "); std::cout << "What is the Employee's salary? "; int salary = intInputLoop(0, 0); // 动态分配Employee对象,指针存入vector Employee* employee = new Employee(); employee->setName(name); employee->setSalary(salary); v.push_back(employee); std::cout << "Added Employee record for " << name << " with a salary of " << salary << std::endl; } }
注意:后续需要在程序结束或清理vector时,遍历vector用delete释放所有动态分配的对象,避免内存泄漏。
额外提醒
std::cin.ignore的使用要匹配前置输入:如果前面用cin >>读取过整数,输入缓冲区会残留换行符,必须用ignore清除;若前置没有残留换行,多次调用会导致程序等待输入。- 尽量用C++标准库的
std::string代替C风格字符数组,减少内存管理错误。
内容的提问来源于stack exchange,提问作者Sage Hopkins
相关产品推荐
相关产品推荐

