CSV Quick Start
This page shows the fastest way to use rix/csv from a Vix.cpp project.
The examples use the public Rix facade:
#include <rix.hpp>and access CSV through:
rix.csvWhat you will build
You will create a small C++ file that:
parses CSV text
prints the number of rows
prints each row
writes CSV text back
runs with vix runCreate a working folder
Create a small folder in your home directory:
mkdir -p ~/rix-csv-quick-start
cd ~/rix-csv-quick-start
touch csv.cppAdd the example
Open:
csv.cppAdd:
#include <rix.hpp>
#include <sstream>
#include <string>
static void print_table(const rixlib::csv::Table &table)
{
for (const auto &row : table)
{
std::ostringstream line;
for (std::size_t i = 0; i < row.size(); ++i)
{
if (i > 0)
{
line << " ";
}
line << row[i];
}
rix.debug.print(line.str());
}
}
int main()
{
const std::string input =
"name,language\n"
"Ada,C++\n"
"Gaspard,Vix\n";
const auto table = rix.csv.parse(input);
rix.debug.print("rows:", table.size());
print_table(table);
const auto output = rix.csv.write(table);
rix.debug.print("----------------------------------------");
rix.debug.print(output);
return 0;
}Run the file
Run:
vix run csv.cppIf Rix is not available yet for single-file usage:
vix install -g rix/rix
vix run csv.cppExpected output
The output should look like this:
rows: 3
name language
Ada C++
Gaspard Vix
----------------------------------------
name,language
Ada,C++
Gaspard,VixThe first part prints the parsed table.
The second part prints the CSV generated from the table.
Parse CSV text
Use:
const auto table = rix.csv.parse(input);Example:
const std::string input =
"name,language\n"
"Ada,C++\n"
"Gaspard,Vix\n";
const auto table = rix.csv.parse(input);The parsed result is a table.
A table is a list of rows.
A row is a list of fields.
table
-> row
-> fieldRead rows
You can iterate over rows:
for (const auto &row : table)
{
rix.debug.print("fields:", row.size());
}You can also access fields by index:
rix.debug.print(table[0][0]);
rix.debug.print(table[0][1]);For this input:
name,language
Ada,C++the values are:
table[0][0] -> name
table[0][1] -> language
table[1][0] -> Ada
table[1][1] -> C++Read the header
CSV does not force a special header type.
The first row can be used as the header by convention:
if (!table.empty())
{
const auto &header = table[0];
for (const auto &column : header)
{
rix.debug.print("column:", column);
}
}Then read data rows from index 1:
for (std::size_t i = 1; i < table.size(); ++i)
{
const auto &row = table[i];
if (row.size() < 2)
{
continue;
}
rix.debug.print("name:", row[0]);
rix.debug.print("language:", row[1]);
}Write CSV
Create a table:
rixlib::csv::Table table;
table.push_back({"name", "language"});
table.push_back({"Ada", "C++"});
table.push_back({"Gaspard", "Vix"});Write it:
const auto output = rix.csv.write(table);Print it:
rix.debug.print(output);Expected shape:
name,language
Ada,C++
Gaspard,VixComplete write example
#include <rix.hpp>
int main()
{
rixlib::csv::Table table;
table.push_back({"name", "project"});
table.push_back({"Ada", "Rix"});
table.push_back({"Gaspard", "Vix.cpp"});
const auto output = rix.csv.write(table);
rix.debug.print(output);
return 0;
}Run it:
vix run csv.cppUse in a Vix project
Create a Vix application:
vix new csv-app --app
cd csv-appAdd Rix:
vix add rix/rix
vix installIn vix.app, make sure Rix is listed under deps:
deps = [
"rix/rix",
]A small vix.app can look like this:
name = "csv-app"
type = "executable"
standard = "c++20"
output_dir = "bin"
sources = [
"src/main.cpp",
]
include_dirs = [
"include",
"src",
]
deps = [
"rix/rix",
]
packages = [
"vix",
]
links = [
"vix::vix",
]Then use CSV in src/main.cpp:
#include <rix.hpp>
int main()
{
const auto table = rix.csv.parse(
"name,language\n"
"Ada,C++\n");
rix.debug.print("rows:", table.size());
return 0;
}Build and run:
vix build
vix runUse only CSV with the facade
If you want the rix.* facade style but only want CSV mounted, define the feature macro before including rix.hpp:
#define RIX_ENABLE_CSV
#include <rix.hpp>
int main()
{
const auto table = rix.csv.parse("name,lang\nAda,C++\n");
return 0;
}When at least one RIX_ENABLE_* macro is defined, only selected modules are mounted.
This is useful for lighter builds.
Use the independent package
For independent usage, install:
vix add rix/csv
vix installIn vix.app:
deps = [
"rix/csv",
]Then include the independent package header:
#include <rix/csv.hpp>Use this style when a project only needs CSV and does not need the full unified Rix facade.
For most application documentation, prefer:
#include <rix.hpp>Validate external CSV
When reading CSV from external input, check the table shape before using indexes.
const auto table = rix.csv.parse(input);
if (table.empty())
{
rix.debug.eprint("CSV is empty");
return 1;
}
if (table[0].size() < 2)
{
rix.debug.eprint("expected at least two columns");
return 1;
}Check each row:
for (std::size_t i = 1; i < table.size(); ++i)
{
const auto &row = table[i];
if (row.size() < 2)
{
rix.debug.eprint("invalid row:", i);
continue;
}
rix.debug.print("name:", row[0]);
rix.debug.print("language:", row[1]);
}This avoids assuming that every row has the expected number of fields.
Common mistakes
Forgetting to install Rix
If #include <rix.hpp> is not found, install the facade package:
vix install -g rix/rixFor a project:
vix add rix/rix
vix installPutting Rix in packages
Do not put Rix registry packages in packages.
Use:
deps = [
"rix/rix",
]deps is for Vix Registry packages.
packages is for CMake package discovery.
Reading rows without checking size
Wrong:
rix.debug.print(row[0], row[1]);Better:
if (row.size() >= 2)
{
rix.debug.print(row[0], row[1]);
}Building CSV by hand
Avoid this:
output += name + "," + language + "\n";Use:
const auto output = rix.csv.write(table);The writer can handle CSV escaping rules.
What you should remember
Use the facade:
#include <rix.hpp>Parse CSV:
const auto table = rix.csv.parse(input);Read rows:
for (const auto &row : table)
{
for (const auto &field : row)
{
rix.debug.print(field);
}
}Write CSV:
const auto output = rix.csv.write(table);For a Vix project, install Rix:
vix add rix/rix
vix installand use:
deps = [
"rix/rix",
]Next step
Learn how to parse CSV data.
Next: Parse CSV