Skip to content

Commit

Permalink
Use Option instead of Result for overflow errors
Browse files Browse the repository at this point in the history
  • Loading branch information
alexandreyc committed Jul 24, 2023
1 parent 35fcf09 commit 0e2b58e
Show file tree
Hide file tree
Showing 2 changed files with 131 additions and 110 deletions.
96 changes: 67 additions & 29 deletions arrow-arith/src/numeric.rs
Original file line number Diff line number Diff line change
Expand Up @@ -346,51 +346,41 @@ fn float_op<T: ArrowPrimitiveType>(
trait TimestampOp: ArrowTimestampType {
type Duration: ArrowPrimitiveType<Native = i64>;

fn add_year_month(timestamp: i64, delta: i32, tz: Tz) -> Result<i64, ArrowError>;
fn add_day_time(timestamp: i64, delta: i64, tz: Tz) -> Result<i64, ArrowError>;
fn add_month_day_nano(timestamp: i64, delta: i128, tz: Tz)
-> Result<i64, ArrowError>;

fn sub_year_month(timestamp: i64, delta: i32, tz: Tz) -> Result<i64, ArrowError>;
fn sub_day_time(timestamp: i64, delta: i64, tz: Tz) -> Result<i64, ArrowError>;
fn sub_month_day_nano(timestamp: i64, delta: i128, tz: Tz)
-> Result<i64, ArrowError>;
fn add_year_month(timestamp: i64, delta: i32, tz: Tz) -> Option<i64>;
fn add_day_time(timestamp: i64, delta: i64, tz: Tz) -> Option<i64>;
fn add_month_day_nano(timestamp: i64, delta: i128, tz: Tz) -> Option<i64>;

fn sub_year_month(timestamp: i64, delta: i32, tz: Tz) -> Option<i64>;
fn sub_day_time(timestamp: i64, delta: i64, tz: Tz) -> Option<i64>;
fn sub_month_day_nano(timestamp: i64, delta: i128, tz: Tz) -> Option<i64>;
}

macro_rules! timestamp {
($t:ty, $d:ty) => {
impl TimestampOp for $t {
type Duration = $d;

fn add_year_month(left: i64, right: i32, tz: Tz) -> Result<i64, ArrowError> {
fn add_year_month(left: i64, right: i32, tz: Tz) -> Option<i64> {
Self::add_year_months(left, right, tz)
}

fn add_day_time(left: i64, right: i64, tz: Tz) -> Result<i64, ArrowError> {
fn add_day_time(left: i64, right: i64, tz: Tz) -> Option<i64> {
Self::add_day_time(left, right, tz)
}

fn add_month_day_nano(
left: i64,
right: i128,
tz: Tz,
) -> Result<i64, ArrowError> {
fn add_month_day_nano(left: i64, right: i128, tz: Tz) -> Option<i64> {
Self::add_month_day_nano(left, right, tz)
}

fn sub_year_month(left: i64, right: i32, tz: Tz) -> Result<i64, ArrowError> {
fn sub_year_month(left: i64, right: i32, tz: Tz) -> Option<i64> {
Self::subtract_year_months(left, right, tz)
}

fn sub_day_time(left: i64, right: i64, tz: Tz) -> Result<i64, ArrowError> {
fn sub_day_time(left: i64, right: i64, tz: Tz) -> Option<i64> {
Self::subtract_day_time(left, right, tz)
}

fn sub_month_day_nano(
left: i64,
right: i128,
tz: Tz,
) -> Result<i64, ArrowError> {
fn sub_month_day_nano(left: i64, right: i128, tz: Tz) -> Option<i64> {
Self::subtract_month_day_nano(left, right, tz)
}
}
Expand Down Expand Up @@ -432,29 +422,77 @@ fn timestamp_op<T: TimestampOp>(

(Op::Add | Op::AddWrapping, Interval(YearMonth)) => {
let r = r.as_primitive::<IntervalYearMonthType>();
try_op!(l, l_s, r, r_s, T::add_year_month(l, r, l_tz))
try_op!(
l,
l_s,
r,
r_s,
T::add_year_month(l, r, l_tz).ok_or(ArrowError::ComputeError(
"Timestamp out of range".to_string()
))
)
}
(Op::Sub | Op::SubWrapping, Interval(YearMonth)) => {
let r = r.as_primitive::<IntervalYearMonthType>();
try_op!(l, l_s, r, r_s, T::sub_year_month(l, r, l_tz))
try_op!(
l,
l_s,
r,
r_s,
T::sub_year_month(l, r, l_tz).ok_or(ArrowError::ComputeError(
"Timestamp out of range".to_string()
))
)
}

(Op::Add | Op::AddWrapping, Interval(DayTime)) => {
let r = r.as_primitive::<IntervalDayTimeType>();
try_op!(l, l_s, r, r_s, T::add_day_time(l, r, l_tz))
try_op!(
l,
l_s,
r,
r_s,
T::add_day_time(l, r, l_tz).ok_or(ArrowError::ComputeError(
"Timestamp out of range".to_string()
))
)
}
(Op::Sub | Op::SubWrapping, Interval(DayTime)) => {
let r = r.as_primitive::<IntervalDayTimeType>();
try_op!(l, l_s, r, r_s, T::sub_day_time(l, r, l_tz))
try_op!(
l,
l_s,
r,
r_s,
T::sub_day_time(l, r, l_tz).ok_or(ArrowError::ComputeError(
"Timestamp out of range".to_string()
))
)
}

(Op::Add | Op::AddWrapping, Interval(MonthDayNano)) => {
let r = r.as_primitive::<IntervalMonthDayNanoType>();
try_op!(l, l_s, r, r_s, T::add_month_day_nano(l, r, l_tz))
try_op!(
l,
l_s,
r,
r_s,
T::add_month_day_nano(l, r, l_tz).ok_or(ArrowError::ComputeError(
"Timestamp out of range".to_string()
))
)
}
(Op::Sub | Op::SubWrapping, Interval(MonthDayNano)) => {
let r = r.as_primitive::<IntervalMonthDayNanoType>();
try_op!(l, l_s, r, r_s, T::sub_month_day_nano(l, r, l_tz))
try_op!(
l,
l_s,
r,
r_s,
T::sub_month_day_nano(l, r, l_tz).ok_or(ArrowError::ComputeError(
"Timestamp out of range".to_string()
))
)
}
_ => {
return Err(ArrowError::InvalidArgumentError(format!(
Expand Down
Loading

0 comments on commit 0e2b58e

Please sign in to comment.