This is an automated email from the ASF dual-hosted git repository.
apitrou pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow.git
The following commit(s) were added to refs/heads/main by this push:
new dbae5f07b6 GH-36789: [C++] Support divide(duration, duration) (#36800)
dbae5f07b6 is described below
commit dbae5f07b62ccc4be6ab1f47d72eaf054d24ae05
Author: Jin Shang <[email protected]>
AuthorDate: Tue Jul 25 16:43:14 2023 +0800
GH-36789: [C++] Support divide(duration, duration) (#36800)
### Rationale for this change
Support divide(duration, duration), as pandas and numpy already do.
### What changes are included in this PR?
Add kernels divide(duration, duration)->float64 and
divide_checked(duration, duration)->float64
### Are these changes tested?
Yes
### Are there any user-facing changes?
No
* Closes: #36789
Authored-by: Jin Shang <[email protected]>
Signed-off-by: Antoine Pitrou <[email protected]>
---
cpp/src/arrow/compute/kernels/scalar_arithmetic.cc | 16 ++++++++++++++++
.../arrow/compute/kernels/scalar_temporal_test.cc | 20 ++++++++++++++++++++
2 files changed, 36 insertions(+)
diff --git a/cpp/src/arrow/compute/kernels/scalar_arithmetic.cc
b/cpp/src/arrow/compute/kernels/scalar_arithmetic.cc
index 2c7363b3ca..c305028be1 100644
--- a/cpp/src/arrow/compute/kernels/scalar_arithmetic.cc
+++ b/cpp/src/arrow/compute/kernels/scalar_arithmetic.cc
@@ -30,6 +30,7 @@
#include "arrow/compute/kernels/common_internal.h"
#include "arrow/compute/kernels/util_internal.h"
#include "arrow/type.h"
+#include "arrow/type_fwd.h"
#include "arrow/type_traits.h"
#include "arrow/util/decimal.h"
#include "arrow/util/int_util_overflow.h"
@@ -1509,6 +1510,13 @@ void RegisterScalarArithmetic(FunctionRegistry*
registry) {
DCHECK_OK(
divide->AddKernel({duration(unit), int64()}, duration(unit),
std::move(exec)));
}
+
+ // Add divide(duration, duration) -> float64
+ for (auto unit : TimeUnit::values()) {
+ auto exec = ScalarBinaryNotNull<DoubleType, DoubleType, DoubleType,
Divide>::Exec;
+ DCHECK_OK(
+ divide->AddKernel({duration(unit), duration(unit)}, float64(),
std::move(exec)));
+ }
DCHECK_OK(registry->AddFunction(std::move(divide)));
// ----------------------------------------------------------------------
@@ -1523,6 +1531,14 @@ void RegisterScalarArithmetic(FunctionRegistry*
registry) {
std::move(exec)));
}
+ // Add divide_checked(duration, duration) -> float64
+ for (auto unit : TimeUnit::values()) {
+ auto exec =
+ ScalarBinaryNotNull<DoubleType, DoubleType, DoubleType,
DivideChecked>::Exec;
+ DCHECK_OK(divide_checked->AddKernel({duration(unit), duration(unit)},
float64(),
+ std::move(exec)));
+ }
+
DCHECK_OK(registry->AddFunction(std::move(divide_checked)));
// ----------------------------------------------------------------------
diff --git a/cpp/src/arrow/compute/kernels/scalar_temporal_test.cc
b/cpp/src/arrow/compute/kernels/scalar_temporal_test.cc
index cd8abf6e92..4c7975add0 100644
--- a/cpp/src/arrow/compute/kernels/scalar_temporal_test.cc
+++ b/cpp/src/arrow/compute/kernels/scalar_temporal_test.cc
@@ -26,6 +26,7 @@
#include "arrow/testing/matchers.h"
#include "arrow/testing/util.h"
#include "arrow/type.h"
+#include "arrow/type_fwd.h"
#include "arrow/type_traits.h"
#include "arrow/util/checked_cast.h"
#include "arrow/util/formatting.h"
@@ -1695,6 +1696,7 @@ TEST_F(ScalarTemporalTest, TestTemporalMultiplyDuration) {
}
TEST_F(ScalarTemporalTest, TestTemporalDivideDuration) {
+ // div(duration, integer) -> integer
for (auto u : TimeUnit::values()) {
for (auto numeric : NumericTypes()) {
if (!is_integer(numeric->id())) continue;
@@ -1718,6 +1720,24 @@ TEST_F(ScalarTemporalTest, TestTemporalDivideDuration) {
CallFunction("divide_checked",
{durations, zeros}));
}
}
+
+ // div(duration, duration) -> float64
+ auto left = ArrayFromJSON(duration(TimeUnit::SECOND), "[1, 2, 3, 4]");
+ auto right = ArrayFromJSON(duration(TimeUnit::MILLI), "[4000, 300, 20, 1]");
+ auto expected_left_by_right =
+ ArrayFromJSON(float64(), "[0.25, 6.666666666666667, 150, 4000]");
+ auto expected_right_by_left =
+ ArrayFromJSON(float64(), "[4, 0.15, 0.006666666666666667, 0.00025]");
+ CheckScalarBinary("divide", left, right, expected_left_by_right);
+ CheckScalarBinary("divide_checked", left, right, expected_left_by_right);
+ CheckScalarBinary("divide", right, left, expected_right_by_left);
+ CheckScalarBinary("divide_checked", right, left, expected_right_by_left);
+
+ // Check dispatching
+ CheckDispatchBest("divide", {duration(TimeUnit::SECOND),
duration(TimeUnit::MILLI)},
+ {duration(TimeUnit::MILLI), duration(TimeUnit::MILLI)});
+ CheckDispatchBest("divide", {duration(TimeUnit::NANO),
duration(TimeUnit::MILLI)},
+ {duration(TimeUnit::NANO), duration(TimeUnit::NANO)});
}
TEST_F(ScalarTemporalTest, TestTemporalDifferenceWeeks) {