DatetimeIndexOpsMixin ===================== .. cpp:class:: pandas::DatetimeIndexOpsMixin Mixin class providing shared functionality. Example ------- .. code-block:: cpp #include using namespace pandas; // Create DatetimeIndexOpsMixin DatetimeIndexOpsMixin idx({1, 2, 3}, "my_index"); size_t len = idx.size(); Constructors ------------ .. list-table:: :widths: 55 25 20 :header-rows: 1 * - Signature - Location - Example * - ``explicit DatetimeIndexOpsMixin(const ArrayType& array, const std::optional& name = std::nullopt, bool copy = false)`` - pd_datetime_index_ops_mixin.h:140 - * - ``explicit DatetimeIndexOpsMixin(ArrayType&& array, const std::optional& name = std::nullopt)`` - pd_datetime_index_ops_mixin.h:150 - * - ``DatetimeIndexOpsMixin(const DatetimeIndexOpsMixin& other)`` - pd_datetime_index_ops_mixin.h:159 - * - ``DatetimeIndexOpsMixin(DatetimeIndexOpsMixin&& other) noexcept`` - pd_datetime_index_ops_mixin.h:167 - Indexing / Selection -------------------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``std::optional get_freq() const override`` - std::optional - pd_datetime_index_ops_mixin.h:216 - :ref:`View ` Data Manipulation ----------------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``DatetimeIndexOpsMixin rename(const std::optional& new_name) const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1474 - :ref:`View ` Statistics ---------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``std::optional mean(std::optional axis = std::nullopt, bool skipna = true) const`` - std::optional - pd_datetime_index_ops_mixin.h:1348 - :ref:`View ` * - ``IntegerArray minute() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:692 - :ref:`View ` Time Series ----------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``DatetimeIndexOpsMixin asfreq(const std::string& freq, const std::string& how = "start") const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1273 - :ref:`View ` * - ``DatetimeIndexOpsMixin shift(int64_t periods, const std::optional& freq = std::nullopt) const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:423 - :ref:`View ` * - ``ArrayType shifted(result)`` - ArrayType - pd_datetime_index_ops_mixin.h:455 - * - ``ArrayType shifted(result)`` - ArrayType - pd_datetime_index_ops_mixin.h:477 - * - ``PeriodArray to_period(const std::string& freq) const`` - PeriodArray - pd_datetime_index_ops_mixin.h:1306 - :ref:`View ` * - ``DatetimeArray to_timestamp(const std::string& how = "start") const`` - DatetimeArray - pd_datetime_index_ops_mixin.h:1292 - :ref:`View ` * - ``DatetimeIndexOpsMixin tz_convert(const std::string& tz, const std::string& tz_display = "") const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1213 - :ref:`View ` * - ``DatetimeIndexOpsMixin tz_localize(const std::string& tz, const std::string& ambiguous = "raise", const std::string& nonexistent = "raise", const std::string& tz_display = "") const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1192 - :ref:`View ` I/O --- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``std::string to_string() const override`` - std::string - pd_datetime_index_ops_mixin.h:1413 - :ref:`View ` Conversion ---------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``DatetimeIndexOpsMixin copy() const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1467 - :ref:`View ` Type Checking ------------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``BooleanArray is_leap_year() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1116 - :ref:`View ` * - ``BooleanArray is_month_end() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:962 - :ref:`View ` * - ``BooleanArray is_month_start() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:934 - :ref:`View ` * - ``BooleanArray is_negative() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1146 - :ref:`View ` * - ``BooleanArray is_positive() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1134 - :ref:`View ` * - ``BooleanArray is_quarter_end() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1024 - :ref:`View ` * - ``BooleanArray is_quarter_start() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:992 - :ref:`View ` * - ``BooleanArray is_year_end() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1087 - :ref:`View ` * - ``BooleanArray is_year_start() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1058 - :ref:`View ` * - ``BooleanArray is_zero() const`` - BooleanArray - pd_datetime_index_ops_mixin.h:1158 - :ref:`View ` Other Methods ------------- .. list-table:: :widths: 40 20 15 25 :header-rows: 1 * - Signature - Return Type - Location - Example * - ``DatetimeIndexOpsMixin ceil(const std::string& freq) const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:361 - :ref:`View ` * - ``ArrayType ceiled(result)`` - ArrayType - pd_datetime_index_ops_mixin.h:390 - * - ``std::unique_ptr clone() const override`` - std::unique_ptr - pd_datetime_index_ops_mixin.h:1402 - :ref:`View ` * - ``IntegerArray day() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:666 - :ref:`View ` * - ``std::vector day_name( const std::optional& locale = std::nullopt) const`` - std::vector - pd_datetime_index_ops_mixin.h:600 - :ref:`View ` * - ``IntegerArray dayofweek() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:784 - :ref:`View ` * - ``IntegerArray dayofyear() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:803 - :ref:`View ` * - ``DatetimeIndexOpsMixin floor(const std::string& freq) const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:317 - :ref:`View ` * - ``ArrayType floored(result)`` - ArrayType - pd_datetime_index_ops_mixin.h:346 - * - ``static std::string format_datetime_strftime(const numpy::datetime64& val, const std::string& format)`` - static std::string - pd_datetime_index_ops_mixin.h:1520 - * - ``static std::string format_period_strftime(numpy::int64 ordinal, const std::string& format, PeriodFrequency freq)`` - static std::string - pd_datetime_index_ops_mixin.h:1546 - * - ``std::optional freq() const`` - std::optional - pd_datetime_index_ops_mixin.h:205 - :ref:`View ` * - ``std::string freqstr() const`` - std::string - pd_datetime_index_ops_mixin.h:228 - :ref:`View ` * - ``gmtime_r(&secs, &tm_time)`` - - pd_datetime_index_ops_mixin.h:1535 - * - ``gmtime_s(&tm_time, &secs)`` - - pd_datetime_index_ops_mixin.h:1533 - * - ``IntegerArray hour() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:678 - :ref:`View ` * - ``std::optional inferred_freq() const`` - std::optional - pd_datetime_index_ops_mixin.h:241 - * - ``IntegerArray microsecond() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:720 - :ref:`View ` * - ``IntegerArray month() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:654 - :ref:`View ` * - ``std::vector month_name( const std::optional& locale = std::nullopt) const`` - std::vector - pd_datetime_index_ops_mixin.h:553 - :ref:`View ` * - ``IntegerArray nanosecond() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:753 - :ref:`View ` * - ``DatetimeIndexOpsMixin normalize() const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1177 - :ref:`View ` * - ``static int64_t parse_freq_to_nanoseconds(const std::string& freq)`` - static int64_t - pd_datetime_index_ops_mixin.h:1495 - * - ``static int64_t period_ordinal_to_nanoseconds(numpy::int64 ordinal, PeriodFrequency freq)`` - static int64_t - pd_datetime_index_ops_mixin.h:1561 - * - ``IntegerArray quarter() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:815 - :ref:`View ` * - ``DatetimeIndexOpsMixin result(std::move(localized), this->name())`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1198 - :ref:`View ` * - ``DatetimeIndexOpsMixin result(std::move(converted), this->name())`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1216 - :ref:`View ` * - ``DatetimeIndexOpsMixin result(\*this)`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:1475 - :ref:`View ` * - ``DatetimeIndexOpsMixin round(const std::string& freq, int decimals = 0) const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:273 - :ref:`View ` * - ``ArrayType rounded(result)`` - ArrayType - pd_datetime_index_ops_mixin.h:302 - * - ``IntegerArray second() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:706 - :ref:`View ` * - ``void set_freq(const std::optional& freq)`` - void - pd_datetime_index_ops_mixin.h:252 - :ref:`View ` * - ``DatetimeIndexOpsMixin snap(const std::string& freq = "S") const`` - DatetimeIndexOpsMixin - pd_datetime_index_ops_mixin.h:405 - :ref:`View ` * - ``std::vector strftime(const std::string& date_format) const`` - std::vector - pd_datetime_index_ops_mixin.h:501 - :ref:`View ` * - ``IntegerArray td_days() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:870 - :ref:`View ` * - ``IntegerArray td_microseconds() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:894 - * - ``IntegerArray td_nanoseconds() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:906 - * - ``IntegerArray td_seconds() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:882 - * - ``FloatingArray total_seconds() const`` - FloatingArray - pd_datetime_index_ops_mixin.h:918 - :ref:`View ` * - ``IndexTypeId type_id() const override`` - IndexTypeId - pd_datetime_index_ops_mixin.h:1406 - :ref:`View ` * - ``std::string tz() const`` - std::string - pd_datetime_index_ops_mixin.h:1228 - :ref:`View ` * - ``bool tz_aware() const`` - bool - pd_datetime_index_ops_mixin.h:1254 - :ref:`View ` * - ``std::string tz_display() const`` - std::string - pd_datetime_index_ops_mixin.h:1241 - * - ``IntegerArray week() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:827 - :ref:`View ` * - ``IntegerArray weekday() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:795 - :ref:`View ` * - ``IntegerArray weekofyear() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:858 - * - ``IntegerArray year() const`` - IntegerArray - pd_datetime_index_ops_mixin.h:642 - :ref:`View ` Code Examples ------------- The following examples are extracted from the test suite. .. _example-datetimeindexopsmixin-get_freq-0: .. dropdown:: get_freq (pd_test_2_all.cpp:20397) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 20387 :emphasize-lines: 11 std::vector ts = { numpy::datetime64(0LL, numpy::DateTimeUnit::Day), numpy::datetime64(1LL, numpy::DateTimeUnit::Day), numpy::datetime64(2LL, numpy::DateTimeUnit::Day) }; auto dt_idx = std::make_unique(ts); dt_idx->set_freq(std::string("D")); df.set_index(std::move(dt_idx)); auto s = df.extract_column_as_numeric_series("val"); check(s.get_freq().has_value(), "freq propagated"); if (s.get_freq().has_value()) { check(s.get_freq().value() == "D", "freq value D"); } // Test MultiIndex propagation pandas::DataFrame df2; std::vector vals2 = {10.0, 20.0}; df2.insert(0, "A", std::make_unique>(vals2, "A"), true); std::vector> arrays = {{"x", "y"}, {"1", "2"}}; std::vector> names = {std::string("first"), std::string("second")}; .. _example-datetimeindexopsmixin-rename-1: .. dropdown:: rename (pd_test_1_all.cpp:5816) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 5806 :emphasize-lines: 11 std::cout << " -> tests passed" << std::endl; } void pd_test_categorical_index_rename() { std::cout << "========= rename ======================================"; pandas::CategoricalArray arr({"x", "y"}); pandas::CategoricalIndex idx(arr, "old_name"); pandas::CategoricalIndex renamed = idx.rename("new_name"); bool passed = (renamed.name().has_value() && *renamed.name() == "new_name" && renamed.size() == idx.size() && renamed.categories() == idx.categories()); if (!passed) { std::cout << " [FAIL] : in pd_test_categorical_index_rename()" << std::endl; throw std::runtime_error("pd_test_categorical_index_rename failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-mean-2: .. dropdown:: mean (pd_test_1_all.cpp:282) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 272 :emphasize-lines: 11 std::optional(true), std::optional(true) }); auto s = arr.sum(); if (!s.has_value() || s.value() != 3) { std::cout << " [FAIL] : in pd_test_boolean_array_reductions() : sum should be 3" << std::endl; throw std::runtime_error("pd_test_boolean_array_reductions failed: sum"); } auto m = arr.mean(); if (!m.has_value() || std::abs(m.value() - 0.75) > 0.001) { std::cout << " [FAIL] : in pd_test_boolean_array_reductions() : mean should be 0.75" << std::endl; throw std::runtime_error("pd_test_boolean_array_reductions failed: mean"); } std::cout << " -> tests passed" << std::endl; } void pd_test_boolean_array_dtype() { std::cout << "========= BooleanArray: dtype ======================= "; .. _example-datetimeindexopsmixin-minute-3: .. dropdown:: minute (pd_test_1_all.cpp:7505) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 7495 :emphasize-lines: 11 std::cout << "========= minute property ============================="; std::vector> values = { make_dt(0), // Minute 0 make_dt(30 * NS_PER_MIN), // Minute 30 make_dt(59 * NS_PER_MIN) // Minute 59 }; pandas::DatetimeArray arr(values); pandas::DatetimeIndex idx(arr); auto minutes = idx.minute(); bool passed = (minutes.size() == 3); auto m0 = minutes[0]; auto m1 = minutes[1]; auto m2 = minutes[2]; passed = passed && m0.has_value() && *m0 == 0; passed = passed && m1.has_value() && *m1 == 30; passed = passed && m2.has_value() && *m2 == 59; if (!passed) { .. _example-datetimeindexopsmixin-asfreq-4: .. dropdown:: asfreq (pd_test_1_all.cpp:2869) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 2859 :emphasize-lines: 11 std::cout << "========= PeriodArray: asfreq ======================= "; // Monthly to quarterly pandas::PeriodArray arr_m(std::vector{ "2024-01", "2024-04", "2024-07", "NaT" }, "M"); auto arr_q = arr_m.asfreq("Q"); if (arr_q.size() != 4) { std::cout << " [FAIL] : asfreq size should be 4" << std::endl; throw std::runtime_error("pd_test_period_array_asfreq failed: size"); } if (arr_q.freqstr() != "Q") { std::cout << " [FAIL] : asfreq freqstr should be 'Q'" << std::endl; throw std::runtime_error("pd_test_period_array_asfreq failed: freqstr"); } // Check NaT is preserved .. _example-datetimeindexopsmixin-shift-5: .. dropdown:: shift (pd_test_1_all.cpp:5188) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 5178 :emphasize-lines: 11 // First element should be NaN val = d["A"].get_value_str(0); passed = std::isnan(std::stod(val)); if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_dataframe_diff_shift() : diff NaN failed" << std::endl; throw std::runtime_error("pd_test_arithmetic_dataframe_diff_shift failed: diff NaN failed"); } // shift: [NaN, 1, 3, 6] auto s = df.shift(); val = s["A"].get_value_str(1); passed = std::abs(std::stod(val) - 1.0) < 0.001; if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_dataframe_diff_shift() : shift failed" << std::endl; throw std::runtime_error("pd_test_arithmetic_dataframe_diff_shift failed: shift failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-to_period-6: .. dropdown:: to_period (pd_test_2_all.cpp:14554) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 14544 :emphasize-lines: 11 std::cout << "====================================== [OK] pd_test_to_parquet test suite ========================" << std::endl; return 0; } } // namespace dataframe_tests // ------------------- pd_test_to_parquet.cpp (end) ----------------------------- // ------------------- pd_test_to_period.cpp (start) ----------------------------- // dataframe_tests/pd_test_to_period.cpp // Test suite for DataFrame.to_period() method #include #include #include #include #include #include "../pandas/pd_dataframe.h" // CRITICAL: No using namespace directives .. _example-datetimeindexopsmixin-to_timestamp-7: .. dropdown:: to_timestamp (pd_test_1_all.cpp:2830) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 2820 :emphasize-lines: 11 void pd_test_period_array_to_timestamp() { std::cout << "========= PeriodArray: to_timestamp ======================= "; pandas::PeriodArray arr(std::vector{ "2024-01", "2024-06", "NaT" }, "M"); // to_timestamp with start auto ts_start = arr.to_timestamp("start"); if (ts_start.size() != 3) { std::cout << " [FAIL] : to_timestamp size should be 3" << std::endl; throw std::runtime_error("pd_test_period_array_to_timestamp failed: size"); } auto ts0 = ts_start[0]; if (!ts0.has_value()) { std::cout << " [FAIL] : ts_start[0] should have value" << std::endl; throw std::runtime_error("pd_test_period_array_to_timestamp failed: ts_start[0]"); } .. _example-datetimeindexopsmixin-tz_convert-8: .. dropdown:: tz_convert (pd_test_2_all.cpp:17874) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 17864 :emphasize-lines: 11 std::cout << "====================================== [OK] pd_test_transform test suite ========================== " << std::endl; return 0; } } // namespace dataframe_tests // ------------------- pd_test_transform.cpp (end) ----------------------------- // ------------------- pd_test_tz_convert.cpp (start) ----------------------------- // dataframe_tests/pd_test_tz_convert.cpp // Test for DataFrame.tz_convert() method #include #include #include #include "../pandas/pd_dataframe.h" namespace dataframe_tests { namespace dataframe_tests_tz_convert { void pd_test_tz_convert_basic() { .. _example-datetimeindexopsmixin-tz_localize-9: .. dropdown:: tz_localize (pd_test_1_all.cpp:1431) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1421 :emphasize-lines: 11 "2023-06-15" }); // Initially should be timezone-naive if (arr.is_tz_aware()) { std::cout << " [FAIL] : array should be timezone-naive initially" << std::endl; throw std::runtime_error("pd_test_datetime_array_timezone failed: naive"); } // Localize to UTC auto localized = arr.tz_localize("UTC"); if (!localized.is_tz_aware()) { std::cout << " [FAIL] : localized array should be timezone-aware" << std::endl; throw std::runtime_error("pd_test_datetime_array_timezone failed: localize"); } // Verify timezone name in dtype auto dt = localized.dtype(); if (!dt.is_tz_aware()) { std::cout << " [FAIL] : dtype should be timezone-aware" << std::endl; throw std::runtime_error("pd_test_datetime_array_timezone failed: dtype tz"); .. _example-datetimeindexopsmixin-to_string-10: .. dropdown:: to_string (pd_test_1_all.cpp:2693) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 2683 :emphasize-lines: 11 pandas::PeriodArray arr_m(std::vector{ "2020-01", "NaT", "2025-06" }, "M"); // Year auto years = arr_m.year(); auto y0 = years[0]; if (!y0.has_value() || y0.value() != 2020) { std::cout << " [FAIL] : year[0] should be 2020, got " << (y0.has_value() ? std::to_string(y0.value()) : "NA") << std::endl; throw std::runtime_error("pd_test_period_array_year_month_quarter failed: year[0]"); } auto y1 = years[1]; if (y1.has_value()) { std::cout << " [FAIL] : year[1] should be NA (NaT)" << std::endl; throw std::runtime_error("pd_test_period_array_year_month_quarter failed: year[1] should be NA"); } auto y2 = years[2]; .. _example-datetimeindexopsmixin-copy-11: .. dropdown:: copy (pd_test_1_all.cpp:5798) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 5788 :emphasize-lines: 11 // ============================================================================ // Copy/Rename Tests // ============================================================================ void pd_test_categorical_index_copy() { std::cout << "========= copy ========================================"; pandas::CategoricalArray arr({"a", "b", "c"}); pandas::CategoricalIndex idx(arr, "original"); pandas::CategoricalIndex copied = idx.copy(); bool passed = (copied.size() == idx.size() && copied.name() == idx.name() && copied.categories() == idx.categories() && copied.ordered() == idx.ordered()); if (!passed) { std::cout << " [FAIL] : in pd_test_categorical_index_copy()" << std::endl; throw std::runtime_error("pd_test_categorical_index_copy failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-is_leap_year-12: .. dropdown:: is_leap_year (pd_test_1_all.cpp:1280) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1270 :emphasize-lines: 11 } // is_month_end auto me = arr.is_month_end(); if (!me[1].has_value() || !me[1].value()) { std::cout << " [FAIL] : 2023-03-31 should be month end" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: month end"); } // is_leap_year auto ly = arr.is_leap_year(); if (!ly[2].has_value() || !ly[2].value()) { std::cout << " [FAIL] : 2024 should be leap year" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: leap year"); } if (!ly[0].has_value() || ly[0].value()) { std::cout << " [FAIL] : 2023 should not be leap year" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: not leap year"); } std::cout << " -> tests passed" << std::endl; .. _example-datetimeindexopsmixin-is_month_end-13: .. dropdown:: is_month_end (pd_test_1_all.cpp:1273) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1263 :emphasize-lines: 11 } // is_month_start auto ms = arr.is_month_start(); if (!ms[0].has_value() || !ms[0].value()) { std::cout << " [FAIL] : 2023-01-01 should be month start" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: month start"); } // is_month_end auto me = arr.is_month_end(); if (!me[1].has_value() || !me[1].value()) { std::cout << " [FAIL] : 2023-03-31 should be month end" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: month end"); } // is_leap_year auto ly = arr.is_leap_year(); if (!ly[2].has_value() || !ly[2].value()) { std::cout << " [FAIL] : 2024 should be leap year" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: leap year"); .. _example-datetimeindexopsmixin-is_month_start-14: .. dropdown:: is_month_start (pd_test_1_all.cpp:1266) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1256 :emphasize-lines: 11 if (!ys[0].has_value() || !ys[0].value()) { std::cout << " [FAIL] : 2023-01-01 should be year start" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: year start"); } if (!ys[1].has_value() || ys[1].value()) { std::cout << " [FAIL] : 2023-03-31 should not be year start" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: not year start"); } // is_month_start auto ms = arr.is_month_start(); if (!ms[0].has_value() || !ms[0].value()) { std::cout << " [FAIL] : 2023-01-01 should be month start" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: month start"); } // is_month_end auto me = arr.is_month_end(); if (!me[1].has_value() || !me[1].value()) { std::cout << " [FAIL] : 2023-03-31 should be month end" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: month end"); .. _example-datetimeindexopsmixin-is_negative-15: .. dropdown:: is_negative (pd_test_1_all.cpp:4269) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 4259 :emphasize-lines: 11 if (!pos[0].has_value() || !pos[0].value()) { std::cout << " [FAIL] : 1 day should be positive" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: is_positive"); } if (!pos[1].has_value() || pos[1].value()) { std::cout << " [FAIL] : -5 hours should not be positive" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: not positive"); } // is_negative auto neg = arr.is_negative(); if (!neg[1].has_value() || !neg[1].value()) { std::cout << " [FAIL] : -5 hours should be negative" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: is_negative"); } if (!neg[0].has_value() || neg[0].value()) { std::cout << " [FAIL] : 1 day should not be negative" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: not negative"); } // is_zero .. _example-datetimeindexopsmixin-is_positive-16: .. dropdown:: is_positive (pd_test_1_all.cpp:4258) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 4248 :emphasize-lines: 11 std::cout << "========= TimedeltaArray: boolean properties ======================= "; pandas::TimedeltaArray arr({ std::optional(numpy::timedelta64(1, numpy::DateTimeUnit::Day)), // positive std::optional(numpy::timedelta64(-5, numpy::DateTimeUnit::Hour)), // negative std::optional(numpy::timedelta64(0, numpy::DateTimeUnit::Second)), // zero std::nullopt }); // is_positive auto pos = arr.is_positive(); if (!pos[0].has_value() || !pos[0].value()) { std::cout << " [FAIL] : 1 day should be positive" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: is_positive"); } if (!pos[1].has_value() || pos[1].value()) { std::cout << " [FAIL] : -5 hours should not be positive" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: not positive"); } // is_negative .. _example-datetimeindexopsmixin-is_quarter_end-17: .. dropdown:: is_quarter_end (pd_test_3_all.cpp:25056) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 25046 :emphasize-lines: 11 }; pandas::Series s(dates); pandas::DatetimeProperties> dt(s); if (dt.has_nat()) throw std::runtime_error("has_nat should be false for clean series"); auto ms = dt.is_month_start(); if (ms[0] != true || ms[1] != false) throw std::runtime_error("is_month_start failed"); auto me = dt.is_month_end(); if (me[1] != true || me[0] != false) throw std::runtime_error("is_month_end failed"); auto qs = dt.is_quarter_start(); if (qs[0] != true || qs[1] != false) throw std::runtime_error("is_quarter_start failed"); auto qe = dt.is_quarter_end(); if (qe[2] != true || qe[0] != false) throw std::runtime_error("is_quarter_end failed"); auto ys = dt.is_year_start(); if (ys[0] != true || ys[1] != false) throw std::runtime_error("is_year_start failed"); auto ye = dt.is_year_end(); if (ye[3] != true || ye[0] != false) throw std::runtime_error("is_year_end failed"); std::cout << " -> tests passed" << std::endl; } void pd_test_dt_bool_na_with_nat() { std::cout << "========= pd_test_dt_bool_na: series with NaT =========="; .. _example-datetimeindexopsmixin-is_quarter_start-18: .. dropdown:: is_quarter_start (pd_test_3_all.cpp:25054) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 25044 :emphasize-lines: 11 numpy::datetime64("2024-03-31"), numpy::datetime64("2024-12-31") }; pandas::Series s(dates); pandas::DatetimeProperties> dt(s); if (dt.has_nat()) throw std::runtime_error("has_nat should be false for clean series"); auto ms = dt.is_month_start(); if (ms[0] != true || ms[1] != false) throw std::runtime_error("is_month_start failed"); auto me = dt.is_month_end(); if (me[1] != true || me[0] != false) throw std::runtime_error("is_month_end failed"); auto qs = dt.is_quarter_start(); if (qs[0] != true || qs[1] != false) throw std::runtime_error("is_quarter_start failed"); auto qe = dt.is_quarter_end(); if (qe[2] != true || qe[0] != false) throw std::runtime_error("is_quarter_end failed"); auto ys = dt.is_year_start(); if (ys[0] != true || ys[1] != false) throw std::runtime_error("is_year_start failed"); auto ye = dt.is_year_end(); if (ye[3] != true || ye[0] != false) throw std::runtime_error("is_year_end failed"); std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-is_year_end-19: .. dropdown:: is_year_end (pd_test_3_all.cpp:25060) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 25050 :emphasize-lines: 11 auto ms = dt.is_month_start(); if (ms[0] != true || ms[1] != false) throw std::runtime_error("is_month_start failed"); auto me = dt.is_month_end(); if (me[1] != true || me[0] != false) throw std::runtime_error("is_month_end failed"); auto qs = dt.is_quarter_start(); if (qs[0] != true || qs[1] != false) throw std::runtime_error("is_quarter_start failed"); auto qe = dt.is_quarter_end(); if (qe[2] != true || qe[0] != false) throw std::runtime_error("is_quarter_end failed"); auto ys = dt.is_year_start(); if (ys[0] != true || ys[1] != false) throw std::runtime_error("is_year_start failed"); auto ye = dt.is_year_end(); if (ye[3] != true || ye[0] != false) throw std::runtime_error("is_year_end failed"); std::cout << " -> tests passed" << std::endl; } void pd_test_dt_bool_na_with_nat() { std::cout << "========= pd_test_dt_bool_na: series with NaT =========="; std::vector dates = { numpy::datetime64("2024-01-01"), numpy::datetime64(), // NaT numpy::datetime64("2024-12-31") .. _example-datetimeindexopsmixin-is_year_start-20: .. dropdown:: is_year_start (pd_test_1_all.cpp:1255) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1245 :emphasize-lines: 11 std::cout << "========= DatetimeArray: boolean properties ======================= "; pandas::DatetimeArray arr(std::vector{ "2023-01-01", // year start, month start "2023-03-31", // quarter end, month end "2024-02-29", // leap year (2024 is leap year) "2023-12-31" // year end, month end }); // is_year_start auto ys = arr.is_year_start(); if (!ys[0].has_value() || !ys[0].value()) { std::cout << " [FAIL] : 2023-01-01 should be year start" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: year start"); } if (!ys[1].has_value() || ys[1].value()) { std::cout << " [FAIL] : 2023-03-31 should not be year start" << std::endl; throw std::runtime_error("pd_test_datetime_array_boolean_props failed: not year start"); } // is_month_start .. _example-datetimeindexopsmixin-is_zero-21: .. dropdown:: is_zero (pd_test_1_all.cpp:4280) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 4270 :emphasize-lines: 11 if (!neg[1].has_value() || !neg[1].value()) { std::cout << " [FAIL] : -5 hours should be negative" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: is_negative"); } if (!neg[0].has_value() || neg[0].value()) { std::cout << " [FAIL] : 1 day should not be negative" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: not negative"); } // is_zero auto zero = arr.is_zero(); if (!zero[2].has_value() || !zero[2].value()) { std::cout << " [FAIL] : 0 seconds should be zero" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: is_zero"); } // NA should propagate if (pos[3].has_value() || neg[3].has_value() || zero[3].has_value()) { std::cout << " [FAIL] : NaT should propagate to boolean props" << std::endl; throw std::runtime_error("pd_test_timedelta_array_boolean_props failed: NaT propagation"); } .. _example-datetimeindexopsmixin-ceil-22: .. dropdown:: ceil (pd_test_1_all.cpp:4949) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 4939 :emphasize-lines: 11 throw std::runtime_error("pd_test_arithmetic_series_round failed: round failed"); } auto f = a.floor(); passed = std::abs(f[0] - 1.0) < 0.001 && std::abs(f[2] - 3.0) < 0.001 && std::abs(f[3] - (-2.0)) < 0.001; if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_series_round() : floor failed" << std::endl; throw std::runtime_error("pd_test_arithmetic_series_round failed: floor failed"); } auto c = a.ceil(); passed = std::abs(c[0] - 2.0) < 0.001 && std::abs(c[2] - 4.0) < 0.001 && std::abs(c[3] - (-1.0)) < 0.001; if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_series_round() : ceil failed" << std::endl; throw std::runtime_error("pd_test_arithmetic_series_round failed: ceil failed"); } // Round with decimals pandas::Series b({1.234, 2.567, 3.891}); auto r2 = b.round(2); passed = std::abs(r2[0] - 1.23) < 0.001 && std::abs(r2[1] - 2.57) < 0.001; .. _example-datetimeindexopsmixin-clone-23: .. dropdown:: clone (pd_test_1_all.cpp:5776) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 5766 :emphasize-lines: 11 std::cout << " -> tests passed" << std::endl; } void pd_test_categorical_index_clone() { std::cout << "========= clone ======================================="; pandas::CategoricalArray arr({"p", "q", "r"}); pandas::CategoricalIndex idx(arr, "original"); std::unique_ptr cloned = idx.clone(); bool passed = (cloned != nullptr && cloned->size() == idx.size() && cloned->name() == idx.name()); if (!passed) { std::cout << " [FAIL] : in pd_test_categorical_index_clone()" << std::endl; throw std::runtime_error("pd_test_categorical_index_clone failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-day-24: .. dropdown:: day (pd_test_1_all.cpp:1193) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1183 :emphasize-lines: 11 std::cout << " [FAIL] : month[0] should be 3" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_month_day failed: month[0]"); } auto m1 = months[1]; if (!m1.has_value() || m1.value() != 12) { std::cout << " [FAIL] : month[1] should be 12" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_month_day failed: month[1]"); } // Day auto days = arr.day(); auto d0 = days[0]; if (!d0.has_value() || d0.value() != 15) { std::cout << " [FAIL] : day[0] should be 15" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_month_day failed: day[0]"); } auto d1 = days[1]; if (!d1.has_value() || d1.value() != 25) { std::cout << " [FAIL] : day[1] should be 25" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_month_day failed: day[1]"); } .. _example-datetimeindexopsmixin-day_name-25: .. dropdown:: day_name (pd_test_1_all.cpp:8474) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8464 :emphasize-lines: 11 void pd_test_datetime_mixin_day_name() { std::cout << "========= day_name ===================================="; std::vector> values = { numpy::datetime64(0LL, numpy::DateTimeUnit::Nanosecond) // 1970-01-01 = Thursday }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); std::vector names = idx.day_name(); bool passed = (names.size() == 1 && names[0] == "Thursday"); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_day_name() got: " << names[0] << std::endl; throw std::runtime_error("pd_test_datetime_mixin_day_name failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-dayofweek-26: .. dropdown:: dayofweek (pd_test_1_all.cpp:7565) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 7555 :emphasize-lines: 11 // 1970-01-01 was a Thursday (day 3) std::vector> values = { make_dt(0), // Thursday (3) make_dt(NS_PER_DAY), // Friday (4) make_dt(2 * NS_PER_DAY), // Saturday (5) make_dt(3 * NS_PER_DAY) // Sunday (6) }; pandas::DatetimeArray arr(values); pandas::DatetimeIndex idx(arr); auto dow = idx.dayofweek(); bool passed = (dow.size() == 4); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_index_dayofweek()" << std::endl; throw std::runtime_error("pd_test_datetime_index_dayofweek failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-dayofyear-27: .. dropdown:: dayofyear (pd_test_3_all.cpp:18582) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 18572 :emphasize-lines: 11 auto seconds = s.dt().second(); if (seconds[0] != 45 || seconds[1] != 30 || seconds[2] != 59) { std::cout << " [FAIL] : second() failed" << std::endl; throw std::runtime_error("pd_test_dt_time_components: second() failed"); } std::cout << " -> tests passed" << std::endl; } // ============================================================================ // Test dt().dayofweek(), dt().dayofyear(), dt().quarter() // ============================================================================ void pd_test_dt_derived_properties() { std::cout << "========= Series.dt().dayofweek/dayofyear/quarter() ======"; // 2020-01-01 is a Wednesday (dayofweek=2), dayofyear=1, Q1 // 2020-07-04 is a Saturday (dayofweek=5), dayofyear=186, Q3 pandas::Series s({"2020-01-01", "2020-07-04"}); auto dow = s.dt().dayofweek(); .. _example-datetimeindexopsmixin-floor-28: .. dropdown:: floor (pd_test_1_all.cpp:4942) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 4932 :emphasize-lines: 11 pandas::Series a({1.4, 2.5, 3.6, -1.4, -2.5}); auto r = a.round(); bool passed = std::abs(r[0] - 1.0) < 0.001 && std::abs(r[2] - 4.0) < 0.001; if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_series_round() : round failed" << std::endl; throw std::runtime_error("pd_test_arithmetic_series_round failed: round failed"); } auto f = a.floor(); passed = std::abs(f[0] - 1.0) < 0.001 && std::abs(f[2] - 3.0) < 0.001 && std::abs(f[3] - (-2.0)) < 0.001; if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_series_round() : floor failed" << std::endl; throw std::runtime_error("pd_test_arithmetic_series_round failed: floor failed"); } auto c = a.ceil(); passed = std::abs(c[0] - 2.0) < 0.001 && std::abs(c[2] - 4.0) < 0.001 && std::abs(c[3] - (-1.0)) < 0.001; if (!passed) { std::cout << " [FAIL] : in pd_test_arithmetic_series_round() : ceil failed" << std::endl; .. _example-datetimeindexopsmixin-freq-29: .. dropdown:: freq (pd_test_1_all.cpp:8233) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8223 :emphasize-lines: 11 std::cout << "========= freq property ==============================="; std::vector> values = { numpy::datetime64(0LL, numpy::DateTimeUnit::Nanosecond), numpy::datetime64(86400000000000LL, numpy::DateTimeUnit::Nanosecond) // 1 day }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); // Default freq is nullopt or inferred auto f = idx.freq(); std::string fs = idx.freqstr(); bool passed = true; // freq may or may not be set if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_freq()" << std::endl; throw std::runtime_error("pd_test_datetime_mixin_freq failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-freqstr-30: .. dropdown:: freqstr (pd_test_1_all.cpp:2671) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 2661 :emphasize-lines: 11 } pandas::PeriodDtype dtype_y("Y"); if (dtype_y.name() != "period[Y]") { std::cout << " [FAIL] : dtype_y.name() should be 'period[Y]'" << std::endl; throw std::runtime_error("pd_test_period_array_freq_validation failed: dtype name Y"); } // Test frequency string pandas::PeriodArray arr(std::vector{"2024-01-15"}, "D"); if (arr.freqstr() != "D") { std::cout << " [FAIL] : arr.freqstr() should be 'D'" << std::endl; throw std::runtime_error("pd_test_period_array_freq_validation failed: freqstr"); } std::cout << " -> tests passed" << std::endl; } void pd_test_period_array_year_month_quarter() { std::cout << "========= PeriodArray: year/month/quarter components ======================= "; .. _example-datetimeindexopsmixin-hour-31: .. dropdown:: hour (pd_test_1_all.cpp:7476) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 7466 :emphasize-lines: 11 std::cout << "========= hour property ==============================="; std::vector> values = { make_dt(0), // Hour 0 make_dt(6 * NS_PER_HOUR), // Hour 6 make_dt(23 * NS_PER_HOUR) // Hour 23 }; pandas::DatetimeArray arr(values); pandas::DatetimeIndex idx(arr); auto hours = idx.hour(); bool passed = (hours.size() == 3); auto h0 = hours[0]; auto h1 = hours[1]; auto h2 = hours[2]; passed = passed && h0.has_value() && *h0 == 0; passed = passed && h1.has_value() && *h1 == 6; passed = passed && h2.has_value() && *h2 == 23; if (!passed) { .. _example-datetimeindexopsmixin-microsecond-32: .. dropdown:: microsecond (pd_test_timestamp_scalar.cpp:45) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 35 :emphasize-lines: 11 // Component constructor pandas::Timestamp ts1(2024, 6, 15, 14, 30, 45); if (ts1.year() != 2024 || ts1.month() != 6 || ts1.day() != 15 || ts1.hour() != 14 || ts1.minute() != 30 || ts1.second() != 45) { pass = false; fail_msg = "Component constructor values incorrect"; } // With microseconds and nanoseconds pandas::Timestamp ts2(2024, 1, 1, 12, 0, 0, 123456, 789); if (ts2.microsecond() != 123456 || ts2.nanosecond() != 789) { pass = false; fail_msg = "Microsecond/nanosecond values incorrect"; } // String constructor - ISO format pandas::Timestamp ts3("2024-06-15T14:30:45"); if (ts3.year() != 2024 || ts3.month() != 6 || ts3.day() != 15) { pass = false; fail_msg = "String constructor parse failed"; } .. _example-datetimeindexopsmixin-month-33: .. dropdown:: month (pd_test_1_all.cpp:1180) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1170 :emphasize-lines: 11 void pd_test_datetime_array_component_month_day() { std::cout << "========= DatetimeArray: month/day components ======================= "; pandas::DatetimeArray arr(std::vector{ "2023-03-15", "2023-12-25", "NaT" }); // Month auto months = arr.month(); auto m0 = months[0]; if (!m0.has_value() || m0.value() != 3) { std::cout << " [FAIL] : month[0] should be 3" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_month_day failed: month[0]"); } auto m1 = months[1]; if (!m1.has_value() || m1.value() != 12) { std::cout << " [FAIL] : month[1] should be 12" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_month_day failed: month[1]"); } .. _example-datetimeindexopsmixin-month_name-34: .. dropdown:: month_name (pd_test_1_all.cpp:8454) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8444 :emphasize-lines: 11 void pd_test_datetime_mixin_month_name() { std::cout << "========= month_name =================================="; std::vector> values = { numpy::datetime64(0LL, numpy::DateTimeUnit::Nanosecond) // 1970-01-01 = January }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); std::vector names = idx.month_name(); bool passed = (names.size() == 1 && names[0] == "January"); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_month_name() got: " << names[0] << std::endl; throw std::runtime_error("pd_test_datetime_mixin_month_name failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-nanosecond-35: .. dropdown:: nanosecond (pd_test_timestamp_scalar.cpp:45) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 35 :emphasize-lines: 11 // Component constructor pandas::Timestamp ts1(2024, 6, 15, 14, 30, 45); if (ts1.year() != 2024 || ts1.month() != 6 || ts1.day() != 15 || ts1.hour() != 14 || ts1.minute() != 30 || ts1.second() != 45) { pass = false; fail_msg = "Component constructor values incorrect"; } // With microseconds and nanoseconds pandas::Timestamp ts2(2024, 1, 1, 12, 0, 0, 123456, 789); if (ts2.microsecond() != 123456 || ts2.nanosecond() != 789) { pass = false; fail_msg = "Microsecond/nanosecond values incorrect"; } // String constructor - ISO format pandas::Timestamp ts3("2024-06-15T14:30:45"); if (ts3.year() != 2024 || ts3.month() != 6 || ts3.day() != 15) { pass = false; fail_msg = "String constructor parse failed"; } .. _example-datetimeindexopsmixin-normalize-36: .. dropdown:: normalize (pd_test_1_all.cpp:8723) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8713 :emphasize-lines: 11 void pd_test_datetime_mixin_normalize() { std::cout << "========= normalize ==================================="; // Create datetime with time component std::vector> values = { numpy::datetime64(86400000000000LL + 3600000000000LL, numpy::DateTimeUnit::Nanosecond) // 1 day + 1 hour }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); pandas::DatetimeMixinIndex normalized = idx.normalize(); bool passed = (normalized.size() == 1); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_normalize()" << std::endl; throw std::runtime_error("pd_test_datetime_mixin_normalize failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-quarter-37: .. dropdown:: quarter (pd_test_1_all.cpp:1218) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1208 :emphasize-lines: 11 void pd_test_datetime_array_quarter() { std::cout << "========= DatetimeArray: quarter ======================= "; pandas::DatetimeArray arr(std::vector{ "2023-01-15", // Q1 "2023-05-20", // Q2 "2023-09-10", // Q3 "2023-11-25" // Q4 }); auto quarters = arr.quarter(); auto q0 = quarters[0]; if (!q0.has_value() || q0.value() != 1) { std::cout << " [FAIL] : quarter[0] should be 1" << std::endl; throw std::runtime_error("pd_test_datetime_array_quarter failed: quarter[0]"); } auto q1 = quarters[1]; if (!q1.has_value() || q1.value() != 2) { std::cout << " [FAIL] : quarter[1] should be 2" << std::endl; throw std::runtime_error("pd_test_datetime_array_quarter failed: quarter[1]"); .. _example-datetimeindexopsmixin-result-38: .. dropdown:: result (pd_test_1_all.cpp:15406) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 15396 :emphasize-lines: 11 data.setElementAt({0}, numpy::datetime64(100LL, numpy::DateTimeUnit::Nanosecond)); data.setElementAt({1}, numpy::datetime64(200LL, numpy::DateTimeUnit::Nanosecond)); numpy::NDArray mask(std::vector{2}); mask.setElementAt({0}, numpy::bool_(false)); mask.setElementAt({1}, numpy::bool_(false)); pandas::DatetimeArray arr(data, mask); pandas::DatetimeIndexBase idx(arr, "original"); // Create join result (int64 values) numpy::NDArray join_result(std::vector{3}); join_result.setElementAt({0}, numpy::int64(500LL)); join_result.setElementAt({1}, numpy::int64(600LL)); join_result.setElementAt({2}, numpy::int64(700LL)); auto new_idx = idx._from_join_target(join_result); bool passed = (new_idx.size() == 3 && new_idx.name().has_value() && *new_idx.name() == "original"); if (!passed) { .. _example-datetimeindexopsmixin-result-39: .. dropdown:: result (pd_test_1_all.cpp:15406) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 15396 :emphasize-lines: 11 data.setElementAt({0}, numpy::datetime64(100LL, numpy::DateTimeUnit::Nanosecond)); data.setElementAt({1}, numpy::datetime64(200LL, numpy::DateTimeUnit::Nanosecond)); numpy::NDArray mask(std::vector{2}); mask.setElementAt({0}, numpy::bool_(false)); mask.setElementAt({1}, numpy::bool_(false)); pandas::DatetimeArray arr(data, mask); pandas::DatetimeIndexBase idx(arr, "original"); // Create join result (int64 values) numpy::NDArray join_result(std::vector{3}); join_result.setElementAt({0}, numpy::int64(500LL)); join_result.setElementAt({1}, numpy::int64(600LL)); join_result.setElementAt({2}, numpy::int64(700LL)); auto new_idx = idx._from_join_target(join_result); bool passed = (new_idx.size() == 3 && new_idx.name().has_value() && *new_idx.name() == "original"); if (!passed) { .. _example-datetimeindexopsmixin-result-40: .. dropdown:: result (pd_test_1_all.cpp:15406) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 15396 :emphasize-lines: 11 data.setElementAt({0}, numpy::datetime64(100LL, numpy::DateTimeUnit::Nanosecond)); data.setElementAt({1}, numpy::datetime64(200LL, numpy::DateTimeUnit::Nanosecond)); numpy::NDArray mask(std::vector{2}); mask.setElementAt({0}, numpy::bool_(false)); mask.setElementAt({1}, numpy::bool_(false)); pandas::DatetimeArray arr(data, mask); pandas::DatetimeIndexBase idx(arr, "original"); // Create join result (int64 values) numpy::NDArray join_result(std::vector{3}); join_result.setElementAt({0}, numpy::int64(500LL)); join_result.setElementAt({1}, numpy::int64(600LL)); join_result.setElementAt({2}, numpy::int64(700LL)); auto new_idx = idx._from_join_target(join_result); bool passed = (new_idx.size() == 3 && new_idx.name().has_value() && *new_idx.name() == "original"); if (!passed) { .. _example-datetimeindexopsmixin-round-41: .. dropdown:: round (pd_test_1_all.cpp:1688) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1678 :emphasize-lines: 11 void pd_test_floating_array_rounding() { std::cout << "========= FloatingArray: rounding ======================= "; pandas::FloatingArray arr({ std::optional(1.234), std::optional(2.567), std::nullopt }); auto rounded = arr.round(2); if (std::abs(rounded[0].value() - 1.23) > 0.001 || std::abs(rounded[1].value() - 2.57) > 0.001) { std::cout << " [FAIL] : in pd_test_floating_array_rounding() : round(2)" << std::endl; throw std::runtime_error("pd_test_floating_array_rounding failed: round(2)"); } if (!rounded.is_na(2)) { std::cout << " [FAIL] : in pd_test_floating_array_rounding() : round should preserve NA" << std::endl; throw std::runtime_error("pd_test_floating_array_rounding failed: NA preservation"); } .. _example-datetimeindexopsmixin-second-42: .. dropdown:: second (pd_test_1_all.cpp:7534) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 7524 :emphasize-lines: 11 std::cout << "========= second property ============================="; std::vector> values = { make_dt(0), // Second 0 make_dt(30 * NS_PER_SEC), // Second 30 make_dt(59 * NS_PER_SEC) // Second 59 }; pandas::DatetimeArray arr(values); pandas::DatetimeIndex idx(arr); auto seconds = idx.second(); bool passed = (seconds.size() == 3); auto s0 = seconds[0]; auto s1 = seconds[1]; auto s2 = seconds[2]; passed = passed && s0.has_value() && *s0 == 0; passed = passed && s1.has_value() && *s1 == 30; passed = passed && s2.has_value() && *s2 == 59; if (!passed) { .. _example-datetimeindexopsmixin-set_freq-43: .. dropdown:: set_freq (pd_test_1_all.cpp:8254) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8244 :emphasize-lines: 11 void pd_test_datetime_mixin_set_freq() { std::cout << "========= set_freq ===================================="; std::vector> values = { numpy::datetime64(0LL, numpy::DateTimeUnit::Nanosecond) }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); idx.set_freq("D"); auto f = idx.freq(); bool passed = (f.has_value() && *f == "D"); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_set_freq()" << std::endl; throw std::runtime_error("pd_test_datetime_mixin_set_freq failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-snap-44: .. dropdown:: snap (pd_test_1_all.cpp:8364) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8354 :emphasize-lines: 11 void pd_test_datetime_mixin_snap() { std::cout << "========= snap ========================================"; std::vector> values = { numpy::datetime64(1000000000123456789LL, numpy::DateTimeUnit::Nanosecond) }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); pandas::DatetimeMixinIndex snapped = idx.snap("s"); bool passed = (snapped.size() == 1); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_snap()" << std::endl; throw std::runtime_error("pd_test_datetime_mixin_snap failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-strftime-45: .. dropdown:: strftime (pd_test_1_all.cpp:8434) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8424 :emphasize-lines: 11 void pd_test_datetime_mixin_strftime() { std::cout << "========= strftime ===================================="; std::vector> values = { numpy::datetime64(0LL, numpy::DateTimeUnit::Nanosecond), // 1970-01-01 numpy::datetime64(86400000000000LL, numpy::DateTimeUnit::Nanosecond) // 1970-01-02 }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); std::vector formatted = idx.strftime("%Y-%m-%d"); bool passed = (formatted.size() == 2 && !formatted[0].empty() && !formatted[1].empty()); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_strftime()" << std::endl; throw std::runtime_error("pd_test_datetime_mixin_strftime failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-td_days-46: .. dropdown:: td_days (pd_test_1_all.cpp:8603) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8593 :emphasize-lines: 11 void pd_test_timedelta_mixin_days() { std::cout << "========= days component (Timedelta) =================="; std::vector> values = { numpy::timedelta64(172800000000000LL, numpy::DateTimeUnit::Nanosecond) // 2 days }; pandas::TimedeltaArray arr(values); pandas::TimedeltaMixinIndex idx(arr); pandas::IntegerArray days = idx.td_days(); bool passed = (days.size() == 1 && days[0].has_value() && *days[0] == 2); if (!passed) { int64_t got = days[0].has_value() ? *days[0] : -1; std::cout << " [FAIL] : in pd_test_timedelta_mixin_days() expected 2, got " << got << std::endl; throw std::runtime_error("pd_test_timedelta_mixin_days failed"); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-total_seconds-47: .. dropdown:: total_seconds (pd_test_1_all.cpp:4224) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 4214 :emphasize-lines: 11 void pd_test_timedelta_array_total_seconds() { std::cout << "========= TimedeltaArray: total_seconds ======================= "; pandas::TimedeltaArray arr({ std::optional(numpy::timedelta64(1, numpy::DateTimeUnit::Day)), std::optional(numpy::timedelta64(1, numpy::DateTimeUnit::Hour)), std::nullopt }); auto total = arr.total_seconds(); auto t0 = total[0]; if (!t0.has_value() || std::abs(t0.value() - 86400.0) > 0.001) { std::cout << " [FAIL] : total_seconds[0] should be 86400" << std::endl; throw std::runtime_error("pd_test_timedelta_array_total_seconds failed: total_seconds[0]"); } auto t1 = total[1]; if (!t1.has_value() || std::abs(t1.value() - 3600.0) > 0.001) { std::cout << " [FAIL] : total_seconds[1] should be 3600" << std::endl; .. _example-datetimeindexopsmixin-type_id-48: .. dropdown:: type_id (pd_test_3_all.cpp:25592) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 25582 :emphasize-lines: 11 // ------------------- pd_test_value_classify (end) ------------------ // ------------------- pd_test_index_type_id (start) ------------------ namespace dataframe_tests_index_type_id { void pd_test_index_type_id_dispatch() { std::cout << "========= IndexTypeId dispatch ======================="; // RangeIndex ::pandas::RangeIndex ri(0, 5); if (ri.type_id() != ::pandas::IndexTypeId::RangeIndex) throw std::runtime_error("RangeIndex type_id failed"); // Index ::pandas::Index si(std::vector{"a", "b", "c"}); if (si.type_id() != ::pandas::IndexTypeId::IndexString) throw std::runtime_error("Index type_id failed"); // Index ::pandas::Index ii(std::vector{1, 2, 3}); if (ii.type_id() != ::pandas::IndexTypeId::IndexInt64) .. _example-datetimeindexopsmixin-tz-49: .. dropdown:: tz (pd_test_2_all.cpp:17914) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 17904 :emphasize-lines: 11 pandas::DataFrame df(data); df.set_index(std::make_unique(tz_aware_idx)); // Verify the index is timezone-aware const pandas::DatetimeIndex* original_idx = dynamic_cast(&df.index()); if (!original_idx) { std::cout << " [FAIL] : in pd_test_tz_convert_basic() : index is not DatetimeIndex" << std::endl; throw std::runtime_error("pd_test_tz_convert_basic failed: index is not DatetimeIndex"); } std::string original_tz = original_idx->tz(); if (original_tz.empty()) { std::cout << " [FAIL] : in pd_test_tz_convert_basic() : original index is not timezone-aware" << std::endl; throw std::runtime_error("pd_test_tz_convert_basic failed: original index is not timezone-aware"); } // Convert to Asia/Shanghai timezone pandas::DataFrame df_shanghai = df.tz_convert("Asia/Shanghai"); // Verify result has a DatetimeIndex const pandas::DatetimeIndex* converted_idx = dynamic_cast(&df_shanghai.index()); .. _example-datetimeindexopsmixin-tz_aware-50: .. dropdown:: tz_aware (pd_test_1_all.cpp:8745) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 8735 :emphasize-lines: 11 std::cout << "========= tz_localize ================================="; std::vector> values = { numpy::datetime64(0LL, numpy::DateTimeUnit::Nanosecond) }; pandas::DatetimeArray arr(values); pandas::DatetimeMixinIndex idx(arr); pandas::DatetimeMixinIndex localized = idx.tz_localize("UTC"); bool passed = (localized.size() == 1 && localized.tz_aware()); if (!passed) { std::cout << " [FAIL] : in pd_test_datetime_mixin_tz_localize()" << std::endl; throw std::runtime_error("pd_test_datetime_mixin_tz_localize failed"); } std::cout << " -> tests passed" << std::endl; } // ============================================================================ // Conversion Method Tests .. _example-datetimeindexopsmixin-week-51: .. dropdown:: week (pd_test_timestamp_scalar.cpp:406) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 396 :emphasize-lines: 11 // 2024-06-15 is a Saturday pandas::Timestamp ts(2024, 6, 15); if (ts.dayofweek() != 5) { pass = false; fail_msg = "2024-06-15 should be Saturday (5)"; } if (ts.day_of_week() != 5) { pass = false; fail_msg = "day_of_week alias"; } if (ts.dayofyear() != 167) { pass = false; fail_msg = "2024-06-15 should be day 167"; } if (ts.day_of_year() != 167) { pass = false; fail_msg = "day_of_year alias"; } if (ts.quarter() != 2) { pass = false; fail_msg = "June is Q2"; } if (ts.days_in_month() != 30) { pass = false; fail_msg = "June has 30 days"; } int week = ts.week(); if (week < 1 || week > 53) { pass = false; fail_msg = "week should be 1-53"; } if (!pass) { std::cout << " [FAIL] : in np_test_timestamp_derived() : " << fail_msg; throw std::runtime_error("np_test_timestamp_derived failed: " + fail_msg); } std::cout << " -> tests passed" << std::endl; } .. _example-datetimeindexopsmixin-weekday-52: .. dropdown:: weekday (pd_test_3_all.cpp:1471) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1461 :emphasize-lines: 11 std::cout << " [FAIL] date_range 10-arg form: expected size 10, got " << idx.size() << std::endl; throw std::runtime_error("date_range 10-arg form regressed"); } } std::cout << " -> tests passed" << std::endl; } void pd_test_3_all_period_weekday() { std::cout << "========= PeriodArray.weekday() ======================"; // Create a PeriodArray with some dates std::vector> ordinals = {0, 1, 2, 3, 4}; // Days from epoch pandas::PeriodArray arr(ordinals, "D"); pandas::IntegerArray weekdays = arr.weekday(); if (weekdays.size() != 5) { std::cout << " [FAIL] : in pd_test_3_all_period_weekday() : size should be 5" << std::endl; throw std::runtime_error("pd_test_3_all_period_weekday failed: size"); .. _example-datetimeindexopsmixin-year-53: .. dropdown:: year (pd_test_1_all.cpp:1147) :class-title: example-dropdown .. code-block:: cpp :linenos: :lineno-start: 1137 :emphasize-lines: 11 void pd_test_datetime_array_component_year() { std::cout << "========= DatetimeArray: year component ======================= "; pandas::DatetimeArray arr(std::vector{ "2020-01-15", "NaT", "2025-06-20" }); auto years = arr.year(); auto y0 = years[0]; if (!y0.has_value() || y0.value() != 2020) { std::cout << " [FAIL] : year[0] should be 2020" << std::endl; throw std::runtime_error("pd_test_datetime_array_component_year failed: year[0]"); } auto y1 = years[1]; if (y1.has_value()) { std::cout << " [FAIL] : year[1] should be NA (NaT)" << std::endl;