This is an automated email from the ASF dual-hosted git repository.

praveenbingo pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/arrow.git


The following commit(s) were added to refs/heads/master by this push:
     new 5f4252b  ARROW-11987: [C++][Gandiva] Implement trigonometric functions
5f4252b is described below

commit 5f4252bbc6d1f05cc2c7c9c113b8e133444bb523
Author: João Pedro <[email protected]>
AuthorDate: Sat Mar 27 16:27:48 2021 +0530

    ARROW-11987: [C++][Gandiva] Implement trigonometric functions
    
    Implement base trigonometric functions (sin; cos; asin; acos; tan; atan; 
sinh; cosh; tanh; cotg; radians; degrees;)
    
    JIRA issue: https://issues.apache.org/jira/browse/ARROW-11987
    
    Closes #9726 from jpedroantunes/feature/add-trigonometry-functions and 
squashes the following commits:
    
    3391776c3 <João Pedro> Correct missing identation
    896d91b49 <João Pedro> Add initialization for atan2 for different numeric 
types
    5ef2c8362 <João Pedro> Correct \ identation on macros being used
    e2355e8e5 <João Pedro> Fix last missing format on extended math ops on 
gandiva
    7cd2659b7 <João Pedro> Fix more identation comments on C++ code
    831cff06d <João Pedro> Fix suggestions on code format by C++ linter
    a2c2b2826 <João Pedro> Add cast for pi float variable used on test
    33987aad4 <João Pedro> Remove unused macro on function registry math on 
gandiva
    11e5c9cb4 <João Pedro> Add ifdef definition for m_pi constants
    434995b7e <João Pedro> Add support for trigonometry functions on Gandiva
    7e1e4d9c2 <João Pedro> Add projector test for new implemented trigonometry 
functions
    6603019c5 <João Pedro> Correct atan2 method name in unit tests
    6b5dafdd6 <João Pedro> Correct macro for atan2 method implementation
    c05463d72 <João Pedro> Register all missing trigonometry methods on funtion 
registry and types header
    63fba45f5 <João Pedro> Register on function registry all base trigonometry 
functions
    c94590fcf <João Pedro> Add unit tests for base trigonometry functions
    870029fa2 <João Pedro> Add implementation for base trigonometry functions
    d474f75a2 <João Pedro> Add registry for base trigonometry functions
    
    Authored-by: João Pedro <[email protected]>
    Signed-off-by: Praveen <[email protected]>
---
 cpp/src/gandiva/function_registry_math_ops.cc      |  15 +++
 cpp/src/gandiva/precompiled/extended_math_ops.cc   | 110 +++++++++++++++++-
 .../gandiva/precompiled/extended_math_ops_test.cc  | 128 +++++++++++++++++++++
 cpp/src/gandiva/precompiled/types.h                |  51 ++++++++
 cpp/src/gandiva/tests/projector_test.cc            |  91 ++++++++++++++-
 5 files changed, 392 insertions(+), 3 deletions(-)

diff --git a/cpp/src/gandiva/function_registry_math_ops.cc 
b/cpp/src/gandiva/function_registry_math_ops.cc
index 771e363..49afd40 100644
--- a/cpp/src/gandiva/function_registry_math_ops.cc
+++ b/cpp/src/gandiva/function_registry_math_ops.cc
@@ -36,6 +36,14 @@ namespace gandiva {
       BINARY_UNSAFE_NULL_IF_NULL(name, ALIASES, float32, float64), \
       BINARY_UNSAFE_NULL_IF_NULL(name, ALIASES, float64, float64)
 
+#define MATH_BINARY_SAFE(name, ALIASES)                                        
   \
+  BINARY_GENERIC_SAFE_NULL_IF_NULL(name, ALIASES, int32, int32, float64),      
   \
+      BINARY_GENERIC_SAFE_NULL_IF_NULL(name, ALIASES, int64, int64, float64),  
   \
+      BINARY_GENERIC_SAFE_NULL_IF_NULL(name, ALIASES, uint32, uint32, 
float64),   \
+      BINARY_GENERIC_SAFE_NULL_IF_NULL(name, ALIASES, uint64, uint64, 
float64),   \
+      BINARY_GENERIC_SAFE_NULL_IF_NULL(name, ALIASES, float32, float32, 
float64), \
+      BINARY_GENERIC_SAFE_NULL_IF_NULL(name, ALIASES, float64, float64, 
float64)
+
 #define UNARY_SAFE_NULL_NEVER_BOOL_FN(name, ALIASES) \
   NUMERIC_BOOL_DATE_TYPES(UNARY_SAFE_NULL_NEVER_BOOL, name, ALIASES)
 
@@ -59,6 +67,13 @@ std::vector<NativeFunction> GetMathOpsFunctionRegistry() {
       BINARY_SAFE_NULL_NEVER_BOOL_FN(is_distinct_from, {}),
       BINARY_SAFE_NULL_NEVER_BOOL_FN(is_not_distinct_from, {}),
 
+      // trigonometry functions
+      MATH_UNARY_OPS(sin, {}), MATH_UNARY_OPS(cos, {}), MATH_UNARY_OPS(asin, 
{}),
+      MATH_UNARY_OPS(acos, {}), MATH_UNARY_OPS(tan, {}), MATH_UNARY_OPS(atan, 
{}),
+      MATH_UNARY_OPS(sinh, {}), MATH_UNARY_OPS(cosh, {}), MATH_UNARY_OPS(tanh, 
{}),
+      MATH_UNARY_OPS(cot, {}), MATH_UNARY_OPS(radians, {}), 
MATH_UNARY_OPS(degrees, {}),
+      MATH_BINARY_SAFE(atan2, {}),
+
       // decimal functions
       UNARY_SAFE_NULL_IF_NULL(abs, {}, decimal128, decimal128),
       UNARY_SAFE_NULL_IF_NULL(ceil, {}, decimal128, decimal128),
diff --git a/cpp/src/gandiva/precompiled/extended_math_ops.cc 
b/cpp/src/gandiva/precompiled/extended_math_ops.cc
index d7de432..b2d62da 100644
--- a/cpp/src/gandiva/precompiled/extended_math_ops.cc
+++ b/cpp/src/gandiva/precompiled/extended_math_ops.cc
@@ -15,6 +15,10 @@
 // specific language governing permissions and limitations
 // under the License.
 
+#ifndef M_PI
+#define M_PI 3.14159265358979323846
+#endif
+
 #include "arrow/util/logging.h"
 #include "gandiva/precompiled/decimal_ops.h"
 
@@ -103,13 +107,117 @@ LOG_WITH_BASE(uint64, uint64, float64)
 LOG_WITH_BASE(float32, float32, float64)
 LOG_WITH_BASE(float64, float64, float64)
 
+// Sin
+#define SIN(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                             \
+  gdv_##OUT_TYPE sin_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(sin(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(SIN, float64)
+
+// Asin
+#define ASIN(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                              \
+  gdv_##OUT_TYPE asin_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(asin(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(ASIN, float64)
+
+// Cos
+#define COS(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                             \
+  gdv_##OUT_TYPE cos_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(cos(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(COS, float64)
+
+// Acos
+#define ACOS(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                              \
+  gdv_##OUT_TYPE acos_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(acos(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(ACOS, float64)
+
+// Tan
+#define TAN(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                             \
+  gdv_##OUT_TYPE tan_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(tan(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(TAN, float64)
+
+// Atan
+#define ATAN(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                              \
+  gdv_##OUT_TYPE atan_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(atan(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(ATAN, float64)
+
+// Sinh
+#define SINH(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                              \
+  gdv_##OUT_TYPE sinh_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(sinh(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(SINH, float64)
+
+// Cosh
+#define COSH(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                              \
+  gdv_##OUT_TYPE cosh_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(cosh(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(COSH, float64)
+
+// Tanh
+#define TANH(IN_TYPE, OUT_TYPE)                                             \
+  FORCE_INLINE                                                              \
+  gdv_##OUT_TYPE tanh_##IN_TYPE(gdv_##IN_TYPE in) {                         \
+    return static_cast<gdv_##OUT_TYPE>(tanh(static_cast<long double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(TANH, float64)
+
+// Atan2
+#define ATAN2(IN_TYPE, OUT_TYPE)                                               
      \
+  FORCE_INLINE                                                                 
      \
+  gdv_##OUT_TYPE atan2_##IN_TYPE##_##IN_TYPE(gdv_##IN_TYPE in1, gdv_##IN_TYPE 
in2) { \
+    return static_cast<gdv_##OUT_TYPE>(                                        
      \
+        atan2(static_cast<long double>(in1), static_cast<long double>(in2)));  
      \
+  }
+ENUMERIC_TYPES_UNARY(ATAN2, float64)
+
+// Cot
+#define COT(IN_TYPE, OUT_TYPE)                                                 
       \
+  FORCE_INLINE                                                                 
       \
+  gdv_##OUT_TYPE cot_##IN_TYPE(gdv_##IN_TYPE in) {                             
       \
+    return static_cast<gdv_##OUT_TYPE>(tan(M_PI / 2 - static_cast<long 
double>(in))); \
+  }
+ENUMERIC_TYPES_UNARY(COT, float64)
+
+// Radians
+#define RADIANS(IN_TYPE, OUT_TYPE)                                             
      \
+  FORCE_INLINE                                                                 
      \
+  gdv_##OUT_TYPE radians_##IN_TYPE(gdv_##IN_TYPE in) {                         
      \
+    return static_cast<gdv_##OUT_TYPE>(static_cast<long double>(in) * M_PI / 
180.0); \
+  }
+ENUMERIC_TYPES_UNARY(RADIANS, float64)
+
+// Degrees
+#define DEGREES(IN_TYPE, OUT_TYPE)                                             
      \
+  FORCE_INLINE                                                                 
      \
+  gdv_##OUT_TYPE degrees_##IN_TYPE(gdv_##IN_TYPE in) {                         
      \
+    return static_cast<gdv_##OUT_TYPE>(static_cast<long double>(in) * 180.0 / 
M_PI); \
+  }
+ENUMERIC_TYPES_UNARY(DEGREES, float64)
+
 // power
 #define POWER(IN_TYPE1, IN_TYPE2, OUT_TYPE)                                    
          \
   FORCE_INLINE                                                                 
          \
   gdv_##OUT_TYPE power_##IN_TYPE1##_##IN_TYPE2(gdv_##IN_TYPE1 in1, 
gdv_##IN_TYPE2 in2) { \
     return static_cast<gdv_float64>(powl(in1, in2));                           
          \
   }
-
 POWER(float64, float64, float64)
 
 FORCE_INLINE
diff --git a/cpp/src/gandiva/precompiled/extended_math_ops_test.cc 
b/cpp/src/gandiva/precompiled/extended_math_ops_test.cc
index 81a3565..6e59f68 100644
--- a/cpp/src/gandiva/precompiled/extended_math_ops_test.cc
+++ b/cpp/src/gandiva/precompiled/extended_math_ops_test.cc
@@ -15,6 +15,10 @@
 // specific language governing permissions and limitations
 // under the License.
 
+#ifndef M_PI
+#define M_PI 3.14159265358979323846
+#endif
+
 #include <gtest/gtest.h>
 #include <cmath>
 #include "gandiva/execution_context.h"
@@ -145,4 +149,128 @@ TEST(TestExtendedMathOps, TestTruncate) {
   EXPECT_EQ(truncate_int64_int32(8124674407369523212, -2), 
8124674407369523200);
 }
 
+TEST(TestExtendedMathOps, TestTrigonometricFunctions) {
+  auto pi_float = static_cast<float>(M_PI);
+  // Sin functions
+  VerifyFuzzyEquals(sin_float32(0), sin(0));
+  VerifyFuzzyEquals(sin_float32(0), sin(0));
+  VerifyFuzzyEquals(sin_float32(pi_float / 2), sin(M_PI / 2));
+  VerifyFuzzyEquals(sin_float32(pi_float), sin(M_PI));
+  VerifyFuzzyEquals(sin_float32(-pi_float / 2), sin(-M_PI / 2));
+  VerifyFuzzyEquals(sin_float64(0), sin(0));
+  VerifyFuzzyEquals(sin_float64(M_PI / 2), sin(M_PI / 2));
+  VerifyFuzzyEquals(sin_float64(M_PI), sin(M_PI));
+  VerifyFuzzyEquals(sin_float64(-M_PI / 2), sin(-M_PI / 2));
+  VerifyFuzzyEquals(sin_int32(0), sin(0));
+  VerifyFuzzyEquals(sin_int64(0), sin(0));
+
+  // Cos functions
+  VerifyFuzzyEquals(cos_float32(0), cos(0));
+  VerifyFuzzyEquals(cos_float32(pi_float / 2), cos(M_PI / 2));
+  VerifyFuzzyEquals(cos_float32(pi_float), cos(M_PI));
+  VerifyFuzzyEquals(cos_float32(-pi_float / 2), cos(-M_PI / 2));
+  VerifyFuzzyEquals(cos_float64(0), cos(0));
+  VerifyFuzzyEquals(cos_float64(M_PI / 2), cos(M_PI / 2));
+  VerifyFuzzyEquals(cos_float64(M_PI), cos(M_PI));
+  VerifyFuzzyEquals(cos_float64(-M_PI / 2), cos(-M_PI / 2));
+  VerifyFuzzyEquals(cos_int32(0), cos(0));
+  VerifyFuzzyEquals(cos_int64(0), cos(0));
+
+  // Asin functions
+  VerifyFuzzyEquals(asin_float32(-1.0), asin(-1.0));
+  VerifyFuzzyEquals(asin_float32(1.0), asin(1.0));
+  VerifyFuzzyEquals(asin_float64(-1.0), asin(-1.0));
+  VerifyFuzzyEquals(asin_float64(1.0), asin(1.0));
+  VerifyFuzzyEquals(asin_int32(0), asin(0));
+  VerifyFuzzyEquals(asin_int64(0), asin(0));
+
+  // Acos functions
+  VerifyFuzzyEquals(acos_float32(-1.0), acos(-1.0));
+  VerifyFuzzyEquals(acos_float32(1.0), acos(1.0));
+  VerifyFuzzyEquals(acos_float64(-1.0), acos(-1.0));
+  VerifyFuzzyEquals(acos_float64(1.0), acos(1.0));
+  VerifyFuzzyEquals(acos_int32(0), acos(0));
+  VerifyFuzzyEquals(acos_int64(0), acos(0));
+
+  // Tan
+  VerifyFuzzyEquals(tan_float32(pi_float), tan(M_PI));
+  VerifyFuzzyEquals(tan_float32(-pi_float), tan(-M_PI));
+  VerifyFuzzyEquals(tan_float64(M_PI), tan(M_PI));
+  VerifyFuzzyEquals(tan_float64(-M_PI), tan(-M_PI));
+  VerifyFuzzyEquals(tan_int32(0), tan(0));
+  VerifyFuzzyEquals(tan_int64(0), tan(0));
+
+  // Atan
+  VerifyFuzzyEquals(atan_float32(pi_float), atan(M_PI));
+  VerifyFuzzyEquals(atan_float32(-pi_float), atan(-M_PI));
+  VerifyFuzzyEquals(atan_float64(M_PI), atan(M_PI));
+  VerifyFuzzyEquals(atan_float64(-M_PI), atan(-M_PI));
+  VerifyFuzzyEquals(atan_int32(0), atan(0));
+  VerifyFuzzyEquals(atan_int64(0), atan(0));
+
+  // Sinh functions
+  VerifyFuzzyEquals(sinh_float32(0), sinh(0));
+  VerifyFuzzyEquals(sinh_float32(pi_float / 2), sinh(M_PI / 2));
+  VerifyFuzzyEquals(sinh_float32(pi_float), sinh(M_PI));
+  VerifyFuzzyEquals(sinh_float32(-pi_float / 2), sinh(-M_PI / 2));
+  VerifyFuzzyEquals(sinh_float64(0), sinh(0));
+  VerifyFuzzyEquals(sinh_float64(M_PI / 2), sinh(M_PI / 2));
+  VerifyFuzzyEquals(sinh_float64(M_PI), sinh(M_PI));
+  VerifyFuzzyEquals(sinh_float64(-M_PI / 2), sinh(-M_PI / 2));
+  VerifyFuzzyEquals(sinh_int32(0), sinh(0));
+  VerifyFuzzyEquals(sinh_int64(0), sinh(0));
+
+  // Cosh functions
+  VerifyFuzzyEquals(cosh_float32(0), cosh(0));
+  VerifyFuzzyEquals(cosh_float32(pi_float / 2), cosh(M_PI / 2));
+  VerifyFuzzyEquals(cosh_float32(pi_float), cosh(M_PI));
+  VerifyFuzzyEquals(cosh_float32(-pi_float / 2), cosh(-M_PI / 2));
+  VerifyFuzzyEquals(cosh_float64(0), cosh(0));
+  VerifyFuzzyEquals(cosh_float64(M_PI / 2), cosh(M_PI / 2));
+  VerifyFuzzyEquals(cosh_float64(M_PI), cosh(M_PI));
+  VerifyFuzzyEquals(cosh_float64(-M_PI / 2), cosh(-M_PI / 2));
+  VerifyFuzzyEquals(cosh_int32(0), cosh(0));
+  VerifyFuzzyEquals(cosh_int64(0), cosh(0));
+
+  // Tanh
+  VerifyFuzzyEquals(tanh_float32(pi_float), tanh(M_PI));
+  VerifyFuzzyEquals(tanh_float32(-pi_float), tanh(-M_PI));
+  VerifyFuzzyEquals(tanh_float64(M_PI), tanh(M_PI));
+  VerifyFuzzyEquals(tanh_float64(-M_PI), tanh(-M_PI));
+  VerifyFuzzyEquals(tanh_int32(0), tanh(0));
+  VerifyFuzzyEquals(tanh_int64(0), tanh(0));
+
+  // Atan2
+  VerifyFuzzyEquals(atan2_float32_float32(1, 0), atan2(1, 0));
+  VerifyFuzzyEquals(atan2_float32_float32(-1.0, 0), atan2(-1, 0));
+  VerifyFuzzyEquals(atan2_float64_float64(1.0, 0.0), atan2(1, 0));
+  VerifyFuzzyEquals(atan2_float64_float64(-1, 0), atan2(-1, 0));
+  VerifyFuzzyEquals(atan2_int32_int32(1, 0), atan2(1, 0));
+  VerifyFuzzyEquals(atan2_int64_int64(-1, 0), atan2(-1, 0));
+
+  // Radians
+  VerifyFuzzyEquals(radians_float32(0), 0);
+  VerifyFuzzyEquals(radians_float32(180.0), M_PI);
+  VerifyFuzzyEquals(radians_float32(90.0), M_PI / 2);
+  VerifyFuzzyEquals(radians_float64(0), 0);
+  VerifyFuzzyEquals(radians_float64(180.0), M_PI);
+  VerifyFuzzyEquals(radians_float64(90.0), M_PI / 2);
+  VerifyFuzzyEquals(radians_int32(180), M_PI);
+  VerifyFuzzyEquals(radians_int64(90), M_PI / 2);
+
+  // Degrees
+  VerifyFuzzyEquals(degrees_float32(0), 0.0);
+  VerifyFuzzyEquals(degrees_float32(pi_float), 180.0);
+  VerifyFuzzyEquals(degrees_float32(pi_float / 2), 90.0);
+  VerifyFuzzyEquals(degrees_float64(0), 0.0);
+  VerifyFuzzyEquals(degrees_float64(M_PI), 180.0);
+  VerifyFuzzyEquals(degrees_float64(M_PI / 2), 90.0);
+  VerifyFuzzyEquals(degrees_int32(1), 57.2958);
+  VerifyFuzzyEquals(degrees_int64(1), 57.2958);
+
+  // Cot
+  VerifyFuzzyEquals(cot_float32(pi_float / 2), tan(M_PI / 2 - M_PI / 2));
+  VerifyFuzzyEquals(cot_float64(M_PI / 2), tan(M_PI / 2 - M_PI / 2));
+}
+
 }  // namespace gandiva
diff --git a/cpp/src/gandiva/precompiled/types.h 
b/cpp/src/gandiva/precompiled/types.h
index 78ac9ec..81bd3a2 100644
--- a/cpp/src/gandiva/precompiled/types.h
+++ b/cpp/src/gandiva/precompiled/types.h
@@ -163,6 +163,57 @@ gdv_float64 log10_int64(gdv_int64);
 gdv_float64 log10_float32(gdv_float32);
 gdv_float64 log10_float64(gdv_float64);
 
+gdv_float64 sin_int32(gdv_int32);
+gdv_float64 sin_int64(gdv_int64);
+gdv_float64 sin_float32(gdv_float32);
+gdv_float64 sin_float64(gdv_float64);
+gdv_float64 cos_int32(gdv_int32);
+gdv_float64 cos_int64(gdv_int64);
+gdv_float64 cos_float32(gdv_float32);
+gdv_float64 cos_float64(gdv_float64);
+gdv_float64 asin_int32(gdv_int32);
+gdv_float64 asin_int64(gdv_int64);
+gdv_float64 asin_float32(gdv_float32);
+gdv_float64 asin_float64(gdv_float64);
+gdv_float64 acos_int32(gdv_int32);
+gdv_float64 acos_int64(gdv_int64);
+gdv_float64 acos_float32(gdv_float32);
+gdv_float64 acos_float64(gdv_float64);
+gdv_float64 tan_int32(gdv_int32);
+gdv_float64 tan_int64(gdv_int64);
+gdv_float64 tan_float32(gdv_float32);
+gdv_float64 tan_float64(gdv_float64);
+gdv_float64 atan_int32(gdv_int32);
+gdv_float64 atan_int64(gdv_int64);
+gdv_float64 atan_float32(gdv_float32);
+gdv_float64 atan_float64(gdv_float64);
+gdv_float64 sinh_int32(gdv_int32);
+gdv_float64 sinh_int64(gdv_int64);
+gdv_float64 sinh_float32(gdv_float32);
+gdv_float64 sinh_float64(gdv_float64);
+gdv_float64 cosh_int32(gdv_int32);
+gdv_float64 cosh_int64(gdv_int64);
+gdv_float64 cosh_float32(gdv_float32);
+gdv_float64 cosh_float64(gdv_float64);
+gdv_float64 tanh_int32(gdv_int32);
+gdv_float64 tanh_int64(gdv_int64);
+gdv_float64 tanh_float32(gdv_float32);
+gdv_float64 tanh_float64(gdv_float64);
+gdv_float64 atan2_int32_int32(gdv_int32 in1, gdv_int32 in2);
+gdv_float64 atan2_int64_int64(gdv_int64 in1, gdv_int64 in2);
+gdv_float64 atan2_float32_float32(gdv_float32 in1, gdv_float32 in2);
+gdv_float64 atan2_float64_float64(gdv_float64 in1, gdv_float64 in2);
+gdv_float64 cot_float32(gdv_float32);
+gdv_float64 cot_float64(gdv_float64);
+gdv_float64 radians_int32(gdv_int32);
+gdv_float64 radians_int64(gdv_int64);
+gdv_float64 radians_float32(gdv_float32);
+gdv_float64 radians_float64(gdv_float64);
+gdv_float64 degrees_int32(gdv_int32);
+gdv_float64 degrees_int64(gdv_int64);
+gdv_float64 degrees_float32(gdv_float32);
+gdv_float64 degrees_float64(gdv_float64);
+
 gdv_int32 bitwise_and_int32_int32(gdv_int32 in1, gdv_int32 in2);
 gdv_int64 bitwise_and_int64_int64(gdv_int64 in1, gdv_int64 in2);
 gdv_int32 bitwise_or_int32_int32(gdv_int32 in1, gdv_int32 in2);
diff --git a/cpp/src/gandiva/tests/projector_test.cc 
b/cpp/src/gandiva/tests/projector_test.cc
index 02988b0..b63af40 100644
--- a/cpp/src/gandiva/tests/projector_test.cc
+++ b/cpp/src/gandiva/tests/projector_test.cc
@@ -15,6 +15,10 @@
 // specific language governing permissions and limitations
 // under the License.
 
+#ifndef M_PI
+#define M_PI 3.14159265358979323846
+#endif
+
 #include "gandiva/projector.h"
 
 #include <gtest/gtest.h>
@@ -356,6 +360,19 @@ TEST_F(TestProjector, TestExtendedMath) {
   auto field_log10 = arrow::field("log10", arrow::float64());
   auto field_logb = arrow::field("logb", arrow::float64());
   auto field_power = arrow::field("power", arrow::float64());
+  auto field_sin = arrow::field("sin", arrow::float64());
+  auto field_cos = arrow::field("cos", arrow::float64());
+  auto field_asin = arrow::field("asin", arrow::float64());
+  auto field_acos = arrow::field("acos", arrow::float64());
+  auto field_tan = arrow::field("tan", arrow::float64());
+  auto field_atan = arrow::field("atan", arrow::float64());
+  auto field_sinh = arrow::field("sinh", arrow::float64());
+  auto field_cosh = arrow::field("cosh", arrow::float64());
+  auto field_tanh = arrow::field("tanh", arrow::float64());
+  auto field_atan2 = arrow::field("atan2", arrow::float64());
+  auto field_cot = arrow::field("cot", arrow::float64());
+  auto field_radians = arrow::field("radians", arrow::float64());
+  auto field_degrees = arrow::field("degrees", arrow::float64());
 
   // Build expression
   auto cbrt_expr = TreeExprBuilder::MakeExpression("cbrt", {field0}, 
field_cbrt);
@@ -365,10 +382,27 @@ TEST_F(TestProjector, TestExtendedMath) {
   auto logb_expr = TreeExprBuilder::MakeExpression("log", {field0, field1}, 
field_logb);
   auto power_expr =
       TreeExprBuilder::MakeExpression("power", {field0, field1}, field_power);
+  auto sin_expr = TreeExprBuilder::MakeExpression("sin", {field0}, field_sin);
+  auto cos_expr = TreeExprBuilder::MakeExpression("cos", {field0}, field_cos);
+  auto asin_expr = TreeExprBuilder::MakeExpression("asin", {field0}, 
field_asin);
+  auto acos_expr = TreeExprBuilder::MakeExpression("acos", {field0}, 
field_acos);
+  auto tan_expr = TreeExprBuilder::MakeExpression("tan", {field0}, field_tan);
+  auto atan_expr = TreeExprBuilder::MakeExpression("atan", {field0}, 
field_atan);
+  auto sinh_expr = TreeExprBuilder::MakeExpression("sinh", {field0}, 
field_sinh);
+  auto cosh_expr = TreeExprBuilder::MakeExpression("cosh", {field0}, 
field_cosh);
+  auto tanh_expr = TreeExprBuilder::MakeExpression("tanh", {field0}, 
field_tanh);
+  auto atan2_expr =
+      TreeExprBuilder::MakeExpression("atan2", {field0, field1}, field_atan2);
+  auto cot_expr = TreeExprBuilder::MakeExpression("cot", {field0}, field_cot);
+  auto radians_expr = TreeExprBuilder::MakeExpression("radians", {field0}, 
field_radians);
+  auto degrees_expr = TreeExprBuilder::MakeExpression("degrees", {field0}, 
field_degrees);
 
   std::shared_ptr<Projector> projector;
   auto status = Projector::Make(
-      schema, {cbrt_expr, exp_expr, log_expr, log10_expr, logb_expr, 
power_expr},
+      schema,
+      {cbrt_expr, exp_expr, log_expr, log10_expr, logb_expr, power_expr, 
sin_expr,
+       cos_expr, asin_expr, acos_expr, tan_expr, atan_expr, sinh_expr, 
cosh_expr,
+       tanh_expr, atan2_expr, cot_expr, radians_expr, degrees_expr},
       TestConfiguration(), &projector);
   EXPECT_TRUE(status.ok());
 
@@ -388,6 +422,19 @@ TEST_F(TestProjector, TestExtendedMath) {
   std::vector<double> log10_vals;
   std::vector<double> logb_vals;
   std::vector<double> power_vals;
+  std::vector<double> sin_vals;
+  std::vector<double> cos_vals;
+  std::vector<double> asin_vals;
+  std::vector<double> acos_vals;
+  std::vector<double> tan_vals;
+  std::vector<double> atan_vals;
+  std::vector<double> sinh_vals;
+  std::vector<double> cosh_vals;
+  std::vector<double> tanh_vals;
+  std::vector<double> atan2_vals;
+  std::vector<double> cot_vals;
+  std::vector<double> radians_vals;
+  std::vector<double> degrees_vals;
   for (int i = 0; i < num_records; i++) {
     cbrt_vals.push_back(static_cast<double>(cbrtl(input0[i])));
     exp_vals.push_back(static_cast<double>(expl(input0[i])));
@@ -395,6 +442,19 @@ TEST_F(TestProjector, TestExtendedMath) {
     log10_vals.push_back(static_cast<double>(log10l(input0[i])));
     logb_vals.push_back(static_cast<double>(logl(input1[i]) / 
logl(input0[i])));
     power_vals.push_back(static_cast<double>(powl(input0[i], input1[i])));
+    sin_vals.push_back(static_cast<double>(sin(input0[i])));
+    cos_vals.push_back(static_cast<double>(cos(input0[i])));
+    asin_vals.push_back(static_cast<double>(asin(input0[i])));
+    acos_vals.push_back(static_cast<double>(acos(input0[i])));
+    tan_vals.push_back(static_cast<double>(tan(input0[i])));
+    atan_vals.push_back(static_cast<double>(atan(input0[i])));
+    sinh_vals.push_back(static_cast<double>(sinh(input0[i])));
+    cosh_vals.push_back(static_cast<double>(cosh(input0[i])));
+    tanh_vals.push_back(static_cast<double>(tanh(input0[i])));
+    atan2_vals.push_back(static_cast<double>(atan2(input0[i], input1[i])));
+    cot_vals.push_back(static_cast<double>(tan(M_PI / 2 - input0[i])));
+    radians_vals.push_back(static_cast<double>(input0[i] * M_PI / 180.0));
+    degrees_vals.push_back(static_cast<double>(input0[i] * 180.0 / M_PI));
   }
   auto expected_cbrt = MakeArrowArray<arrow::DoubleType, double>(cbrt_vals, 
validity);
   auto expected_exp = MakeArrowArray<arrow::DoubleType, double>(exp_vals, 
validity);
@@ -402,7 +462,21 @@ TEST_F(TestProjector, TestExtendedMath) {
   auto expected_log10 = MakeArrowArray<arrow::DoubleType, double>(log10_vals, 
validity);
   auto expected_logb = MakeArrowArray<arrow::DoubleType, double>(logb_vals, 
validity);
   auto expected_power = MakeArrowArray<arrow::DoubleType, double>(power_vals, 
validity);
-
+  auto expected_sin = MakeArrowArray<arrow::DoubleType, double>(sin_vals, 
validity);
+  auto expected_cos = MakeArrowArray<arrow::DoubleType, double>(cos_vals, 
validity);
+  auto expected_asin = MakeArrowArray<arrow::DoubleType, double>(asin_vals, 
validity);
+  auto expected_acos = MakeArrowArray<arrow::DoubleType, double>(acos_vals, 
validity);
+  auto expected_tan = MakeArrowArray<arrow::DoubleType, double>(tan_vals, 
validity);
+  auto expected_atan = MakeArrowArray<arrow::DoubleType, double>(atan_vals, 
validity);
+  auto expected_sinh = MakeArrowArray<arrow::DoubleType, double>(sinh_vals, 
validity);
+  auto expected_cosh = MakeArrowArray<arrow::DoubleType, double>(cosh_vals, 
validity);
+  auto expected_tanh = MakeArrowArray<arrow::DoubleType, double>(tanh_vals, 
validity);
+  auto expected_atan2 = MakeArrowArray<arrow::DoubleType, double>(atan2_vals, 
validity);
+  auto expected_cot = MakeArrowArray<arrow::DoubleType, double>(cot_vals, 
validity);
+  auto expected_radians =
+      MakeArrowArray<arrow::DoubleType, double>(radians_vals, validity);
+  auto expected_degrees =
+      MakeArrowArray<arrow::DoubleType, double>(degrees_vals, validity);
   // prepare input record batch
   auto in_batch = arrow::RecordBatch::Make(schema, num_records, {array0, 
array1});
 
@@ -419,6 +493,19 @@ TEST_F(TestProjector, TestExtendedMath) {
   EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_log10, outputs.at(3), epsilon);
   EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_logb, outputs.at(4), epsilon);
   EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_power, outputs.at(5), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_sin, outputs.at(6), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_cos, outputs.at(7), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_asin, outputs.at(8), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_acos, outputs.at(9), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_tan, outputs.at(10), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_atan, outputs.at(11), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_sinh, outputs.at(12), 1E-08);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_cosh, outputs.at(13), 1E-08);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_tanh, outputs.at(14), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_atan2, outputs.at(15), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_cot, outputs.at(16), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_radians, outputs.at(17), epsilon);
+  EXPECT_ARROW_ARRAY_APPROX_EQUALS(expected_degrees, outputs.at(18), epsilon);
 }
 
 TEST_F(TestProjector, TestFloatLessThan) {

Reply via email to