Tomasz Krakowiak
04/21/2021, 4:59 PMJannis
04/21/2021, 5:01 PMTomasz Krakowiak
04/21/2021, 5:15 PMJannis
04/21/2021, 5:19 PMI don't think IDE performance should matter when designing API. It's IDE issue, not mine.It does matter tho. Believe me I'd like it not to, but if you want someone (even if thats you yourself) to use your api better make damn sure its, well, usable from within an ide. If the functions are complex SAM interfaces are easier imo, otherwise function types will be just fine. Not sure how SAM interfaces fare vs normal function types in terms of performance tho. Also iirc SAM interfaces cannot be suspend, whereas function aliases can. So imo this is never a black/white kind of question and highly depends on what you want to do with that api.
Tomasz Krakowiak
04/21/2021, 5:26 PMIt does matter tho. Believe me I'd like it not to, but if you want someone (even if thats you yourself) to use your api better make damn sure its, well, usable from within an ide.It's should be a must for IDE developers to support all language features. Otherwise it's something wrong with either IDE or language and reason good enough to change former or latter.
Also iirc SAM interfaces cannot be suspend, whereas function aliases can.I think supended SAM only got temporairly suspended( : P ). A reason good enaugh to temporarily use typealias, but in such cases I mark such declarations with an @OptIn annotation specific to pending language feature.
So imo this is never a black/white kind of question and highly depends on what you want to do with that api.That's why I am looking for a principle. I think SAM should be preferred unless given declaration is purely for generic functional use, like
Sequence.map
Roukanken
04/21/2021, 9:23 PM(A) -> B
to SAM with (A) -> B
function
If that's true and I'm not talking out of my ass, then there is imho pretty clear distinction between the usage of the two.
And that is - use SAM if and only if you require some additional "features" of the function, other than it's type.
For example a HashFunction
should most definitelly be a SAM, because not every (String) -> String
function is a hash function - you also require the results to be well distributed, so you want to forbid user passing just any function, just those that implement HashFunction or direct lambda at the call
On the other hand the functional usage does not require any additional features, so they should be either typealias or direct type usage.Tomasz Krakowiak
04/22/2021, 9:01 AMvalue class Hash(val hash : Long)
value class HashFunction<T>(val hash: (T)->Hash)
We can reduce delegation this way, if we could somehow cast between (T)->Hash and (T)->Long. This would play nicely if multiple libraries would define type for HashFunction.