From 4a2daeb739c535b47834c5b52133bb4ad02fdb6b Mon Sep 17 00:00:00 2001 From: Tpt Date: Mon, 23 Dec 2019 21:47:27 +0100 Subject: [PATCH] Adds back float to decimal casts --- lib/src/model/xsd/decimal.rs | 42 ++++++++++++++++++++++++++++++------ lib/src/sparql/eval.rs | 32 +++++++++++++-------------- 2 files changed, 52 insertions(+), 22 deletions(-) diff --git a/lib/src/model/xsd/decimal.rs b/lib/src/model/xsd/decimal.rs index cc4eb1cf..2517a62a 100644 --- a/lib/src/model/xsd/decimal.rs +++ b/lib/src/model/xsd/decimal.rs @@ -19,6 +19,7 @@ pub struct Decimal { } impl Decimal { + #[inline] pub fn from_le_bytes(bytes: [u8; 16]) -> Self { Self { value: i128::from_le_bytes(bytes), @@ -27,6 +28,7 @@ impl Decimal { } impl> From for Decimal { + #[inline] fn from(value: I) -> Self { let value: i64 = value.into(); Self { @@ -194,6 +196,7 @@ impl fmt::Display for Decimal { impl Neg for Decimal { type Output = Self; + #[inline] fn neg(self) -> Self { Self { value: self.value.neg(), @@ -206,11 +209,13 @@ impl Decimal { (self.value / DECIMAL_PART_POW) as i64 }*/ + #[inline] pub fn to_le_bytes(&self) -> [u8; 16] { self.value.to_le_bytes() } /// [op:numeric-add](https://www.w3.org/TR/xpath-functions/#func-numeric-add) + #[inline] pub fn checked_add(&self, rhs: Self) -> Option { Some(Self { value: self.value.checked_add(rhs.value)?, @@ -218,6 +223,7 @@ impl Decimal { } /// [op:numeric-subtract](https://www.w3.org/TR/xpath-functions/#func-numeric-subtract) + #[inline] pub fn checked_sub(&self, rhs: Self) -> Option { Some(Self { value: self.value.checked_sub(rhs.value)?, @@ -225,6 +231,7 @@ impl Decimal { } /// [op:numeric-multiply](https://www.w3.org/TR/xpath-functions/#func-numeric-multiply) + #[inline] pub fn checked_mul(&self, rhs: Self) -> Option { //TODO: better algorithm to keep precision Some(Self { @@ -236,6 +243,7 @@ impl Decimal { } /// [op:numeric-divide](https://www.w3.org/TR/xpath-functions/#func-numeric-divide) + #[inline] pub fn checked_div(&self, rhs: Self) -> Option { //TODO: better algorithm to keep precision Some(Self { @@ -248,6 +256,7 @@ impl Decimal { } /// [fn:abs](https://www.w3.org/TR/xpath-functions/#func-abs) + #[inline] pub fn abs(&self) -> Decimal { Self { value: self.value.abs(), @@ -255,6 +264,7 @@ impl Decimal { } /// [fn:round](https://www.w3.org/TR/xpath-functions/#func-round) + #[inline] pub fn round(&self) -> Decimal { let value = self.value / DECIMAL_PART_POW_MINUS_ONE; Self { @@ -267,6 +277,7 @@ impl Decimal { } /// [fn:ceiling](https://www.w3.org/TR/xpath-functions/#func-ceiling) + #[inline] pub fn ceil(&self) -> Decimal { Self { value: if self.value >= 0 && self.value % DECIMAL_PART_POW != 0 { @@ -278,6 +289,7 @@ impl Decimal { } /// [fn:floor](https://www.w3.org/TR/xpath-functions/#func-floor) + #[inline] pub fn floor(&self) -> Decimal { Self { value: if self.value >= 0 || self.value % DECIMAL_PART_POW == 0 { @@ -288,14 +300,32 @@ impl Decimal { } } - pub fn to_f32(&self) -> Option { - //TODO: precision? - Some((self.value as f32) / (DECIMAL_PART_POW as f32)) + /// Creates a `Decimal` from a `f32` without taking care of precision + #[inline] + pub fn from_f32(v: f32) -> Self { + Self { + value: (v * (DECIMAL_PART_POW as f32)) as i128, + } + } + + /// Creates a `f32` from a `Decimal` without taking care of precision + #[inline] + pub fn to_f32(&self) -> f32 { + (self.value as f32) / (DECIMAL_PART_POW as f32) + } + + /// Creates a `Decimal` from a `f64` without taking care of precision + #[inline] + pub fn from_f64(v: f64) -> Self { + Self { + value: (v * (DECIMAL_PART_POW as f64)) as i128, + } } - pub fn to_f64(&self) -> Option { - //TODO: precision? - Some((self.value as f64) / (DECIMAL_PART_POW as f64)) + /// Creates a `f64` from a `Decimal` without taking care of precision + #[inline] + pub fn to_f64(&self) -> f64 { + (self.value as f64) / (DECIMAL_PART_POW as f64) } } diff --git a/lib/src/sparql/eval.rs b/lib/src/sparql/eval.rs index a5e196d0..599999ab 100644 --- a/lib/src/sparql/eval.rs +++ b/lib/src/sparql/eval.rs @@ -1328,7 +1328,7 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { EncodedTerm::FloatLiteral(value) => Some(value.to_f64()?.into()), EncodedTerm::DoubleLiteral(value) => Some(value.to_f64()?.into()), EncodedTerm::IntegerLiteral(value) => Some(value.to_f64()?.into()), - EncodedTerm::DecimalLiteral(value) => Some(value.to_f64()?.into()), + EncodedTerm::DecimalLiteral(value) => Some(value.to_f64().into()), EncodedTerm::BooleanLiteral(value) => { Some(if value { 1. as f64 } else { 0. }.into()) } @@ -1341,7 +1341,7 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { EncodedTerm::FloatLiteral(value) => Some(value.to_f32()?.into()), EncodedTerm::DoubleLiteral(value) => Some(value.to_f32()?.into()), EncodedTerm::IntegerLiteral(value) => Some(value.to_f32()?.into()), - EncodedTerm::DecimalLiteral(value) => Some(value.to_f32()?.into()), + EncodedTerm::DecimalLiteral(value) => Some(value.to_f32().into()), EncodedTerm::BooleanLiteral(value) => { Some(if value { 1. as f32 } else { 0. }.into()) } @@ -1362,8 +1362,8 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { _ => None, }, PlanExpression::DecimalCast(e) => match self.eval_expression(e, tuple)? { - //TODO: code EncodedTerm::FloatLiteral(value) => Some(Decimal::from_f32(*value)?.into()), - //TODO: code EncodedTerm::DoubleLiteral(value) => Some(Decimal::from_f64(*value)?.into()), + EncodedTerm::FloatLiteral(value) => Some(Decimal::from_f32(*value).into()), + EncodedTerm::DoubleLiteral(value) => Some(Decimal::from_f64(*value).into()), EncodedTerm::IntegerLiteral(value) => Some(Decimal::from(value).into()), EncodedTerm::DecimalLiteral(value) => Some(value.into()), EncodedTerm::BooleanLiteral(value) => { @@ -1653,7 +1653,7 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { EncodedTerm::FloatLiteral(b) => Some(a == b), EncodedTerm::DoubleLiteral(b) => Some(a.to_f64()? == *b), EncodedTerm::IntegerLiteral(b) => Some(*a == b.to_f32()?), - EncodedTerm::DecimalLiteral(b) => Some(*a == b.to_f32()?), + EncodedTerm::DecimalLiteral(b) => Some(*a == b.to_f32()), EncodedTerm::TypedLiteral { .. } => None, _ => Some(false), }, @@ -1661,7 +1661,7 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { EncodedTerm::FloatLiteral(b) => Some(*a == b.to_f64()?), EncodedTerm::DoubleLiteral(b) => Some(a == b), EncodedTerm::IntegerLiteral(b) => Some(*a == b.to_f64()?), - EncodedTerm::DecimalLiteral(b) => Some(*a == b.to_f64()?), + EncodedTerm::DecimalLiteral(b) => Some(*a == b.to_f64()), EncodedTerm::TypedLiteral { .. } => None, _ => Some(false), }, @@ -1674,8 +1674,8 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { _ => Some(false), }, EncodedTerm::DecimalLiteral(a) => match b { - EncodedTerm::FloatLiteral(b) => Some(a.to_f32()? == *b), - EncodedTerm::DoubleLiteral(b) => Some(a.to_f64()? == *b), + EncodedTerm::FloatLiteral(b) => Some(a.to_f32() == *b), + EncodedTerm::DoubleLiteral(b) => Some(a.to_f64() == *b), EncodedTerm::IntegerLiteral(b) => Some(a == Decimal::from(b)), EncodedTerm::DecimalLiteral(b) => Some(a == b), EncodedTerm::TypedLiteral { .. } => None, @@ -1799,14 +1799,14 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { EncodedTerm::FloatLiteral(b) => (*a).partial_cmp(&*b), EncodedTerm::DoubleLiteral(b) => a.to_f64()?.partial_cmp(&*b), EncodedTerm::IntegerLiteral(b) => (*a).partial_cmp(&b.to_f32()?), - EncodedTerm::DecimalLiteral(b) => (*a).partial_cmp(&b.to_f32()?), + EncodedTerm::DecimalLiteral(b) => (*a).partial_cmp(&b.to_f32()), _ => None, }, EncodedTerm::DoubleLiteral(a) => match b { EncodedTerm::FloatLiteral(b) => (*a).partial_cmp(&b.to_f64()?), EncodedTerm::DoubleLiteral(b) => (*a).partial_cmp(&*b), EncodedTerm::IntegerLiteral(b) => (*a).partial_cmp(&b.to_f64()?), - EncodedTerm::DecimalLiteral(b) => (*a).partial_cmp(&b.to_f64()?), + EncodedTerm::DecimalLiteral(b) => (*a).partial_cmp(&b.to_f64()), _ => None, }, EncodedTerm::IntegerLiteral(a) => match b { @@ -1817,8 +1817,8 @@ impl<'a, S: StoreConnection + 'a> SimpleEvaluator { _ => None, }, EncodedTerm::DecimalLiteral(a) => match b { - EncodedTerm::FloatLiteral(b) => a.to_f32()?.partial_cmp(&*b), - EncodedTerm::DoubleLiteral(b) => a.to_f64()?.partial_cmp(&*b), + EncodedTerm::FloatLiteral(b) => a.to_f32().partial_cmp(&*b), + EncodedTerm::DoubleLiteral(b) => a.to_f64().partial_cmp(&*b), EncodedTerm::IntegerLiteral(b) => a.partial_cmp(&Decimal::from(b)), EncodedTerm::DecimalLiteral(b) => a.partial_cmp(&b), _ => None, @@ -1894,7 +1894,7 @@ impl NumericBinaryOperands { Some(NumericBinaryOperands::Float(*v1, v2.to_f32()?)) } (EncodedTerm::FloatLiteral(v1), EncodedTerm::DecimalLiteral(v2)) => { - Some(NumericBinaryOperands::Float(*v1, v2.to_f32()?)) + Some(NumericBinaryOperands::Float(*v1, v2.to_f32())) } (EncodedTerm::DoubleLiteral(v1), EncodedTerm::FloatLiteral(v2)) => { Some(NumericBinaryOperands::Double(*v1, v2.to_f64()?)) @@ -1906,7 +1906,7 @@ impl NumericBinaryOperands { Some(NumericBinaryOperands::Double(*v1, v2.to_f64()?)) } (EncodedTerm::DoubleLiteral(v1), EncodedTerm::DecimalLiteral(v2)) => { - Some(NumericBinaryOperands::Double(*v1, v2.to_f64()?)) + Some(NumericBinaryOperands::Double(*v1, v2.to_f64())) } (EncodedTerm::IntegerLiteral(v1), EncodedTerm::FloatLiteral(v2)) => { Some(NumericBinaryOperands::Float(v1.to_f32()?, *v2)) @@ -1921,10 +1921,10 @@ impl NumericBinaryOperands { Some(NumericBinaryOperands::Decimal(Decimal::from(v1), v2)) } (EncodedTerm::DecimalLiteral(v1), EncodedTerm::FloatLiteral(v2)) => { - Some(NumericBinaryOperands::Float(v1.to_f32()?, *v2)) + Some(NumericBinaryOperands::Float(v1.to_f32(), *v2)) } (EncodedTerm::DecimalLiteral(v1), EncodedTerm::DoubleLiteral(v2)) => { - Some(NumericBinaryOperands::Double(v1.to_f64()?, *v2)) + Some(NumericBinaryOperands::Double(v1.to_f64(), *v2)) } (EncodedTerm::DecimalLiteral(v1), EncodedTerm::IntegerLiteral(v2)) => { Some(NumericBinaryOperands::Decimal(v1, Decimal::from(v2)))