我没有看到这个问题已经发布,或任何有用的类似内容。
我正在上第二学期的 C++ 课程,只通过了 10 个测试点中的 5 个。我可以看出我的 try/catch 设置有问题。在互联网上搜索之后,我可能对我遇到的错误更加困惑:
main.cpp: In function ‘std::string FindID(std::string, std::ifstream&)’:
main.cpp:24:1: warning: control reaches end of non-void function [-Wreturn-type]
24 | }
| ^
main.cpp: In function ‘std::string FindName(std::string, std::ifstream&)’:
main.cpp:49:1: warning: control reaches end of non-void function [-Wreturn-type]
49 | }
| ^
问题和我的代码如下:
6.9 LAB:未找到学生信息
给定一个在文本文件中搜索学生 ID 或姓名的程序,请完成
FindID()
和 FindName()
函数。然后,在main()
中插入try/catch语句来捕获FindID()
或FindName()
抛出的任何异常,并输出异常消息。文本文件中的每一行都包含一个名称和 ID,以空格分隔。
函数
FindID()
有两个参数:学生姓名(字符串)和文本文件的内容(ifstream)。如果学生姓名在文件中,则函数 FindID()
返回与学生姓名关联的 ID,否则,函数抛出 runtime_error
并显示消息“未找到 StudentName 的学生 ID”,其中 StudentName 是学生的姓名.
函数
FindName()
有两个参数:学生的ID(字符串)和文本文件的内容(ifstream)。如果 ID 在文件中,则函数 FindName() 返回与学生 ID 关联的名称,否则,函数会抛出运行时错误,并显示消息“未找到学生 ID 的学生姓名”,其中 StudentID 是学生的 ID。
主程序接受用户的三个输入:文本文件的名称(字符串)、用于查找学生的 ID 或姓名的搜索选项(int)以及学生的 ID 或姓名(字符串)。如果搜索选项为 0,则以学生姓名作为参数调用 FindID()。如果搜索选项为 1,则以学生 ID 作为参数调用 FindName()。主程序输出搜索结果或捕获的异常消息。
例如:如果程序的输入是:
roster.txt 0 Reagan
roster.txt的内容是:
Reagan rebradshaw835
Ryley rbarber894
Peyton pstott885
Tyrese tmayo945
Caius ccharlton329
程序的输出是:
rebradshaw835
例如:如果程序的输入是:
roster.txt 0 Mcauley
程序输出异常信息:
Student ID not found for Mcauley
例如:如果程序的输入是:
roster.txt 1 rebradshaw835
程序的输出是:
Reagan
例如:如果程序的输入是:
roster.txt 1 mpreston272
程序输出异常信息:
Student name not found for mpreston272
我的main.cpp代码:
#include <string>
#include <iostream>
#include <stdexcept>
#include <fstream>
using namespace std;
string FindID(string name, ifstream &infoFS) {
bool foundID = false;
string input;
infoFS >> input;
while (infoFS)
{
if (input == name)
{
infoFS >> input;
return input;
}
else { infoFS >> input; }
}
if (foundID == false)
{
throw name;
}
}
string FindName(string ID, ifstream &infoFS) {
bool foundName = false;
string previous;
string input;
infoFS >> previous;
infoFS >> input;
while (infoFS)
{
if (input == ID)
{
foundName = true;
return previous;
}
else
{
previous = input;
infoFS >> input;
}
}
if (foundName == false)
{
throw ID;
}
}
int main() {
int userChoice;
string studentName;
string studentID;
string studentInfoFileName;
ifstream studentInfoFS;
// Read the text file name from user
cin >> studentInfoFileName;
// Open the text file
studentInfoFS.open(studentInfoFileName);
// Read search option from user. 0: FindID(), 1: FindName()
cin >> userChoice;
try
{
if (userChoice == 0) {
cin >> studentName;
studentID = FindID(studentName, studentInfoFS);
cout << studentID << endl;
}
else {
cin >> studentID;
studentName = FindName(studentID, studentInfoFS);
cout << studentName << endl;
}
}
catch (string name)
{
if (userChoice == 0) {
cout << "Student ID not found for " << name << endl;
}
}
catch (char ID)
{
cout << "Student name not found for " << ID << endl;
}
studentInfoFS.close();
return 0;
}
提交时编译器警告:
main.cpp: In function ‘std::string FindID(std::string, std::ifstream&)’:
main.cpp:24:1: warning: control reaches end of non-void function [-Wreturn-type]
24 | }
| ^
main.cpp: In function ‘std::string FindName(std::string, std::ifstream&)’:
main.cpp:49:1: warning: control reaches end of non-void function [-Wreturn-type]
49 | }
| ^
通过测试:
1: Compare output
Input
roster.txt 0 Reagan
Your output
rebradshaw835
2: Compare output
Input
roster.txt 0 Mcauley
Your output
Student ID not found for Mcauley
3: Compare output
Input
roster.txt 1 rebradshaw835
Your output
Reagan
7: Unit test
Test FindName("mpreston272", infoFS) with roster1.txt, should return Mcauley
Your output
FindName("mpreston272", infoFS) correctly returned Mcauley
8: Unit test
Test FindID("Mcauley", infoFS) with roster1.txt, should return mpreston272
Your output
FindID("Mcauley", infoFS) correctly returned mpreston272
失败的测试:
4: Compare output
Input
roster.txt 1 mpreston272
Your output
Your program produced no output
Expected output
Student name not found for mpreston272
5: Unit test
Test FindID("John", infoFS) with roster1.txt, should throw an exception
Returned unexpected error code (-6)
6: Unit test
Test FindName("jsmith474", infoFS) with roster1.txt, should throw an exception
Returned unexpected error code (-6)
我终于让它工作并通过了所有 10 项测试。感谢@WBuck 的评论,让我更仔细地研究了 try/catch 语法:“不要抛出 std::string,而是抛出 std::runtime_error。然后,将异常处理程序更改为:catch ( const std: :异常&错误) – WBuck”
我发现这篇文章很有帮助:如何抛出 C++ 异常
以及 cpp 参考站点:https://en.cppreference.com/w/cpp/language/function-try-block
我试图传递通用错误字符串,然后在 catch 语句中添加变量名称/ID 输入,但除非传递变量,否则这不起作用。因此,我必须使用默认消息 + 输入变量创建一个新字符串,然后将其作为一个字符串传递到引发的运行时错误中。
编译器内置于 ZyBooks 的网站中,并且没有说明它使用的 C++ 版本。
这是通过所有测试的代码,以防其他人遇到类似的问题。
#include <string>
#include <iostream>
#include <stdexcept>
#include <fstream>
using namespace std;
string FindID(string name, ifstream &infoFS) {
bool foundID = false;
string input;
infoFS >> input;
while (infoFS)
{
if (input == name)
{
foundID = true;
infoFS >> input;
return input;
break;
}
else { infoFS >> input; }
}
if (foundID == false)
{
string NoNameMsg = "Student ID not found for " + name;
throw runtime_error(NoNameMsg);
}
return "";
}
string FindName(string ID, ifstream &infoFS) {
bool foundName = false;
string previous;
string input;
infoFS >> previous;
infoFS >> input;
while (infoFS)
{
if (input == ID)
{
foundName = true;
return previous;
break;
}
else
{
previous = input;
infoFS >> input;
}
}
if (foundName == false)
{
string NoIDMsg = "Student name not found for " + ID;
throw std::runtime_error(NoIDMsg);
}
return "";
}
int main() {
int userChoice;
string studentName;
string studentID;
string studentInfoFileName;
ifstream studentInfoFS;
// Read the text file name from user
cin >> studentInfoFileName;
// Open the text file
studentInfoFS.open(studentInfoFileName);
// Read search option from user. 0: FindID(), 1: FindName()
cin >> userChoice;
try
{
if (userChoice == 0) {
cin >> studentName;
studentID = FindID(studentName, studentInfoFS);
cout << studentID << endl;
}
else {
cin >> studentID;
studentName = FindName(studentID, studentInfoFS);
cout << studentName << endl;
}
}
catch ( const std::runtime_error& e )
{
cout << e.what() << endl;
}
studentInfoFS.close();
return 0;
}
以下是 Python 中该问题的解决方案:
# Define custom exception
class StudentInfoError(Exception):
def __init__(self, message):
self.message = message # Initialize the exception message
def find_ID(name, info):
# Type your code here.
if name not in info.keys():
raise StudentInfoError('Student ID not found for {}'.format(name))
the_id = info[name]
return the_id
def find_name(ID, info):
# Type your code here.
if ID not in info.values():
raise StudentInfoError('Student name not found for {}'.format(ID))
the_name = list(info.keys())[list(info.values()).index(ID)]
return the_name
if __name__ == '__main__':
# Dictionary of student names and IDs
student_info = {
'Reagan' : 'rebradshaw835',
'Ryley' : 'rbarber894',
'Peyton' : 'pstott885',
'Tyrese' : 'tmayo945',
'Caius' : 'ccharlton329'
}
userChoice = input() # Read search option from user. 0: find_ID(), 1: find_name()
# FIXME: find_ID() and find_name() may throw an Exception.
# Insert a try/except statement to catch the exception and output any exception message.
if userChoice == "0":
try:
name = input()
result = find_ID(name, student_info)
print(result)
except StudentInfoError as e:
print(e)
else:
try:
ID = input()
result = find_name(ID, student_info)
print(result)
except StudentInfoError as e:
print(e)
发现对我的 Python 课程非常有帮助。谢谢!