scratch_test_value/conversions/
to_float.rs1use crate::{ARc, QuirkSink, SNumber, SValue};
2
3pub enum SValueToFloatQ {
5 BoolNotANumber(bool),
7 TextNotANumber(ARc<str>),
9 IntToFloatNotLossless,
11}
12
13pub enum SNumberToFloatQ {
15 IntToFloatNotLossless,
17}
18
19impl SValue {
20 pub fn q_as_float<Q>(&self, sink: &mut Q) -> f64
21 where
22 Q: QuirkSink<SValueToFloatQ>,
23 {
24 match self {
25 Self::Bool(b) => {
26 sink.put(SValueToFloatQ::BoolNotANumber(*b));
27 if *b { 1.0 } else { 0.0 }
28 }
29 Self::Text(t) => {
30 if let Ok(f) = t.parse() {
31 f
32 } else {
33 sink.put(SValueToFloatQ::TextNotANumber(t.clone()));
34 0.0
35 }
36 }
37 Self::Int(i1) => {
38 let f: f64 = (*i1) as f64;
39 let i2 = f as i64;
40 if *i1 != i2 {
41 sink.put(SValueToFloatQ::IntToFloatNotLossless);
42 }
43 f
44 }
45 Self::Float(f) => *f,
46 }
47 }
48}
49impl SNumber {
50 pub fn q_as_float<Q>(&self, sink: &mut Q) -> f64
51 where
52 Q: QuirkSink<SNumberToFloatQ>,
53 {
54 match self {
55 Self::Int(i1) => {
56 let f: f64 = (*i1) as f64;
57 let i2 = f as i64;
58 if *i1 != i2 {
59 sink.put(SNumberToFloatQ::IntToFloatNotLossless);
60 }
61 f
62 }
63 Self::Float(f) => *f,
64 }
65 }
66 pub(crate) fn q_as_float_nan_is_zero<Q>(&self, sink: &mut Q) -> f64
70 where
71 Q: QuirkSink<SNumberToFloatQ>,
72 {
73 let f = self.q_as_float(sink);
74 if f.is_nan() { 0.0 } else { f }
75 }
76}