Skip to content
This repository has been archived by the owner on Feb 18, 2024. It is now read-only.

Commit

Permalink
Add weekday, iso_week and nanosecond extractors
Browse files Browse the repository at this point in the history
  • Loading branch information
VasanthakumarV committed Sep 25, 2021
1 parent d672229 commit c0ca677
Show file tree
Hide file tree
Showing 2 changed files with 77 additions and 0 deletions.
53 changes: 53 additions & 0 deletions src/compute/temporal.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,24 @@ use crate::types::NaturalDataType;

use super::arity::unary;

trait U32Weekday: Datelike {
fn u32_weekday(&self) -> u32 {
self.weekday().number_from_monday()
}
}

impl U32Weekday for chrono::NaiveDateTime {}
impl<T: chrono::TimeZone> U32Weekday for chrono::DateTime<T> {}

trait U32IsoWeek: Datelike {
fn u32_iso_week(&self) -> u32 {
self.iso_week().week()
}
}

impl U32IsoWeek for chrono::NaiveDateTime {}
impl<T: chrono::TimeZone> U32IsoWeek for chrono::DateTime<T> {}

macro_rules! date_like {
($extract:ident, $array:ident, $data_type:path) => {
match $array.data_type() {
Expand Down Expand Up @@ -70,6 +88,20 @@ pub fn day(array: &dyn Array) -> Result<PrimitiveArray<u32>> {
date_like!(day, array, DataType::UInt32)
}

/// Extracts weekday of a temporal array as [`PrimitiveArray<u32>`].
/// Monday is 1, Tuesday is 2, ... Sunday is 7
/// Use [`can_weekday`] to check if this operation is supported for the target [`DataType`]
pub fn weekday(array: &dyn Array) -> Result<PrimitiveArray<u32>> {
date_like!(u32_weekday, array, DataType::UInt32)
}

/// Extracts ISO week of a temporal array as [`PrimitiveArray<u32>`]
/// Value ranges from 1 to 53.
/// Use [`can_iso_week`] to check if this operation is supported for the target [`DataType`]
pub fn iso_week(array: &dyn Array) -> Result<PrimitiveArray<u32>> {
date_like!(u32_iso_week, array, DataType::UInt32)
}

macro_rules! time_like {
($extract:ident, $array:ident, $data_type:path) => {
match $array.data_type() {
Expand Down Expand Up @@ -115,6 +147,12 @@ pub fn second(array: &dyn Array) -> Result<PrimitiveArray<u32>> {
time_like!(second, array, DataType::UInt32)
}

/// Extracts the nanoseconds of a temporal array as [`PrimitiveArray<u32>`].
/// Use [`can_nanosecond`] to check if this operation is supported for the target [`DataType`].
pub fn nanosecond(array: &dyn Array) -> Result<PrimitiveArray<u32>> {
time_like!(nanosecond, array, DataType::UInt32)
}

pub fn date_variants<F, O>(
array: &dyn Array,
data_type: DataType,
Expand Down Expand Up @@ -325,6 +363,16 @@ pub fn can_day(data_type: &DataType) -> bool {
can_date(data_type)
}

/// Checks if an array of type `data_type` can perform weekday operation
pub fn can_weekday(data_type: &DataType) -> bool {
can_date(data_type)
}

/// Checks if an array of type `data_type` can perform ISO week operation
pub fn can_iso_week(data_type: &DataType) -> bool {
can_date(data_type)
}

fn can_date(data_type: &DataType) -> bool {
matches!(
data_type,
Expand Down Expand Up @@ -383,6 +431,11 @@ pub fn can_second(data_type: &DataType) -> bool {
can_time(data_type)
}

/// Checks if an array of type `datatype` can perform nanosecond operation
pub fn can_nanosecond(data_type: &DataType) -> bool {
can_time(data_type)
}

fn can_time(data_type: &DataType) -> bool {
matches!(
data_type,
Expand Down
24 changes: 24 additions & 0 deletions tests/it/compute/temporal.rs
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,30 @@ fn naive_timestamp_micro_hour() {
assert_eq!(result, expected);
}

#[test]
fn date64_weekday() {
let array = Int64Array::from(&[Some(1514764800000), None, Some(86400000)]).to(DataType::Date64);

let result = weekday(&array).unwrap();
let expected = UInt32Array::from(&[Some(1), None, Some(5)]);
assert_eq!(result, expected);
}

#[test]
fn date64_iso_week() {
let array = Int64Array::from(&[
Some(1514764800000),
None,
Some(1515456000000),
Some(1514678400000),
])
.to(DataType::Date64);

let result = iso_week(&array).unwrap();
let expected = UInt32Array::from(&[Some(1), None, Some(2), Some(52)]);
assert_eq!(result, expected);
}

#[test]
fn date64_year() {
let array = Int64Array::from(&[Some(1514764800000), None]).to(DataType::Date64);
Expand Down

0 comments on commit c0ca677

Please sign in to comment.