Writing .csv files from C++

C++Csv

C++ Problem Overview


I'm trying to output some data to a .csv file and it is outputting it to the file but it isn't separating the data into different columns and seems to be outputting the data incorrectly.

    ofstream Morison_File ("linear_wave_loading.csv");         //Opening file to print info to
    Morison_File << "Time Force(N/m)" << endl;          //Headings for file
    for (t = 0; t <= 20; t++) {
      u = sin(omega * t);
      du = cos(omega * t); 
      F = (0.5 * rho * C_d * D * u * fabs(u)) + rho * Area * C_m * du; 
      
      cout << "t = " << t << "\t\tF = " << F << endl;
      Morison_File << t;                                 //Printing to file
      Morison_File << F;

    }
 
     Morison_File.close();

Time and Force(N/m) are in columns A and B respectively but the t and F values are both printing the first row.

What is the syntax to separate them to print t into column A and F into column B?

C++ Solutions


Solution 1 - C++

There is nothing special about a CSV file. You can create them using a text editor by simply following the basic rules. The RFC 4180 (tools.ietf.org/html/rfc4180) accepted separator is the comma ',' not the semi-colon ';'. Programs like MS Excel expect a comma as a separator.

There are some programs that treat the comma as a decimal and the semi-colon as a separator, but these are technically outside of the "accepted" standard for CSV formatted files.

So, when creating a CSV you create your filestream and add your lines like so:

#include <iostream>
#include <fstream>
int main( int argc, char* argv[] )
{
      std::ofstream myfile;
      myfile.open ("example.csv");
      myfile << "This is the first cell in the first column.\n";
      myfile << "a,b,c,\n";
      myfile << "c,s,v,\n";
      myfile << "1,2,3.456\n";
	  myfile << "semi;colon";
      myfile.close();
      return 0;
}

This will result in a CSV file that looks like this when opened in MS Excel:

Image of CSV file created with C++

Solution 2 - C++

Here is a STL-like class

File "csvfile.h"

#pragma once

#include <iostream>
#include <fstream>

class csvfile;

inline static csvfile& endrow(csvfile& file);
inline static csvfile& flush(csvfile& file);

class csvfile
{
	std::ofstream fs_;
	const std::string separator_;
public:
	csvfile(const std::string filename, const std::string separator = ";")
		: fs_()
		, separator_(separator)
	{
		fs_.exceptions(std::ios::failbit | std::ios::badbit);
		fs_.open(filename);
	}

	~csvfile()
	{
		flush();
		fs_.close();
	}

	void flush()
	{
		fs_.flush();
	}

	void endrow()
	{
		fs_ << std::endl;
	}

	csvfile& operator << ( csvfile& (* val)(csvfile&))
	{
		return val(*this);
	}

	csvfile& operator << (const char * val)
	{
		fs_ << '"' << val << '"' << separator_;
		return *this;
	}

	csvfile& operator << (const std::string & val)
	{
		fs_ << '"' << val << '"' << separator_;
		return *this;
	}

	template<typename T>
	csvfile& operator << (const T& val)
	{
		fs_ << val << separator_;
		return *this;
	}
};


inline static csvfile& endrow(csvfile& file)
{
	file.endrow();
	return file;
}

inline static csvfile& flush(csvfile& file)
{
	file.flush();
	return file;
}

File "main.cpp"

#include "csvfile.h"

int main()
{
	try
	{
		csvfile csv("MyTable.csv"); // throws exceptions!
		// Header
		csv << "X" << "VALUE"        << endrow;
		// Data
		csv <<  1  << "String value" << endrow;
		csv <<  2  << 123            << endrow;
		csv <<  3  << 1.f            << endrow;
		csv <<  4  << 1.2            << endrow;
	}
	catch (const std::exception& ex)
	{
		std::cout << "Exception was thrown: " << e.what() << std::endl;
	}
	return 0;
}

Latest version here

Solution 3 - C++

Change

Morison_File << t;                                 //Printing to file
Morison_File << F;

To

Morison_File << t << ";" << F << endl;                                 //Printing to file

a , would also do instead of ;

Solution 4 - C++

You must ";" separator, CSV => Comma Separator Value

 ofstream Morison_File ("linear_wave_loading.csv");         //Opening file to print info to
    Morison_File << "'Time'; 'Force(N/m)' " << endl;          //Headings for file
    for (t = 0; t <= 20; t++) {
      u = sin(omega * t);
      du = cos(omega * t); 
      F = (0.5 * rho * C_d * D * u * fabs(u)) + rho * Area * C_m * du; 

      cout << "t = " << t << "\t\tF = " << F << endl;
      Morison_File << t << ";" << F;

    }

     Morison_File.close();

Solution 5 - C++

If you wirte to a .csv file in C++ - you should use the syntax of :

myfile <<" %s; %s; %d", string1, string2, double1 <<endl;

This will write the three variables (string 1&2 and double1) into separate columns and leave an empty row below them. In excel the ; means the new row, so if you want to just take a new row - you can alos write a simple ";" before writing your new data into the file. If you don't want to have an empty row below - you should delete the endl and use the:

myfile.open("result.csv", std::ios::out | std::ios::app);

syntax when opening the .csv file (example the result.csv). In this way next time you write something into your result.csv file - it will write it into a new row directly below the last one - so you can easily manage a for cycle if you would like to.

Solution 6 - C++

As explained above by @kris, depending on the region configurations of MS Excel it won't interpret the comma as the separator character. In my case I had to change it to semi-colon

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
Questionuser3460758View Question on Stackoverflow
Solution 1 - C++BHawkView Answer on Stackoverflow
Solution 2 - C++Valdemar_RudolfovichView Answer on Stackoverflow
Solution 3 - C++Mr.WorshipMeView Answer on Stackoverflow
Solution 4 - C++MiguelAngel_LVView Answer on Stackoverflow
Solution 5 - C++Ádám HadarView Answer on Stackoverflow
Solution 6 - C++Edson ManoelView Answer on Stackoverflow