6 ms·
I am not sure this is the only value, but it is generally true. And this is one of the great advantages of haskell. By the way, now that I know some haskell, I
by hristov 7y ago
I am not sure this is the only value, but it is generally true. And this is one of the great advantages of haskell.
By the way, now that I know some haskell, I see this edge case sloppiness all the time and it is really annoying. For example, here is something that annoyed me just recently. You go to yahoo finance and there they will show you the revenues of a company as well as the revenue growth from past year. But sometimes this revenue growth number is not available. For example, the company may not have existed past year, or perhaps it was not public past year and thus it did not publicly disclose its revenues. When they cannot compute revenue growth for these reasons, yahoo finance will helpfully show revenue growth as "N/A", i.e., not available.
That seems all nice and logical, but I noticed that yahoo finance tended to show that revenue growth was not available for many established public companies for which they should have the data. I looked at it more closely and noticed with shock that if the revenue growth of a company was about 0%, yahoo finance would still show it as "N/A"! So some programmer just decided to use 0 as not available and just erased a lot of useful information from their system. Now when I see a company that has N/A as revenue growth on yahoo finance I have to go and check whether the revenue growth was zero, or it was truly unavailable. As I said -- really annoying.
This is of course a textbook case for Haskells Maybe concept. You can have a type that is a Maybe Int, and that means it have a value or it can be Nothing. Thus, you encompass the edge case of not having the value available, without using an embarrassing hack that deletes real data. But of course Haskell gives you more power than just using Maybe. You can create a type that can encompass all kinds of edge cases and information about them. For example, you can embed a reason why the revenue growth data was not available, if that is the case.
- justAnotherNET 7y agoSwift has this as well, but calls them “Optional”. The concept is definitely useful!
- davinic 7y agoAlso Java has Optional<T> and C# has Nullable<T>.
- LessDmesg 7y agoThat's not important in practice. What's important is that null infects all reference types in Java and C#, whether you asked for it or not. Just today I've spent a half an hour looking for a null dereference error - which the type system should've warned me of but didn't. The sad fact is, neither Java nor C# are fixable, because no new feature will fix the broken, null-unsafe code already written. All because of this billion dollar mistake that should've had no place in a GCed language but was blindly copied over from C++. The sooner Java gives way to Kotlin and completely fades into obscurity, the better.
- howellnick 7y agoC# 8.0 introduced "Nullable Reference Types" (https://devblogs.microsoft.com/dotnet/embracing-nullable-reference-types/ https://devblogs.microsoft.com/dotnet/embracing-nullable-ref...), which, if enabled, can help solve this problem.
- deleted 7y ago[deleted]
- navaati 7y ago> was blindly copied over from C++. From C! AFAIK C++'s references can not be null!
- dep_b 7y agoThe big difference is that nullability is the standard in Java and C# while in Swift it's the other way round, it's non-nullable unless you clearly indicate it's not.
- waheoo 7y agoIve noticed other languages with this feature, they call them optional types, you can pass in a null or a type value. /s slightly, maybe more snarky, but seriously, optional types are way overhyped. Null objects are far more useful than optionals. Optionals tend to leak all over the show.
- baseballdork 7y agoI don't understand. In this situation an optional type is a reasonable solution to the problem: None => N/A, Some(0%) => 0%.
- heavenlyblue 7y agoOnly if you are speaking of Scalia?
- swirepe 7y ago>Scalia :)
- Smaug123 7y agoNulls leak exactly as badly as optionals, except it's additionally impossible to tell where nulls have leaked to.
- a1369209993 7y agoActually, nulls leak worse than optionals, because it's impossible to tell where nulls have leaked to (so you end up forgetting to filter out a null at a interface where you would have decided to filter out a maybe).
- K0nserv 7y agoI upvoted you because I think it's unfair that you are being downvoted while contributing to the discussion, that said you are completely wrong. Without Optional/Maybe nulls leak everywhere except you have no idea where they are. This leads programmers to engage in defensive programming for all references since there is nothing to help them understand what they should expect to be null in some cases. Optional/Maybe encourages good data modelling by making values that might be missing very clear. It encourages a style of programming that eliminates these issue via better modelling or by rejecting bad data earlier. For example consider a network response that in a JS app might be passed around as an opaque object. In a language like Swift this is infeasible, you have to transition from the network serialized version to concrete models at the network layer. If you encounter mismatches in the expectation of what is optional you have to handle it here at the edge of the program. This enables massively safer code and makes reasoning about your program much simpler if anything. As a concerete example say an API response tells you if a user is verified(for some domain specific definition of "verified"), additionally you want to know when they were verified maybe to give them a hint when they need to do it again. You coudl model this as: { "verified": false, "verified_at": null } before they have verified and { "verified": true, "verified_at": "2020-02-24T15:31:12Z" } after they have verified. In Swift this would then be modelled as struct Users { let verified: Bool let verifiedAt: Date? } However this introduces an Optional which complicates code that needs to deal with users who are verified or not. Instead you could model the same thing and avoid this issue as: { "verification_status": { "status": "unverified" } } for the unverified case and { "verification_status": { "status": "verified", "at": "2020-02-24T15:31:12Z" } } for the verified case. In Swift this can be nicely modelled without any Optionals using an enum enum VerificationStatus { case unverified case verified(Date) } struct User { let verificationStatus: VerificationStatus } Better optional value visibility leads to better data modelling.
- munchbunny 7y ago> You can create a type that can encompass all kinds of edge cases and information about them. This is not unique to functional programming languages. Haskell was definitely a trailblazer for this, but plenty of conventional languages support this now with relative ease.
- Spivak 7y agoAny language with a type system at all can create a Maybe type. The difference is that failing to handle the None case is a runtime exception in most languages where in Haskel/Rust it won’t compile. I don’t know of any mainstream language that has bolted on that level of verification.
- Scarbutt 7y agoScala3 and Kotlin.
- still_grokking 7y agoYou mean Scala 2. And likely even Scala 1 had this. (Scala 3 is still in development). But Kotlin? Since when does Kotlin have pattern matching with exhaustive checks? Also it does not have an `Maybe a` / `Option[A]` type out-of-the box.
- skybrian 7y agoKotlin distinguishes between nullable and not-null references, which is an alternative to the maybe type. It serves roughly the same purpose, to replace runtime errors with compile-time verification that you haven't missed a corner case.
- acomar 7y agothat prevents you from assigning null to a non-nullable reference. does it also error if you dereference a nullable reference without first checking if it's null?
- dmitriid 7y ago> This is of course a textbook case for Haskells Maybe concept. You can have a type that is a Maybe Int, and that means it have a value or it can be Nothing. Thus, you encompass the edge case of not having the value available If you encompass it this way. Literally nothing stops you from encoding this behavior in Haskell. Because the behavior you described is *if revenue is equal to zero, display it as N/A". No magic monad will prevent this.
- BoiledCabbage 7y agoNo, but it's the difference between implicit and explicit stupidity. All of us do implicit stupidity all of the time - it's human nature (or more accurately a side effect of working in a difficult field). When transformed into a choice between explicit stupidity, or doing things the right way, we instead usually choose to to do things the right way -- or at minimum do it the wrong way to test something out then change it to the write way. Being explicit is what makes that change likely to happen, rather than just be ignored.
- dmitriid 7y agoNo. No matter how much you dress it with words, technology is not magic. Monads are not magic. Haskell is not magic. If your data and/or problem is modeled as "if 0 then N/A" no amount of "human nature implicitly explicitly transformed" will help you. Dealing with non-existent data as opposed to "value = 0" is just as natural in Java, C++ or Javascript as it is in Haskell. And yet, that didn't help.