tag:blogger.com,1999:blog-7045524330253482541.post4979407567454223262..comments2024-01-04T22:19:45.990-08:00Comments on Jim McBeath: Type Safe Builder in Scala, Part 2Jim McBeathhttp://www.blogger.com/profile/10541190774989580614noreply@blogger.comBlogger4125tag:blogger.com,1999:blog-7045524330253482541.post-36602598285785303532011-03-17T21:06:53.848-07:002011-03-17T21:06:53.848-07:00Skavookie: Are you asking why the optional "g...Skavookie: Are you asking why the optional "glass" parameter is different from the other parameters? Other than the fact that the private OrderOfScotch constructor takes an Option for the glass parameter, the other difference, that the HAS_GLASS type is required to be NOT_MULTI, is because that argument is allowed to appear zero or one times (anything other than multiple times), whereas the other arguments must all appear exactly one time.Jim McBeathhttps://www.blogger.com/profile/10541190774989580614noreply@blogger.comtag:blogger.com,1999:blog-7045524330253482541.post-31423929377037069482011-03-08T18:58:21.424-08:002011-03-08T18:58:21.424-08:00Why the different implementation of Option?Why the different implementation of Option?Skavookiehttps://www.blogger.com/profile/09454378441839786791noreply@blogger.comtag:blogger.com,1999:blog-7045524330253482541.post-59016797752166095322009-09-08T20:00:48.832-07:002009-09-08T20:00:48.832-07:00gambistics: Interesting approach. Thanks for the ...gambistics: Interesting approach. Thanks for the reminder that it is so easy in Scala to implement chaining techniques other than method call chaining. There are indeed many ways to solve this problem. I am even now working on yet another one.Jim McBeathhttps://www.blogger.com/profile/10541190774989580614noreply@blogger.comtag:blogger.com,1999:blog-7045524330253482541.post-76278911707258729352009-09-07T11:05:43.250-07:002009-09-07T11:05:43.250-07:00Hi Jim,
there's an even simpler solution. The...Hi Jim,<br /><br />there's an even simpler solution. The underlying problem to solve is, how to restrict member methods from being called, based on information in the type parameters/members. Your approach is one to get this done. There are at least another two approaches which work equally well:<br /><br />1.) Since you can't specify a type for member functions which would restrict their applicability directly you can turn the method calling scheme upside down.<br /><br />In the class you can introduce a new operator which just applies the function given to itself (respecting its own type parameters). I call it usally '~'. (You may call the operator 'reverse method application operator' as well):<br /><br />class Builder[A,B,C] /* ... */ {<br /> def ~[X](f:Builder[A,B,C => X):X = f(this)<br />}<br /><br />The former members become standalone functions. Instead of using the selection operator '.' you can then use '~' to call (and chain) the functions upon the object. See http://gist.github.com/182249 for the complete example.<br /><br />Another optimization I've used, is that I didn't introduced an extra type (TRUE,FALSE) for the type parameters but just used Some[X] for TRUE and None for FALSE. (Actually I cheated because I had to redefine the Option-hierarchy. That's because I didn't manage to work out the type of the scala built-in None. Anyone?)<br /><br />2.) Another possibility to 'guard' member calls is using implicits. With this scheme you write your class cleanly as before without any checks. Afterwards each method which has to be checked gets an implicit parameter which serves as evidence that the object's type conforms to the wanted configuration. I actually implemented this one as well, but this implicit-stuff regular crashes the compiler or doesn't stop to compile at all. If I get it working I can upload this version as well.Johanneshttps://www.blogger.com/profile/17243632157564129686noreply@blogger.com