1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
use std::ops::Add;
use std::ops::Sub;
use std::ops::Mul;
use std::ops::Div;
use std::cmp::PartialEq;
use ::si_units::*;
#[macro_export] macro_rules! convert_unit {
($i1:ident, $i2:ident, $e1:expr, $e2:expr) => {
impl From<$i1> for $i2 {
fn from($i1(value): $i1) -> Self {
$i2($e1(value))
}
}
impl From<$i2> for $i1 {
fn from($i2(value): $i2) -> Self {
$i1($e2(value))
}
}
};
($i1:ident, $i2:ident, $i3:ident) => {
impl From<$i1> for $i2 {
fn from($i1(value): $i1) -> Self {
$i2(value * $i3)
}
}
impl From<$i2> for $i1 {
fn from($i2(value): $i2) -> Self {
$i1(value / $i3)
}
}
};
}
const METER_TO_FOOT: f64 = 3.28084;
const METER_TO_YARD: f64 = 1.09361;
const METER_TO_MILE: f64 = 0.000621371;
const METER_TO_KILOMETER: f64 = 1.0e-3;
const METER_TO_MILIMETER: f64 = 1.0e+3;
const METER_TO_MICROMETER: f64 = 1.0e+6;
const METER_TO_NANOMETER: f64 = 1.0e+9;
const METER_TO_ASTRONOMICALUNIT: f64 = 1.0 / 149597870700.0;
const METER_TO_LIGHTYEAR: f64 = 1.0 / 9.4607e15;
const METER_TO_PARSEC: f64 = 1.0 / 3.08567758149137e16;
const SECOND_TO_MINUTE: f64 = 60.0;
const SECOND_TO_HOUR: f64 = 60.0 * 60.0;
const SECOND_TO_DAY: f64 = 60.0 * 60.0 * 24.0;
const SECOND_TO_WEEK: f64 = SECOND_TO_DAY * 7.0;
const SECOND_TO_MONTH: f64 = SECOND_TO_DAY * 30.0;
const SECOND_TO_MONTH_AVG: f64 = SECOND_TO_DAY * 30.42;
const SECOND_TO_MONTH_AVG_LEAP: f64 = SECOND_TO_DAY * 30.50;
const SECOND_TO_MONTH_SOLAR: f64 = SECOND_TO_DAY * 30.44;
const SECOND_TO_MONTH_LUNAR: f64 = SECOND_TO_DAY * 29.53;
const SECOND_TO_YEAR: f64 = SECOND_TO_DAY * 365.25;
const SECOND_TO_MIL_YEAR: f64 = SECOND_TO_YEAR * 1.0e6;
const DEGC_TO_KELVIN: f64 = 273.15;
init_unit!(Foot);
init_unit!(Yard);
init_unit!(Mile);
convert_unit!(Meter, Foot, METER_TO_FOOT);
convert_unit!(Meter, Yard, METER_TO_YARD);
convert_unit!(Meter, Mile, METER_TO_MILE);
init_unit!(Kilometer);
init_unit!(Milimeter);
init_unit!(Micrometer);
init_unit!(Nanometer);
convert_unit!(Meter, Kilometer, METER_TO_KILOMETER);
convert_unit!(Meter, Milimeter, METER_TO_MILIMETER);
convert_unit!(Meter, Micrometer, METER_TO_MICROMETER);
convert_unit!(Meter, Nanometer, METER_TO_NANOMETER);
init_unit!(AstronomicalUnit);
init_unit!(LightYear);
init_unit!(Parsec);
convert_unit!(Meter, AstronomicalUnit, METER_TO_ASTRONOMICALUNIT);
convert_unit!(Meter, LightYear, METER_TO_LIGHTYEAR);
convert_unit!(Meter, Parsec, METER_TO_PARSEC);
init_unit!(Minute);
init_unit!(Hour);
init_unit!(Day);
init_unit!(Week);
init_unit!(Month);
init_unit!(Year);
init_unit!(MilYear);
convert_unit!(Second, Minute, SECOND_TO_MINUTE);
convert_unit!(Second, Hour, SECOND_TO_HOUR);
convert_unit!(Second, Day, SECOND_TO_DAY);
convert_unit!(Second, Week, SECOND_TO_WEEK);
convert_unit!(Second, Month, SECOND_TO_MONTH);
convert_unit!(Second, Year, SECOND_TO_YEAR);
convert_unit!(Second, MilYear, SECOND_TO_MIL_YEAR);
init_unit!(Fahrenheit);
convert_unit!(DegC, Kelvin, |value| {value + DEGC_TO_KELVIN}, |value| {value - DEGC_TO_KELVIN});
convert_unit!(DegC, Fahrenheit, |value| {(value * 1.8) + 32.0}, |value| {(value - 32.0) / 1.8});