读取文件并将其内容存储到 2-D 数组C++中
Reading a file and storing its contents into a 2-D Array C++
我一直在尝试创建一个函数,该函数读取名为"test.txt"的文件并将其内容存储到二维数组中以用于其他函数。
它似乎正在从文本文件中读取某些内容,但它只在测试.txt数字应该在的区域重复"-9.25996e+61"。
任何帮助将不胜感激,谢谢。
"test.txt"文件包含以下 12 个元素。它们在文档中垂直对齐:
70
80
90
75
85
90
60
80
80
90
80
75
我的代码是:
#include <iostream>
#include <fstream>
using namespace std;
//S is the # of students and T is the number of test scores per student
const int S = 3;
const int T = 4;
void getTests(double[][T]);
int main()
{
double testScores[S][T];
getTests(testScores);
}
//*******************
//Gets test scores
void getTests(double testScores[S][T])
{
ifstream testFile("test.txt");
double score;
for (int student = 0; student < S; student++)
{
cout << "Student " << student + 1 << endl;
for (int test = 0; test < T; test++)
{
testFile >> score;
cout << "Test " << test + 1 << endl;
cout << score << endl;
}
}
}
上面的代码输出:
Student 1
Test 1
9.25596e+61
Test 2
9.25596e+61
Test 3
9.25596e+61
Test 4
9.25596e+61
Student 2
Test 1
9.25596e+61
Test 2
9.25596e+61
Test 3
9.25596e+61
Test 4
9.25596e+61
Student 3
Test 1
9.25596e+61
Test 2
9.25596e+61
Test 3
9.25596e+61
Test 4
9.25596e+61
输出表明您尝试使用ifstream testFile("test.txt");
打开文件失败。您永远不会验证文件是否已打开,并且无法验证每次读取,因此您无法知道文件从未打开过。
处理输入时,必须验证每个操作。您可以通过验证流状态 std::basic_ios 提供成员函数来执行此操作,允许您通过成员函数.good(), .eof(), .fail() & .bad()
检查流状态。应在尝试打开文件后立即验证流状态。使用.good()
显式执行,或通过验证每次尝试从文件中读取是否成功来隐式执行。
在您的情况下,您可以执行以下操作:
/* read test scores from file 'fname' */
void getTests(double testScores[][T], std::string fname)
{
std::ifstream testFile (fname); /* open file */
double score;
if (!testFile.good()) { /* validate file is open for reading */
std::cerr << "error: file open failed - " << fname << 'n';
return;
}
(注意:不要在代码中硬编码文件名,尤其是不要埋在函数中。将文件名作为参数传递,或者更好的是,在调用方中打开文件,并在验证调用方中的打开成功后将打开的文件流作为参数传递。如果文件无法成功打开,则无需进行函数调用...
从文件中读取分数时,必须验证每次读取。您可以通过使用读取本身的结果控制读取循环来做到这一点。getTests()
函数的简单其余部分可以是:
for (int student = 0; testFile.good() && student < S; student++) {
int test = 0;
std::cout << "Student " << student + 1 << 'n';
while (test < T && testFile >> score) { /* validate EVERY input */
testScores[student][test] = score; /* store value in array */
std::cout << "Test " << ++test << 'n' << score << 'n';
}
}
}
上面的读取循环以test < T
和testFile >> score
为条件。如果读取score
失败,循环将退出。同样,由于您使用嵌套循环来读取一定数量的学生,因此外部循环只会递增,而testFile.good()
保持不变。
总而言之,您的简短示例将是:
#include <iostream>
#include <fstream>
#include <string>
const int S = 3; /* number of students */
const int T = 4; /* number of scores per-student */
void getTests(double[][T], std::string fname); /* pass filename as parameter */
int main (int argc, char **argv) {
double testScores[S][T];
std::string filename = argc > 1 ? argv[1] : "test.txt";
getTests (testScores, filename);
}
/* read test scores from file 'fname' */
void getTests(double testScores[][T], std::string fname)
{
std::ifstream testFile (fname); /* open file */
double score;
if (!testFile.good()) { /* validate file is open for reading */
std::cerr << "error: file open failed - " << fname << 'n';
return;
}
for (int student = 0; testFile.good() && student < S; student++) {
int test = 0;
std::cout << "Student " << student + 1 << 'n';
while (test < T && testFile >> score) { /* validate EVERY input */
testScores[student][test] = score; /* store value in array */
std::cout << "Test " << ++test << 'n' << score << 'n';
}
}
}
(注意:程序期望文件名作为程序的第一个st参数读取。如果未提供参数,则默认情况下,程序将尝试从test.txt
读取。另请注意:您通常希望避免在代码中包含整个namespace std
。这取决于你,但通常不受欢迎。
示例输入文件
$ cat dat/test12elements.txt
70
80
90
75
85
90
60
80
80
90
80
75
示例使用/输出
$ ./bin/studentscores dat/test12elements.txt
Student 1
Test 1
70
Test 2
80
Test 3
90
Test 4
75
Student 2
Test 1
85
Test 2
90
Test 3
60
Test 4
80
Student 3
Test 1
80
Test 2
90
Test 3
80
Test 4
75
仔细查看,如果您有其他问题,请告诉我。此外,与其将分数存储在普通的旧数组中double
,不如考虑使用 std::array 或 std::vector。您甚至可以创建一个简短的结构或std::unordered_set
,以允许您存储学生姓名以及测试分数的数组或向量。
- Mongodb c++驱动程序:如何查询元素的数组
- 将数组的地址分配给变量并删除
- 从C++本机插件更新Vector3数组
- lambda参数转换为constexpr技巧,然后获取带链接的数组
- 将数组作为参数传递给函数安全吗?作为第三方职能部门,可以探索他们想要的之外的其他元素
- 数组索引的值没有增加
- 将对象数组的引用传递给函数
- 为char数组调整zlib-zpipe
- 2D数组来自文本输入,中间有空格
- std::向量与传递值的动态数组
- 在c++中用vector填充一个简单的动态数组
- 使用strcpy将char数组的元素复制到另一个数组
- 使用指针从C++中的数组中获取最大值
- C++使用整数的压缩数组初始化对象
- 告诉一个 const char 数组,除了编译时 C 样式的字符串外,它不以 '