Skip to content

Commit

Permalink
1195 Formatter for date to have consistent Format (#1198)
Browse files Browse the repository at this point in the history
- Formatter to print date objects

Co-authored-by: reneSchm <49305466+reneSchm@users.noreply.github.com>
  • Loading branch information
HenrZu and reneSchm authored Feb 17, 2025
1 parent edb2f59 commit 040d985
Show file tree
Hide file tree
Showing 6 changed files with 104 additions and 40 deletions.
32 changes: 29 additions & 3 deletions cpp/memilio/utils/date.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#define EPI_UTILS_DATE_H

#include "memilio/io/io.h"
#include "memilio/utils/logging.h"
#include <string>
#include <iostream>
#include <tuple>
Expand Down Expand Up @@ -106,11 +107,27 @@ struct Date {
//@}

/**
* gtest printer.
* Formats the date into a string in ISO 8601 format (YYYY-MM-DD).
* @return A string representing the date in ISO 8601 format.
*/
friend void PrintTo(const Date& self, std::ostream* os)
std::string to_iso_string() const
{
*os << self.year << "." << self.month << "." << self.day;
// the format after ":" reads as
// 1) '0' -> fill with zeros
// 2) '>' -> align text right
// 3) '4' or '2' -> specify the width (4 for year, 2 for month and day)
return fmt::format("{:0>4}-{:0>2}-{:0>2}", year, month, day);
}

/**
* Overload for stream operator to use the ISO 8601 format.
* @param os Output stream.
* @param date Date to output.
* @return Reference to the output stream.
*/
friend std::ostream& operator<<(std::ostream& os, const Date& date)
{
return os << date.to_iso_string();
}

/**
Expand Down Expand Up @@ -156,6 +173,15 @@ struct Date {
static constexpr std::array<int, 12> month_lengths_leap_year = {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
};

/**
* @brief Format date objects using the ISO notation for logging with spdlog.
* @param d date object.
*/
inline std::string format_as(const mio::Date& d)
{
return d.to_iso_string();
}

/**
* @brief Computes the length of a month for a given date.
* @param date date.
Expand Down
14 changes: 4 additions & 10 deletions cpp/models/ide_secir/parameters_io.h
Original file line number Diff line number Diff line change
Expand Up @@ -288,17 +288,11 @@ IOResult<void> set_initial_flows(Model& model, const ScalarType dt, const std::v
return a.date < b.date;
});
auto min_date = min_date_entry->date;

std::string min_date_string =
std::to_string(min_date.day) + "." + std::to_string(min_date.month) + "." + std::to_string(min_date.year);
// Get first date that is needed.
mio::Date min_offset_date = offset_date_by_days(date, int(min_offset_needed));
std::string min_offset_date_string = std::to_string(min_offset_date.day) + "." +
std::to_string(min_offset_date.month) + "." +
std::to_string(min_offset_date.year);
log_warning("RKI data is needed from " + min_offset_date_string +
" to compute initial values. RKI data is only available from " + min_date_string +
". Missing dates were set to 0.");
mio::Date min_offset_date = offset_date_by_days(date, int(min_offset_needed));
log_warning("RKI data is needed from {} to compute initial values. RKI data is only available from {}. Missing "
"dates were set to 0.",
min_offset_date, min_date);
}

//--- Calculate the flows "after" InfectedNoSymptomsToInfectedSymptoms (that were set above using rki_data). ---
Expand Down
10 changes: 5 additions & 5 deletions cpp/models/ode_secir/parameters_io.h
Original file line number Diff line number Diff line change
Expand Up @@ -143,9 +143,8 @@ IOResult<void> set_confirmed_cases_data(std::vector<Model<FP>>& model, std::vect
}
}
else {
log_warning("No infections reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[node]) + ". Population data has not been set.");
log_warning("No infections reported on date {} for region {}. Population data has not been set.", date,
region[node]);
}
}
return success();
Expand Down Expand Up @@ -196,8 +195,9 @@ IOResult<void> set_divi_data(std::vector<Model<FP>>& model, const std::string& p
{
// DIVI dataset will no longer be updated from CW29 2024 on.
if (!is_divi_data_available(date)) {
log_warning("No DIVI data available for date: {}-{}-{}", date.year, date.month, date.day,
". ICU compartment will be set based on Case data.");
log_warning("No DIVI data available for date: {}. "
"ICU compartment will be set based on Case data.",
date);
return success();
}
std::vector<double> sum_mu_I_U(vregion.size(), 0);
Expand Down
23 changes: 12 additions & 11 deletions cpp/models/ode_secirts/parameters_io.h
Original file line number Diff line number Diff line change
Expand Up @@ -421,9 +421,9 @@ set_confirmed_cases_data(std::vector<Model>& model, const std::vector<ConfirmedC
}
}
if (std::accumulate(num_InfectedSymptoms[county].begin(), num_InfectedSymptoms[county].end(), 0.0) == 0) {
log_warning("No infections for unvaccinated reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[county]) + ". Population data has not been set.");
log_warning(
"No infections for unvaccinated reported on date {} for region {}. Population data has not been set.",
date, region[county]);
}
}

Expand Down Expand Up @@ -478,9 +478,9 @@ set_confirmed_cases_data(std::vector<Model>& model, const std::vector<ConfirmedC
num_timm1[county][i];
}
if (std::accumulate(num_InfectedSymptoms[county].begin(), num_InfectedSymptoms[county].end(), 0.0) == 0) {
log_warning("No infections for partially vaccinated reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[county]) + ". Population data has not been set.");
log_warning("No infections for partially vaccinated reported on date {} for region {}. "
"Population data has not been set.",
date, region[county]);
}
}

Expand Down Expand Up @@ -536,9 +536,9 @@ set_confirmed_cases_data(std::vector<Model>& model, const std::vector<ConfirmedC
num_timm2[county][i];
}
if (std::accumulate(num_InfectedSymptoms[county].begin(), num_InfectedSymptoms[county].end(), 0.0) == 0) {
log_warning("No infections for vaccinated reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[county]) + ". Population data has not been set.");
log_warning("No infections for vaccinated reported on date {} for region {}. "
"Population data has not been set.",
date, region[county]);
}
}
return success();
Expand Down Expand Up @@ -663,8 +663,9 @@ IOResult<void> set_divi_data(std::vector<Model>& model, const std::string& path,
{
// DIVI dataset will no longer be updated from CW29 2024 on.
if (!is_divi_data_available(date)) {
log_warning("No DIVI data available for date: {}-{}-{}", date.year, date.month, date.day,
". ICU compartment will be set based on Case data.");
log_warning("No DIVI data available for date: {}. "
"ICU compartment will be set based on Case data.",
date);
return success();
}
std::vector<FP> sum_mu_I_U(vregion.size(), 0);
Expand Down
23 changes: 12 additions & 11 deletions cpp/models/ode_secirvvs/parameters_io.h
Original file line number Diff line number Diff line change
Expand Up @@ -196,9 +196,9 @@ IOResult<void> set_confirmed_cases_data(std::vector<Model>& model,

// }
if (std::accumulate(num_InfectedSymptoms[county].begin(), num_InfectedSymptoms[county].end(), 0.0) == 0) {
log_warning("No infections for unvaccinated reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[county]) + ". Population data has not been set.");
log_warning(
"No infections for unvaccinated reported on date {} for region {}. Population data has not been set.",
date, region[county]);
}
}

Expand Down Expand Up @@ -284,9 +284,9 @@ IOResult<void> set_confirmed_cases_data(std::vector<Model>& model,
}
// }
if (std::accumulate(num_InfectedSymptoms[county].begin(), num_InfectedSymptoms[county].end(), 0.0) == 0) {
log_warning("No infections for partially vaccinated reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[county]) + ". Population data has not been set.");
log_warning("No infections for partially vaccinated reported on date {} for region {}. "
"Population data has not been set.",
date, region[county]);
}
}

Expand Down Expand Up @@ -370,9 +370,9 @@ IOResult<void> set_confirmed_cases_data(std::vector<Model>& model,
}
}
if (std::accumulate(num_InfectedSymptoms[county].begin(), num_InfectedSymptoms[county].end(), 0.0) == 0) {
log_warning("No infections for vaccinated reported on date " + std::to_string(date.year) + "-" +
std::to_string(date.month) + "-" + std::to_string(date.day) + " for region " +
std::to_string(region[county]) + ". Population data has not been set.");
log_warning("No infections for vaccinated reported on date {} for region {}. "
"Population data has not been set.",
date, region[county]);
}
}

Expand Down Expand Up @@ -428,8 +428,9 @@ IOResult<void> set_divi_data(std::vector<Model>& model, const std::string& path,
{
// DIVI dataset will no longer be updated from CW29 2024 on.
if (!is_divi_data_available(date)) {
log_warning("No DIVI data available for date: {}-{}-{}", date.year, date.month, date.day,
". ICU compartment will be set based on Case data.");
log_warning("No DIVI data available for date: {}. "
"ICU compartment will be set based on Case data.",
date);
return success();
}
std::vector<double> sum_mu_I_U(vregion.size(), 0);
Expand Down
42 changes: 42 additions & 0 deletions cpp/tests/test_date.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -170,3 +170,45 @@ TEST(TestDate, getOffset)
offset = mio::get_offset_in_days({2019, 11, 30}, {2020, 11, 30});
EXPECT_EQ(offset, -366);
}

TEST(TestDate, toIsoString)
{
EXPECT_EQ(mio::Date(2020, 9, 2).to_iso_string(), "2020-09-02");
EXPECT_EQ(mio::Date(2021, 8, 30).to_iso_string(), "2021-08-30");
EXPECT_EQ(mio::Date(2021, 3, 4).to_iso_string(), "2021-03-04");
EXPECT_EQ(mio::Date(2021, 1, 1).to_iso_string(), "2021-01-01");
EXPECT_EQ(mio::Date(2020, 2, 29).to_iso_string(), "2020-02-29");
}

TEST(TestDate, streamOutput)
{
std::ostringstream oss1;
oss1 << mio::Date(2020, 9, 2);
EXPECT_EQ(oss1.str(), "2020-09-02");

std::ostringstream oss2;
oss2 << mio::Date(2021, 8, 30);
EXPECT_EQ(oss2.str(), "2021-08-30");

std::ostringstream oss3;
oss3 << mio::Date(2021, 3, 4);
EXPECT_EQ(oss3.str(), "2021-03-04");

std::ostringstream oss4;
oss4 << mio::Date(2021, 1, 1);
EXPECT_EQ(oss4.str(), "2021-01-01");

std::ostringstream oss5;
oss5 << mio::Date(2020, 2, 29);
EXPECT_EQ(oss5.str(), "2020-02-29");
}

TEST(TestDate, formatViaFmt)
{
EXPECT_EQ(fmt::format("{}", mio::Date(2020, 9, 2)), "2020-09-02");
EXPECT_EQ(fmt::format("{}", mio::Date(2021, 8, 30)), "2021-08-30");
EXPECT_EQ(fmt::format("{}", mio::Date(2021, 1, 1)), "2021-01-01");
EXPECT_EQ(fmt::format("{}", mio::Date(2020, 2, 29)), "2020-02-29");
EXPECT_EQ(fmt::format("{}", mio::Date(2021, 3, 4)), "2021-03-04");
EXPECT_EQ(fmt::format("Todays date is: {}", mio::Date(2021, 12, 31)), "Todays date is: 2021-12-31");
}

0 comments on commit 040d985

Please sign in to comment.