2 | import public Data.List.Quantifiers.Extra
3 | import public Data.Refined
4 | import public Data.Refined.Bits16
5 | import public Data.Refined.Bits8
6 | import public Data.Refined.Int8
8 | import Derive.Prelude
9 | import Derive.Refined
12 | %language ElabReflection
20 | 0 IsAtomicNr : Bits8 -> Type
21 | IsAtomicNr = FromTo 1 118
25 | record AtomicNr where
26 | constructor MkAtomicNr
28 | {auto 0 prf : IsAtomicNr value}
31 | %runElab derive "AtomicNr" [Show,Eq,Ord,RefinedInteger]
39 | constructor MkMassNr
41 | {auto 0 prf : FromTo 1 511 value}
44 | Interpolation MassNr where
45 | interpolate = show . value
48 | %runElab derive "MassNr" [Show,Eq,Ord,RefinedInteger]
54 | public export %inline
55 | MinAbundanceValue : Double
56 | MinAbundanceValue = 1.0e-100
59 | IsAbundance : Double -> Bool
60 | IsAbundance v = v >= MinAbundanceValue && v <= 1.0
63 | record Abundance where
64 | constructor MkAbundance
66 | {auto 0 prf : Holds IsAbundance value}
69 | Interpolation Abundance where
70 | interpolate = show . value
73 | %runElab derive "Abundance" [Show,Eq,Ord,RefinedDouble]
75 | public export %inline
76 | multAbundance : Abundance -> Abundance -> Abundance
77 | multAbundance a1 a2 =
78 | let res = a1.value * a2.value
79 | in case hdec0 {p = Holds IsAbundance} res of
80 | Just0 _ => MkAbundance res
81 | Nothing0 => 1.0e-100
83 | public export %inline
84 | Semigroup Abundance where
85 | (<+>) = multAbundance
87 | public export %inline
88 | Monoid Abundance where
100 | public export %inline
101 | MaxMolecularMass : Double
102 | MaxMolecularMass = 1.0e60
104 | public export %inline
105 | IsMolecularMass : Double -> Bool
106 | IsMolecularMass v = v >= 0.0 && v <= MaxMolecularMass
110 | record MolecularMass where
111 | constructor MkMolecularMass
113 | {auto 0 prf : Holds IsMolecularMass value}
116 | Interpolation MolecularMass where
117 | interpolate = show . value
119 | namespace MolecularMass
120 | %runElab derive "MolecularMass" [Show,Eq,Ord,RefinedDouble]
122 | public export %inline
123 | addMolecularMass : MolecularMass -> MolecularMass -> MolecularMass
124 | addMolecularMass a1 a2 =
125 | let res = a1.value + a2.value
126 | in case hdec0 {p = Holds IsMolecularMass} res of
127 | Just0 _ => MkMolecularMass res
130 | public export %inline
131 | multMolecularMass : Nat -> MolecularMass -> MolecularMass
132 | multMolecularMass a1 a2 =
133 | let res = cast a1 * a2.value
134 | in case hdec0 {p = Holds IsMolecularMass} res of
135 | Just0 _ => MkMolecularMass res
138 | public export %inline
139 | Semigroup MolecularMass where
140 | (<+>) = addMolecularMass
142 | public export %inline
143 | Monoid MolecularMass where
152 | record MolarMass where
153 | constructor MkMolarMass
157 | {auto 0 prf : Holds IsMolecularMass value}
160 | Interpolation MolarMass where
161 | interpolate = show . value
163 | namespace MolarMass
164 | %runElab derive "MolarMass" [Show,Eq,Ord,RefinedDouble]
167 | molarMass : Double -> MolarMass
169 | case hdec0 {p = Holds IsMolecularMass} v of
170 | Just0 _ => MkMolarMass v
171 | Nothing0 => if v < 0.0 then 0 else 1.0e60
174 | addMolarMass : MolarMass -> MolarMass -> MolarMass
175 | addMolarMass a1 a2 = molarMass (a1.value + a2.value)
178 | Semigroup MolarMass where
179 | (<+>) = addMolarMass
182 | Monoid MolarMass where
186 | Cast MolecularMass MolarMass where
187 | cast (MkMolecularMass v) = MkMolarMass v
190 | Cast MolarMass MolecularMass where
191 | cast (MkMolarMass v) = MkMolecularMass v
194 | interface HasMolarMass a where
198 | mass : a -> MolarMass
203 | exactMass : a -> MolarMass
206 | multByAbundance : Abundance -> MolarMass -> MolarMass
207 | multByAbundance a m = molarMass (a.value * m.value)
214 | record Charge where
215 | constructor MkCharge
217 | {auto 0 prf : FromTo (-
15) 15 value}
220 | Interpolation Charge where
221 | interpolate = show . value
224 | %runElab derive "Charge" [Show,Eq,Ord,RefinedInteger]
227 | Finite Charge where
228 | values = mapMaybe refineCharge [(-
16)..16]
234 | incCharge : Charge -> Charge
236 | case refineCharge $
x.value+1 of
244 | decCharge : Charge -> Charge
246 | case refineCharge $
x.value-1 of
255 | record HCount where
256 | constructor MkHCount
258 | {auto 0 prf : value < 10}
261 | Interpolation HCount where
262 | interpolate = show . value
265 | %runElab derive "HCount" [Show,Eq,Ord,RefinedInteger]
268 | Finite HCount where
269 | values = mapMaybe refineHCount [0..9]
287 | %runElab derive "NoH" [Show,Eq,Ord]
295 | data Radical = NoRadical | Singlet | Doublet | Triplet
297 | %runElab derive "Radical" [Show,Eq,Ord,Finite]
305 | data Hybridization : Type where
306 | None : Hybridization
307 | Planar : Hybridization
310 | SP2 : Hybridization
311 | SP3 : Hybridization
312 | SP3D1 : Hybridization
313 | SP3D2 : Hybridization
314 | Tetrahedral : Hybridization
315 | Octahedral : Hybridization
317 | %runElab derive "Hybridization" [Show,Eq,Ord,Finite]
324 | data BondOrder = Single | Dbl | Triple
327 | Interpolation BondOrder where
328 | interpolate Single = "1"
329 | interpolate Dbl = "2"
330 | interpolate Triple = "3"
332 | %runElab derive "BondOrder" [Eq,Show,Ord]
339 | 0 ChemRes : List Type -> Type -> Type
340 | ChemRes es x = Either (HSum es) x