I’m using Unitful for the first time and would like direction on the proper way to use it. For my use case, I am creating a struct that I would like to store a specific unit because the value is being passed to such things as xml file creation and cli programs as only a number. I’d like conversion of the to happen at construction, rather than having to do something like uconvert(u"output-unit", someQuantity)
every place the raw number has to be passed to the external applications.
In my first implementation that works, I had a struct similar to the following:
struct MyStruct
value::typeof(1.0u"cm^-3")
end
I thought this was too restricting because I may want to allow Int
or something for the quantity, so I changed my struct to the following:
struct MyStruct
value::Unitful.Quantity{<:Real, Unitful.𝐋^-3, u"cm^-3"}
end
But when I try to construct an instance, I get the following error:
ERROR: MethodError: no method matching Quantity{#s92495,𝐋^-3,cm^-3} where #s92495<:Real(::Quantity{Int64,𝐋^-3,Unitful.FreeUnits{(cm^-3,),𝐋^-3,nothing}})
To experiment with different types, I discovered the following
julia> typeof(1.0u"cm^-3")
Quantity{Float64,𝐋^-3,Unitful.FreeUnits{(cm^-3,),𝐋^-3,nothing}}
julia> typeof(1.0u"cm^-3") <: typeof(1.0u"cm^-3")
true
julia> typeof(1.0u"cm^-3") <: Unitful.Quantity{Float64, Unitful.𝐋^-3,Unitful.FreeUnits{( Unitful.cm^-3,), Unitful.𝐋^-3,nothing}}
false
That is a surprising result that I don’t understand.
Which leads me to why I asking a question. What is the proper way to force a specific Unit
in the struct or a function signature? Also, what is best practice? I would normally expect to use something like Quantity{<:Real, 𝐋^-3}
, but for my specific case it seems safer to force the Unit as well to avoid having to remember do uconvert
with the correct type everywhere when I am interfacing with external applications.