将csv文件中的数据读取到数组中



我有一个CSV文件,我希望将其中的值存储到C++中的三维数组Cl[x][y][z]中。

当前文件遵循二维阵列的格式。

29  26  20  18  
29  25  23  21  
31  28  25  23
33  30  28  25  

这个2D阵列必须在第三维度中重复多次才能产生3D阵列,我将在代码中进一步使用它。

目前,我在读取csv文件中的值并将其转换为C++中的3D数组时遇到了问题。

这是我目前拥有的代码:

unsigned short int widthX = wX;
unsigned short int widthY = wY;
unsigned short int widthZ = wZ;
unsigned short int x, y, z;
float clvDefault = 0.0;
float *** Cl = new float**[widthZ];
for (i=0; i<widthZ; i++) 
{
Cl[i] = new float*[widthY];
for (j=0; j<widthY; j++) 
{
Cl[i][j] = new float[widthX];
}
}
std::ifstream clvIn;
std::string clvFileName = "File_read.csv";
clvIn.open(clvFileName.c_str());
if(clvIn.fail())
{
// something bad happened when opening the file
}
std::string filejunk;
char delim;
std::getline(clvIn, filejunk);
int clvX, clvY, clvZ;
float clvValue;
for (z = 0; z < widthZ; z++)
{
for (y = 0; y < widthY; y++)
{
for (x = 0; x < widthX; x++)
{
Cl[z][y][x] = clvDefault;
}
}
}

while(clvIn >> clvY >> delim >> clvX >> delim >> clvValue)
{
Cl[0][clvY][clvX] = clvValue;
}
for(y = 0; y < widthY; y++)
{
for(x = 0; x < widthX; x++)
{
clvIn >> Cl[0][y][x] >> delim;
}
for (z = 1; z < widthZ; z++)
{
for (y = 0; y < widthY; y++)
{
for (x = 0; x < widthX; x++)
{
Cl[z][y][x] = Cl[0][y][x];
}
}
}

当我运行代码时,数组的每个元素都有我分配的clvDefault值,并且不会读取csv文件中的值。

看起来while循环在运行过程中被跳过了。欢迎就如何解决此问题提出任何建议。

程序中有很多错误。让我列出最重要的:

  • 拥有内存的原始指针的使用。永远不要在C++中执行此操作(如果有的话,请改用std::unique_ptr(
  • 不要在C++中使用new来分配内存(使用std::make_unique(
  • 如果使用new分配内存,则必须稍后使用delete
  • 最佳:请使用标准库中的容器,在本例中为std::vector
  • 始终初始化所有变量
  • 始终检查打开或>>等文件操作的结果
  • 处理错误
  • 使用++v而不是v++
  • 在需要时定义变量。保持它们的作用域。防止命名空间污染
  • 如果你想写C++代码,那么就使用C++语言元素,而不是C
  • 尝试使用现代C++语言元素设计代码

所以。我修复了您的代码,使其运行、读取示例文件并显示结果。我去掉了主要的bug。请参阅:

#include <iostream>
#include <fstream>
#include <string>
#include <sstream>
float*** get3dArry(unsigned short widthX, unsigned short widthY, unsigned short widthZ) {
unsigned short int i, j, x, y, z;
float clvDefault = 0.0;
float*** Cl = new float** [widthZ];
for (i = 0; i < widthZ; i++)
{
Cl[i] = new float* [widthY];
for (j = 0; j < widthY; j++)
{
Cl[i][j] = new float[widthX];
}
}
std::ifstream clvIn;
std::string clvFileName = "r:\File_read.csv";
clvIn.open(clvFileName.c_str());
if (clvIn.fail())
{
std::cerr << "n*** Error: Could not open input filen";
}
else {
std::string filejunk, line;
char delim;
//std::getline(clvIn, filejunk);
int clvX, clvY, clvZ;
float clvValue;
for (z = 0; z < widthZ; z++)
{
for (y = 0; y < widthY; y++)
{
for (x = 0; x < widthX; x++)
{
Cl[z][y][x] = clvDefault;
}
}
}
for (y = 0; (y < widthY) && std::getline(clvIn, line); ++y) {
std::istringstream iss{ line };
for (x = 0; (x < widthY) && (iss >> Cl[0][y][x]); ++x)
;
}
for (z = 0; z < widthZ; z++)
{
for (y = 0; y < widthY; y++)
{
for (x = 0; x < widthX; x++)
{
Cl[z][y][x] = Cl[0][y][x];
}
}
}
}
return Cl;
}
int main() {
float*** a3d = get3dArry(4, 4, 3);
for (int z = 0; z < 3; ++z) {
std::cout << "n";
for (int y = 0; y < 4; ++y) {
for (int x = 0; x < 4; ++x) {
std::cout << a3d[z][y][x] << "t";
}
std::cout << "n";
delete[] a3d[z][y];
}
delete[] a3d[z];
}
delete[] a3d;
return 0;
}

然而。我不建议使用它。质量太差了。它很容易出错,而且在某种程度上仍然可以完成C程序。

请参阅我阅读CSV文件的部分。当然,这里不需要外部图书馆。我经常听到这种对超简单CSV文件的无意义的建议。所以,没有图书馆。以上代码示例:

for (y = 0; (y < widthY) && std::getline(clvIn, line); ++y) {
std::istringstream iss{ line };
for (x = 0; (x < widthY) && (iss >> Cl[0][y][x]); ++x)
;
}

没有人能说服我,我需要一个库,因为我可以用3行简单的代码做什么。

如果你有兴趣学习,那么我还会向你展示一个"更现代"的C++解决方案:

#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <sstream>
#include <iterator>
// Make reading datatypes easier
using DataType = float;
using Matrix1dX = std::vector<DataType>;
using Matrix2dYX = std::vector<Matrix1dX>;
using Matrix3dZYX = std::vector<Matrix2dYX>;
// This is the number of z values for the 3rd dimension. Whatever you want
constexpr size_t NumberOfDimensionZ = 3U;
int main() {
// Open input csv file, and check, if open operation worked
if (std::ifstream clvIn("r:\File_read.csv"); clvIn) {
// Define 2d array and initialize all values with 0.0;
Matrix2dYX myx{};
// Read all lines of the file and split values
for (std::string line{}; std::getline(clvIn, line); ) {
// Convert just read string to a std::istringstream
std::istringstream iss{ line };
// Add the new values to the 2d array. Iterate over all values in one line
// then create a 1d vector inplace and add this line values to our 2d matrix
myx.emplace_back(Matrix1dX(std::istream_iterator<DataType>(iss), {}));
}
// Define a 3d matrix, with a given size and having each z-value be the data from the csv file
Matrix3dZYX mzyx(NumberOfDimensionZ, myx);

// Some debug output
// Show result to user
for (const Matrix2dYX& m2 : mzyx) {
std::cout << "n";
for (const Matrix1dX& m1 : m2) {
for (const DataType& d : m1) std::cout << d << "t";
std::cout << "n";
}
}
}
else {
std::cerr << "n*** Error: Could not open input filen";
}
return 0;
}

请注意,您可以用C++编写优雅、非常优雅和紧凑的代码。

对于读取文件和创建三维矢量,我不需要任何循环。

请阅读并试着理解。请用谷歌搜索unknwon语言结构。如果你不明白,那就去问。

相关内容

  • 没有找到相关文章

最新更新