Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions include/internal/csv_writer.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -128,8 +128,8 @@ namespace internals {
csv::enable_if_t<std::is_integral<T>::value && std::is_signed<T>::value, int> = 0
>
inline std::string to_string(T value) {
return (value >= 0) ? to_string((size_t)value)
: "-" + to_string((size_t)(value * -1));
return (value >= 0) ? to_string(static_cast<unsigned long long>(value))
: "-" + to_string(0ULL - static_cast<unsigned long long>(value));
}

/** to_string() for floating point numbers */
Expand Down
36 changes: 36 additions & 0 deletions tests/test_write_csv.cpp
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
#include <fstream>
#include <limits>
#include <sstream>
#include <queue>
#include <list>
Expand Down Expand Up @@ -449,3 +450,38 @@ TEST_CASE("DataFrame - Write with Sparse Overlay", "[test_dataframe_sparse_overl
REQUIRE(result.find("Everything is fine in production") != std::string::npos); // quote updated
}
//! [DataFrame Sparse Overlay Write Example]

TEST_CASE("Signed integer conversion - extrema regression", "[test_convert_number][regression]") {
SECTION("Negative integers") {
// Negating the minimum signed value used to overflow before conversion.
const int min_int = (std::numeric_limits<int>::min)();
const long long min_long_long = (std::numeric_limits<long long>::min)();

REQUIRE(csv::internals::to_string(-1) == "-1");
REQUIRE(csv::internals::to_string(min_int) == std::to_string(min_int));
REQUIRE(csv::internals::to_string(min_long_long) == std::to_string(min_long_long));
}

SECTION("Non-negative integers") {
// Converting through size_t can truncate long long on 32-bit platforms.
const long long max_long_long = (std::numeric_limits<long long>::max)();

REQUIRE(csv::internals::to_string(0) == "0");
REQUIRE(csv::internals::to_string(0LL) == "0");
REQUIRE(csv::internals::to_string(max_long_long) == std::to_string(max_long_long));
}
}

TEST_CASE("CSV Writer - signed integer extrema regression", "[test_csv_tuple][regression]") {
// Exercise the public writer API so extrema stay intact in a mixed tuple.
const int min_int = (std::numeric_limits<int>::min)();
const long long min_long_long = (std::numeric_limits<long long>::min)();
const long long max_long_long = (std::numeric_limits<long long>::max)();
std::stringstream output, correct;
auto writer = make_csv_writer(output);

writer << std::make_tuple(min_int, min_long_long, -1, 0, max_long_long);
correct << min_int << ',' << min_long_long << ",-1,0," << max_long_long << '\n';

REQUIRE(output.str() == correct.str());
}
Loading