-
Notifications
You must be signed in to change notification settings - Fork 21
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Convert between Unit of Measurement by means of conversion expressions #911
Comments
To be honest I made this proposal mainly to start a discussion and to have the conclusion documented :) The more I think about it, the more I actually like the idea, but also the more I think this is quite unfeasible to do. |
I believe this is covered by this proposal #892, which aims to make it easier to convert to/from measures. If not, please elaborate in what it does differently (I'm aware that I may just not understand your suggestion well enough ;) |
@abelbraaksma I believe that proposal is about converting to and from the primitive so I propose we allow the conversions between nthose UoMs to happen automatically when a conversion expression is defined. So anytime the compiler expects an AFAIK this is not yet possible and the compiler will not allow something like this: let speed distance time =
distance / time
speed 1<m> 1<s> // -> 1<m/s>
speed 1<km> 1<s> // compiler error And with my limited understanding there's only one proper way to do this currently let inline convertToMeter <kilometer:int<kilometer> : int<meter> =
(kilometer |> int |>LanguagePrimitives.IntWithMeasure) * 1000
let speed distance time =
distance / time
speed 1<m> 1<s> // -> 1<m/s>
speed (convertToMeter 1<km>) 1<s> // -> 1<m/s>
this starts to break down when you also want to arbitrarily convert km -> m -> cm -> nm etc. As you need to define all conversions upfront whereas if you can somehow define a measurement in terms of another measurement the compiler can figure out how to do the conversion for you. I realize this might break with the don't implicitly convert, but maybe a syntax can be added for that as well, to opt-in to the conversion per statement, for example: let speed distance time =
distance / time
speed 1<m> 1<s>
speed 1<km>* 1<s> where * would obviously need to be something that is not yet in use. |
I understand it better now, thanks. Given the other proposal, this would be easier to define, but I agree, it wouldn't be automatic. I'm not sure I personally agree to the implicit nature (this could cause backward compat issues, maybe), and perhaps it would be better to allow defining this on the measure type itself. But the idea is intriguing now that I understand it better :) |
There is indeed some overlap between the proposals. Whereas yours deals mainly with conversion, this one is maybe more about being able to define one UoM in terms of another through some means in such a way that the conversion can help you eliminate tedious manual conversions (possibly even at compile time). |
I understand the suggestion, however this was effectively decided in F# 2.0 - units of measure do not allow equivalence-up-to-conversion, and so units like It is a deep alteration to UoM to allow scaling , and while the specific language feature above to declare scalings is not a bad suggestion, it's just a fundamental reworking of the assumptions underlying the whole feature. |
What if the units were still declared and considered as independent, but the ergonomics of converting them by user code would be eased by the use of implicit conversions? The following code works as of today, but of course it is not nice to use.
|
Convert between Unit of Measurement by means of conversion expressions
After seeing a discussion on Reddit and searching the issues here I propose we allow for compound units of measurement. Take for example this code
Once you get in the realm of more complicated units like
N m/s
and multiplying those withkN km/h
and such I think the real benefits will start to show.The existing way of approaching this problem in F# is to define a conversion method to do this calculation for you and call this manually each time you want the conversion to happen and to create these conversion functions for converting between all possible units, whereas with this maybe something like the following will be possible
Pros and Cons
The advantages of making this adjustment to F# are making UoM more expressive and code easier to read.
The disadvantages of making this adjustment to F# are yet another feature which will make the language more expressive, but also more complicated.
Extra information
Estimated cost (XS, S, M, L, XL, XXL): probably not trivial to implement.
Related suggestions: (put links to related suggestions here)
Affidavit (please submit!)
Please tick this by placing a cross in the box:
Please tick all that apply:
For Readers
If you would like to see this issue implemented, please click the 👍 emoji on this issue. These counts are used to generally order the suggestions by engagement.
The text was updated successfully, but these errors were encountered: