@@ -57,7 +57,9 @@ use super::SimpleDomain;
5757use super :: SimpleType ;
5858use super :: SimpleValueType ;
5959use super :: ValueType ;
60+ use crate :: types:: CoreNumber ;
6061use crate :: types:: DataType ;
62+ use crate :: types:: F64 ;
6163use crate :: utils:: arrow:: buffer_into_mut;
6264use crate :: with_decimal_mapped_type;
6365use crate :: with_decimal_type;
@@ -71,11 +73,15 @@ use crate::Value;
7173#[ derive( Debug , Clone , PartialEq , Eq ) ]
7274pub struct CoreDecimal < T : Decimal > ( PhantomData < T > ) ;
7375
76+ #[ derive( Debug , Clone , PartialEq , Eq ) ]
77+ pub struct CoreScalarDecimal < T : Decimal > ( PhantomData < T > ) ;
78+
7479pub type Decimal64Type = DecimalType < i64 > ;
7580pub type Decimal128Type = DecimalType < i128 > ;
7681pub type Decimal256Type = DecimalType < i256 > ;
7782
7883pub type DecimalType < T > = SimpleValueType < CoreDecimal < T > > ;
84+ pub type DecimalScalarType < T > = SimpleValueType < CoreScalarDecimal < T > > ;
7985
8086impl < Num : Decimal > SimpleType for CoreDecimal < Num > {
8187 type Scalar = Num ;
@@ -149,6 +155,95 @@ impl<Num: Decimal> SimpleType for CoreDecimal<Num> {
149155 }
150156}
151157
158+ impl < Num : Decimal > SimpleType for CoreScalarDecimal < Num > {
159+ type Scalar = ( Num , DecimalSize ) ;
160+ type Domain = SimpleDomain < ( Num , DecimalSize ) > ;
161+
162+ fn downcast_scalar ( scalar : & ScalarRef ) -> Option < Self :: Scalar > {
163+ let scalar = scalar. as_decimal ( ) ?;
164+ Num :: try_downcast_scalar ( scalar) . map ( |v| ( v, scalar. size ( ) ) )
165+ }
166+
167+ fn downcast_column ( col : & Column ) -> Option < Buffer < Self :: Scalar > > {
168+ Num :: try_downcast_column ( col) . map ( |( col, x) | col. into_iter ( ) . map ( |v| ( v, x) ) . collect ( ) )
169+ }
170+
171+ fn downcast_domain ( domain : & Domain ) -> Option < Self :: Domain > {
172+ let size = domain. as_decimal ( ) ?. decimal_size ( ) ;
173+ let domain = Num :: try_downcast_domain ( domain. as_decimal ( ) ?) ?;
174+ Some ( SimpleDomain {
175+ min : ( domain. min , size) ,
176+ max : ( domain. max , size) ,
177+ } )
178+ }
179+
180+ // It's not allowed to call downcast_builder temporarily
181+ fn downcast_builder ( _builder : & mut ColumnBuilder ) -> Option < & mut Vec < Self :: Scalar > > {
182+ None
183+ }
184+
185+ fn downcast_owned_builder ( builder : ColumnBuilder ) -> Option < Vec < Self :: Scalar > > {
186+ let size = builder. as_decimal ( ) ?. decimal_size ( ) ;
187+ let b = Num :: try_downcast_owned_builder ( builder) ;
188+ b. map ( |v| v. into_iter ( ) . map ( |v| ( v, size) ) . collect ( ) )
189+ }
190+
191+ fn upcast_column_builder (
192+ builder : Vec < Self :: Scalar > ,
193+ data_type : & DataType ,
194+ ) -> Option < ColumnBuilder > {
195+ Some ( ColumnBuilder :: Decimal ( Num :: upcast_builder (
196+ builder. into_iter ( ) . map ( |( v, _) | v) . collect ( ) ,
197+ * data_type. as_decimal ( ) . unwrap ( ) ,
198+ ) ) )
199+ }
200+
201+ fn upcast_scalar ( scalar : Self :: Scalar , data_type : & DataType ) -> Scalar {
202+ let size = * data_type. as_decimal ( ) . unwrap ( ) ;
203+ Num :: upcast_scalar ( scalar. 0 , size)
204+ }
205+
206+ fn upcast_column ( col : Buffer < Self :: Scalar > , data_type : & DataType ) -> Column {
207+ let col = col. into_iter ( ) . map ( |( v, _) | v) . collect ( ) ;
208+ let size = * data_type. as_decimal ( ) . unwrap ( ) ;
209+ Num :: upcast_column ( col, size)
210+ }
211+
212+ fn upcast_domain ( domain : Self :: Domain , data_type : & DataType ) -> Domain {
213+ let domain = SimpleDomain {
214+ min : domain. min . 0 ,
215+ max : domain. max . 0 ,
216+ } ;
217+ let size = * data_type. as_decimal ( ) . unwrap ( ) ;
218+ Num :: upcast_domain ( domain, size)
219+ }
220+
221+ #[ inline( always) ]
222+ fn compare ( lhs : & Self :: Scalar , rhs : & Self :: Scalar ) -> Ordering {
223+ lhs. cmp ( rhs)
224+ }
225+
226+ #[ inline( always) ]
227+ fn greater_than ( left : & Self :: Scalar , right : & Self :: Scalar ) -> bool {
228+ left > right
229+ }
230+
231+ #[ inline( always) ]
232+ fn greater_than_equal ( left : & Self :: Scalar , right : & Self :: Scalar ) -> bool {
233+ left >= right
234+ }
235+
236+ #[ inline( always) ]
237+ fn less_than ( left : & Self :: Scalar , right : & Self :: Scalar ) -> bool {
238+ left < right
239+ }
240+
241+ #[ inline( always) ]
242+ fn less_than_equal ( left : & Self :: Scalar , right : & Self :: Scalar ) -> bool {
243+ left <= right
244+ }
245+ }
246+
152247impl < Num : Decimal > DecimalType < Num > {
153248 pub fn full_domain ( size : & DecimalSize ) -> SimpleDomain < Num > {
154249 SimpleDomain {
@@ -200,6 +295,12 @@ impl DecimalScalar {
200295 } )
201296 }
202297
298+ pub fn scale ( & self ) -> u8 {
299+ with_decimal_type ! ( |DECIMAL | match self {
300+ DecimalScalar :: DECIMAL ( _, size) => size. scale,
301+ } )
302+ }
303+
203304 pub fn as_decimal < D : Decimal > ( & self ) -> D {
204305 with_decimal_type ! ( |DECIMAL | match self {
205306 DecimalScalar :: DECIMAL ( value, _) => value. as_decimal( ) ,
@@ -249,6 +350,8 @@ impl DecimalDomain {
249350 Copy ,
250351 PartialEq ,
251352 Eq ,
353+ PartialOrd ,
354+ Ord ,
252355 Hash ,
253356 Serialize ,
254357 Deserialize ,
@@ -260,6 +363,15 @@ pub struct DecimalSize {
260363 scale : u8 ,
261364}
262365
366+ impl Default for DecimalSize {
367+ fn default ( ) -> Self {
368+ DecimalSize {
369+ precision : 15 ,
370+ scale : 2 ,
371+ }
372+ }
373+ }
374+
263375impl DecimalSize {
264376 pub fn new_unchecked ( precision : u8 , scale : u8 ) -> DecimalSize {
265377 DecimalSize { precision, scale }
@@ -2807,6 +2919,8 @@ impl Ord for i256 {
28072919}
28082920
28092921pub type DecimalView < F , T > = ComputeView < DecimalConvert < F , T > , CoreDecimal < F > , CoreDecimal < T > > ;
2922+ pub type DecimalF64View < F > =
2923+ ComputeView < DecimalConvert < F , F64 > , CoreScalarDecimal < F > , CoreNumber < F64 > > ;
28102924
28112925#[ derive( Debug , Clone , PartialEq , Eq , Default ) ]
28122926pub struct DecimalConvert < F , T > ( std:: marker:: PhantomData < ( F , T ) > ) ;
@@ -2829,10 +2943,32 @@ where
28292943 }
28302944}
28312945
2946+ impl < F > Compute < CoreScalarDecimal < F > , CoreNumber < F64 > > for DecimalConvert < F , F64 >
2947+ where F : Decimal
2948+ {
2949+ #[ inline]
2950+ fn compute ( value : & ( F , DecimalSize ) ) -> F64 {
2951+ value. 0 . to_float64 ( value. 1 . scale ( ) ) . into ( )
2952+ }
2953+
2954+ fn compute_domain ( domain : & SimpleDomain < ( F , DecimalSize ) > ) -> SimpleDomain < F64 > {
2955+ let min = domain. min . 0 . to_float64 ( domain. min . 1 . scale ( ) ) ;
2956+ let max = domain. max . 0 . to_float64 ( domain. max . 1 . scale ( ) ) ;
2957+
2958+ SimpleDomain {
2959+ min : min. into ( ) ,
2960+ max : max. into ( ) ,
2961+ }
2962+ }
2963+ }
2964+
2965+ pub type Decimal64AsF64Type = DecimalF64View < i64 > ;
2966+ pub type Decimal128AsF64Type = DecimalF64View < i128 > ;
2967+ pub type Decimal256AsF64Type = DecimalF64View < i256 > ;
2968+
28322969macro_rules! decimal_convert_type {
28332970 ( $from: ty, $to: ty, $alias: ident, $compat: ident) => {
2834- pub type $alias =
2835- ComputeView <DecimalConvert <$from, $to>, CoreDecimal <$from>, CoreDecimal <$to>>;
2971+ pub type $alias = DecimalView <$from, $to>;
28362972 pub type $compat = DecimalConvert <$from, $to>;
28372973 } ;
28382974}
0 commit comments