Why have method "get" in Option?

classic Classic list List threaded Threaded
80 messages Options
1234
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Why have method "get" in Option?

Sean Leather
Following on from some recent discussion on the design of Option and in my ongoing search to understand Scala, I have a fundamental question.

Why does the method "get" exist in the Option class? Here is the abbreviated code from scala/Option.scala.

sealed abstract class Option[+A] extends Product {
  def get: A
}

final case class Some[+A](x: A) extends Option[A] {
  def get = x
}

case object None extends Option[Nothing] {
  def get = throw new NoSuchElementException("None.get")
}

For reasons of type safety, shouldn't "get" only exist in Some? Or is this just another way of replacing "x.getOrElse(default)" with "try { x.get } catch { default }"?

Regards,
Sean
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

HamsterofDeath
that would force you to cast option to some and every time you now do
{know that op is defined} op.get
would turn into
{know that op is defined} op.asInstanceOf[Some[MyType]].get

with no benefit because if {know that op is defined} is wrong, you'll just replace nosuchelement by a classcast.


-------- Original-Nachricht --------
> Datum: Fri, 13 Aug 2010 12:30:40 +0200
> Von: Sean Leather <[hidden email]>
> An: Scala Users Lists <[hidden email]>
> Betreff: [scala-user] Why have method "get" in Option?

> Following on from some recent discussion on the design of Option and in my
> ongoing search to understand Scala, I have a fundamental question.
>
> Why does the method "get" exist in the Option class? Here is the
> abbreviated
> code from scala/Option.scala.
>
> sealed abstract class Option[+A] extends Product {
>   def get: A
> }
>
> final case class Some[+A](x: A) extends Option[A] {
>   def get = x
> }
>
> case object None extends Option[Nothing] {
>   def get = throw new NoSuchElementException("None.get")
> }
>
> For reasons of type safety, shouldn't "get" only exist in Some? Or is this
> just another way of replacing "x.getOrElse(default)" with "try { x.get }
> catch { default }"?
>
> Regards,
> Sean

--
GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
http://portal.gmx.net/de/go/dsl
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Tony Morris
In reply to this post by Sean Leather
Hi Sean,
Your question can be generalised to, "why have partial functions?" The
answer is not because they are preferred, but because they are necessary
according to Turing's undecidability.

Some languages do away with turing-completeness in favour of totality
(that is, no partial functions). Examples are Coq and Agda.

This is related to the mistakes in the original article.


Sean Leather wrote:

> Following on from some recent discussion on the design of Option and
> in my ongoing search to understand Scala, I have a fundamental question.
>
> Why does the method "get" exist in the Option class? Here is the
> abbreviated code from scala/Option.scala.
>
> sealed abstract class Option[+A] extends Product {
>   def get: A
> }
>
> final case class Some[+A](x: A) extends Option[A] {
>   def get = x
> }
>
> case object None extends Option[Nothing] {
>   def get = throw new NoSuchElementException("None.get")
> }
>
> For reasons of type safety, shouldn't "get" only exist in Some? Or is
> this just another way of replacing "x.getOrElse(default)" with "try {
> x.get } catch { default }"?
>
> Regards,
> Sean

--
Tony Morris
http://tmorris.net/


Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Sc iss
In reply to this post by HamsterofDeath
no, the question is valid. basically you should be able to get completely around with 'foreach', 'map' and 'getOrElse', thus 'get' is a really poor method that introduces potential runtime errors which would be impossible without this method. and thus, if you consider 'get' being not there, also the question of why not all the methods are in the subclasses of None and Some is totally accurate. i think that would have been cleaner (besides slightly faster) than the if( ....isDefined ) all over the Option class. the argumentation of "Algebraic data types" versus "Class hierarchies" misses the point IMO. Option is already sealed, so there can be only the two subclasses None and Some.

best, -sciss-


Am 13.08.2010 um 12:30 schrieb Dennis Haupt:

> that would force you to cast option to some and every time you now do
> {know that op is defined} op.get
> would turn into
> {know that op is defined} op.asInstanceOf[Some[MyType]].get
>
> with no benefit because if {know that op is defined} is wrong, you'll just replace nosuchelement by a classcast.
>
>
> -------- Original-Nachricht --------
>> Datum: Fri, 13 Aug 2010 12:30:40 +0200
>> Von: Sean Leather <[hidden email]>
>> An: Scala Users Lists <[hidden email]>
>> Betreff: [scala-user] Why have method "get" in Option?
>
>> Following on from some recent discussion on the design of Option and in my
>> ongoing search to understand Scala, I have a fundamental question.
>>
>> Why does the method "get" exist in the Option class? Here is the
>> abbreviated
>> code from scala/Option.scala.
>>
>> sealed abstract class Option[+A] extends Product {
>>  def get: A
>> }
>>
>> final case class Some[+A](x: A) extends Option[A] {
>>  def get = x
>> }
>>
>> case object None extends Option[Nothing] {
>>  def get = throw new NoSuchElementException("None.get")
>> }
>>
>> For reasons of type safety, shouldn't "get" only exist in Some? Or is this
>> just another way of replacing "x.getOrElse(default)" with "try { x.get }
>> catch { default }"?
>>
>> Regards,
>> Sean
>
> --
> GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
> http://portal.gmx.net/de/go/dsl

Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Jesper de Jong
In reply to this post by HamsterofDeath
No, it wouldn't force you to cast, because you can use pattern matching instead of casting:

val opt: Option[X] = ...

opt match {
  case Some(x) => println(x)
  case None => println("None")
}

(Note, you don't even have to call 'get', pattern matching gets the value out of the Option for you).

Jesper

2010/8/13 Dennis Haupt <[hidden email]>
that would force you to cast option to some and every time you now do
{know that op is defined} op.get
would turn into
{know that op is defined} op.asInstanceOf[Some[MyType]].get

with no benefit because if {know that op is defined} is wrong, you'll just replace nosuchelement by a classcast.


-------- Original-Nachricht --------
> Datum: Fri, 13 Aug 2010 12:30:40 +0200
> Von: Sean Leather <[hidden email]>
> An: Scala Users Lists <[hidden email]>
> Betreff: [scala-user] Why have method "get" in Option?

> Following on from some recent discussion on the design of Option and in my
> ongoing search to understand Scala, I have a fundamental question.
>
> Why does the method "get" exist in the Option class? Here is the
> abbreviated
> code from scala/Option.scala.
>
> sealed abstract class Option[+A] extends Product {
>   def get: A
> }
>
> final case class Some[+A](x: A) extends Option[A] {
>   def get = x
> }
>
> case object None extends Option[Nothing] {
>   def get = throw new NoSuchElementException("None.get")
> }
>
> For reasons of type safety, shouldn't "get" only exist in Some? Or is this
> just another way of replacing "x.getOrElse(default)" with "try { x.get }
> catch { default }"?
>
> Regards,
> Sean

--
GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
http://portal.gmx.net/de/go/dsl



--
Jesper de Jong
[hidden email]
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Daniel Degrandi
That is correct, but it was not the question. To use the method get you would have to cast to Some.

I think the get method is only useful in cases where you are 100% sure that you have a Some to make the whole thing more concise. Whenever you are unsure use pattern matching or getOrElse.

Dan

Jesper de Jong schrieb:
No, it wouldn't force you to cast, because you can use pattern matching instead of casting:

val opt: Option[X] = ...

opt match {
  case Some(x) => println(x)
  case None => println("None")
}

(Note, you don't even have to call 'get', pattern matching gets the value out of the Option for you).

Jesper

2010/8/13 Dennis Haupt <[hidden email]>
that would force you to cast option to some and every time you now do
{know that op is defined} op.get
would turn into
{know that op is defined} op.asInstanceOf[Some[MyType]].get

with no benefit because if {know that op is defined} is wrong, you'll just replace nosuchelement by a classcast.


-------- Original-Nachricht --------
> Datum: Fri, 13 Aug 2010 12:30:40 +0200
> Von: Sean Leather <[hidden email]>
> An: Scala Users Lists <[hidden email]>
> Betreff: [scala-user] Why have method "get" in Option?

> Following on from some recent discussion on the design of Option and in my
> ongoing search to understand Scala, I have a fundamental question.
>
> Why does the method "get" exist in the Option class? Here is the
> abbreviated
> code from scala/Option.scala.
>
> sealed abstract class Option[+A] extends Product {
>   def get: A
> }
>
> final case class Some[+A](x: A) extends Option[A] {
>   def get = x
> }
>
> case object None extends Option[Nothing] {
>   def get = throw new NoSuchElementException("None.get")
> }
>
> For reasons of type safety, shouldn't "get" only exist in Some? Or is this
> just another way of replacing "x.getOrElse(default)" with "try { x.get }
> catch { default }"?
>
> Regards,
> Sean

--
GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
http://portal.gmx.net/de/go/dsl



--
Jesper de Jong
[hidden email]
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Sean Leather
In reply to this post by Sean Leather
Thanks for the response. There are quite a few replies here, and I'm certain I don't understand most. As a result, I will try to clarify my question.

Why does the method "get" exist in the Option class?

The point of this question is that the method "get" is by definition unsafe. By unsafe, I mean that it will likely lead a programmer who uses it into error. Why is it unsafe? Let's review the code:
 
sealed abstract class Option[+A] extends Product { def get: A }
final case class Some[+A](x: A) extends Option[A] { def get = x }
case object None extends Option[Nothing] { def get = throw new NoSuchElementException("None.get") }

Since "get" is defined in the class Option, there is an implication that each subclass will override it and return some A value. Looking at each inheritor, we see that Some overrides and results in a value, but None throws an exception. Since there are only two subclasses and half of them are exceptional cases, I'd say it's pretty clear that "get" will lead somebody into error. Thus, it is unsafe.

For reasons of type safety, shouldn't "get" only exist in Some? Or is this just another way of replacing "x.getOrElse(default)" with "try { x.get } catch { default }"?

I'm suggesting that "get" not be defined in Option but rather in Some. That provides one way to get the value out of Some. But how do you get the value out of an Option? Again, I'm new to Scala but I already see multiple ways:
  • getOrElse
  • foreach/for
  • iterator
  • opt match { case Some(x) => ... ; case None => ... }
And I'm sure there are others.

Of course, this is not to say that a method equivalent to "get" can't still be written outside of Option.

def fromSome(opt: Option[A]) = opt match {
  case Some(x) => x
  case None => throw new NoSuchElementException("fromSome")
}

However, by putting "Option.get" (and even "orNull" and possibly others) in the standard library, it encourages programmers to use unsafe methods by making it easy. I get the impression that such unsafe methods are generally included in the Scala libraries. So, I suppose my real question should be: Why are unsafe methods included in the standard libraries?

Regards,
Sean
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Nils Kilden-Pedersen
In reply to this post by Sc iss
On Fri, Aug 13, 2010 at 6:38 AM, Sciss <[hidden email]> wrote:
no, the question is valid. basically you should be able to get completely around with 'foreach', 'map' and 'getOrElse', thus 'get' is a really poor method that introduces potential runtime errors which would be impossible without this method.

In the cases I use 'get' without checking I *want* a runtime error. It means I made a wrong assumption in my code and it better fail fast.

Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Patrik Andersson-3
In reply to this post by Sean Leather
But get is not any more unsafe than dereferencing any non-final (e.g. val) reference. As I've said in one of the other Option threads - it's not Options / nullabilities fault that we have NoSuchElementException / NPE:s, it's bad assumptions. Bad assumptions don't go away because you take away get. You could just aswell do foreach on an Option not accounting for the fact that in your particular use-case you also need to handle the None-case. Bad assumption.

Structure the code in such a way that there are no assumptions that cannot be 100% trusted.

On Fri, Aug 13, 2010 at 2:37 PM, Sean Leather <[hidden email]> wrote:
Thanks for the response. There are quite a few replies here, and I'm certain I don't understand most. As a result, I will try to clarify my question.

Why does the method "get" exist in the Option class?

The point of this question is that the method "get" is by definition unsafe. By unsafe, I mean that it will likely lead a programmer who uses it into error. Why is it unsafe? Let's review the code:
 
sealed abstract class Option[+A] extends Product { def get: A }
final case class Some[+A](x: A) extends Option[A] { def get = x }
case object None extends Option[Nothing] { def get = throw new NoSuchElementException("None.get") }

Since "get" is defined in the class Option, there is an implication that each subclass will override it and return some A value. Looking at each inheritor, we see that Some overrides and results in a value, but None throws an exception. Since there are only two subclasses and half of them are exceptional cases, I'd say it's pretty clear that "get" will lead somebody into error. Thus, it is unsafe.

For reasons of type safety, shouldn't "get" only exist in Some? Or is this just another way of replacing "x.getOrElse(default)" with "try { x.get } catch { default }"?

I'm suggesting that "get" not be defined in Option but rather in Some. That provides one way to get the value out of Some. But how do you get the value out of an Option? Again, I'm new to Scala but I already see multiple ways:
  • getOrElse
  • foreach/for
  • iterator
  • opt match { case Some(x) => ... ; case None => ... }
And I'm sure there are others.

Of course, this is not to say that a method equivalent to "get" can't still be written outside of Option.

def fromSome(opt: Option[A]) = opt match {
  case Some(x) => x
  case None => throw new NoSuchElementException("fromSome")
}

However, by putting "Option.get" (and even "orNull" and possibly others) in the standard library, it encourages programmers to use unsafe methods by making it easy. I get the impression that such unsafe methods are generally included in the Scala libraries. So, I suppose my real question should be: Why are unsafe methods included in the standard libraries?

Regards,
Sean

Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Rex Kerr-2
In reply to this post by Sean Leather
On Fri, Aug 13, 2010 at 6:30 AM, Sean Leather <[hidden email]> wrote:
Following on from some recent discussion on the design of Option and in my ongoing search to understand Scala, I have a fundamental question.

Why does the method "get" exist in the Option class?


It exists so you can do things like this:

// Example 1: You know it will succeed, why check again?
def f(o: Option[Int]) = o map (i => i + i*i)
f(Some(7)).get

// Example 2: Usually don't need the value, why pattern-match?
def g(o: Option[Int], rare_condition: Boolean) {
  if (o.isDefined) {
    println("All sorts of stuff happens here")
    if (rare_condition) println( o.get )
    println("More stuff happens here")
  }
  else {
    println("Various stuff here")
  }
}

// Example 3: We're prototyping here--let's not error-check every case yet
def h(command_line_argument: Option[String]) {
  println("User asked for: " + command_line_argument.get)
}

The coder's job is know when get is the appropriate method, and when they should use something else.

  --Rex

Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

HamsterofDeath
In reply to this post by Jesper de Jong
that just hides the cast, and it's even longer than using a cast or getOrElse directly.

i still vote for a simple "get"

-------- Original-Nachricht --------
> Datum: Fri, 13 Aug 2010 13:46:27 +0200
> Von: Jesper de Jong <[hidden email]>
> An: scala-user <[hidden email]>
> Betreff: Re: [scala-user] Why have method "get" in Option?

> No, it wouldn't force you to cast, because you can use pattern matching
> instead of casting:
>
> val opt: Option[X] = ...
>
> opt match {
>   case Some(x) => println(x)
>   case None => println("None")
> }
>
> (Note, you don't even have to call 'get', pattern matching gets the value
> out of the Option for you).
>
> Jesper
>
> 2010/8/13 Dennis Haupt <[hidden email]>
>
> > that would force you to cast option to some and every time you now do
> > {know that op is defined} op.get
> > would turn into
> > {know that op is defined} op.asInstanceOf[Some[MyType]].get
> >
> > with no benefit because if {know that op is defined} is wrong, you'll
> just
> > replace nosuchelement by a classcast.
> >
> >
> > -------- Original-Nachricht --------
> > > Datum: Fri, 13 Aug 2010 12:30:40 +0200
> > > Von: Sean Leather <[hidden email]>
> > > An: Scala Users Lists <[hidden email]>
> > > Betreff: [scala-user] Why have method "get" in Option?
> >
> > > Following on from some recent discussion on the design of Option and
> in
> > my
> > > ongoing search to understand Scala, I have a fundamental question.
> > >
> > > Why does the method "get" exist in the Option class? Here is the
> > > abbreviated
> > > code from scala/Option.scala.
> > >
> > > sealed abstract class Option[+A] extends Product {
> > >   def get: A
> > > }
> > >
> > > final case class Some[+A](x: A) extends Option[A] {
> > >   def get = x
> > > }
> > >
> > > case object None extends Option[Nothing] {
> > >   def get = throw new NoSuchElementException("None.get")
> > > }
> > >
> > > For reasons of type safety, shouldn't "get" only exist in Some? Or is
> > this
> > > just another way of replacing "x.getOrElse(default)" with "try { x.get
> }
> > > catch { default }"?
> > >
> > > Regards,
> > > Sean
> >
> > --
> > GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99
> ¿/mtl.!*
> > http://portal.gmx.net/de/go/dsl
> >
>
>
>
> --
> Jesper de Jong
> [hidden email]

--
GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
http://portal.gmx.net/de/go/dsl
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Kris Nuttycombe-3
I think that the presence of 'get' in Option (rather than Some) is
unfortunate as well. It defeats the purpose of using Option in the
first place, and as such I never use it.

With respect to the example:

// Example 1: You know it will succeed, why check again?
def f(o: Option[Int]) = o map (i => i + i*i)
f(Some(7)).get

I thought that there might be a solution to this in a definition like:

scala> def f[T <: Option[Int]](o: T): T = o.map(i => i + i*i)
<console>:5: error: type mismatch;
 found   : Option[Int]
 required: T

but it appears that the type of map does not specialize adequately (at
least with this construction.) I was surprised when I went to the
scaladoc to find that Option doesn't extend from TraversableLike. This
seems very odd to me - it means that this kind of construction fails
too:

scala> for (v <- Some(2); v2 <- List(4, 5, 6)) yield v * v2
<console>:6: error: type mismatch;
 found   : List[Int]
 required: Option[?]
       for (v <- Some(2); v2 <- List(4, 5, 6)) yield v * v2
                             ^

Yuck! Why is Option a second-class citizen???

Kris



On Fri, Aug 13, 2010 at 8:34 AM, Dennis Haupt <[hidden email]> wrote:

> that just hides the cast, and it's even longer than using a cast or getOrElse directly.
>
> i still vote for a simple "get"
>
> -------- Original-Nachricht --------
>> Datum: Fri, 13 Aug 2010 13:46:27 +0200
>> Von: Jesper de Jong <[hidden email]>
>> An: scala-user <[hidden email]>
>> Betreff: Re: [scala-user] Why have method "get" in Option?
>
>> No, it wouldn't force you to cast, because you can use pattern matching
>> instead of casting:
>>
>> val opt: Option[X] = ...
>>
>> opt match {
>>   case Some(x) => println(x)
>>   case None => println("None")
>> }
>>
>> (Note, you don't even have to call 'get', pattern matching gets the value
>> out of the Option for you).
>>
>> Jesper
>>
>> 2010/8/13 Dennis Haupt <[hidden email]>
>>
>> > that would force you to cast option to some and every time you now do
>> > {know that op is defined} op.get
>> > would turn into
>> > {know that op is defined} op.asInstanceOf[Some[MyType]].get
>> >
>> > with no benefit because if {know that op is defined} is wrong, you'll
>> just
>> > replace nosuchelement by a classcast.
>> >
>> >
>> > -------- Original-Nachricht --------
>> > > Datum: Fri, 13 Aug 2010 12:30:40 +0200
>> > > Von: Sean Leather <[hidden email]>
>> > > An: Scala Users Lists <[hidden email]>
>> > > Betreff: [scala-user] Why have method "get" in Option?
>> >
>> > > Following on from some recent discussion on the design of Option and
>> in
>> > my
>> > > ongoing search to understand Scala, I have a fundamental question.
>> > >
>> > > Why does the method "get" exist in the Option class? Here is the
>> > > abbreviated
>> > > code from scala/Option.scala.
>> > >
>> > > sealed abstract class Option[+A] extends Product {
>> > >   def get: A
>> > > }
>> > >
>> > > final case class Some[+A](x: A) extends Option[A] {
>> > >   def get = x
>> > > }
>> > >
>> > > case object None extends Option[Nothing] {
>> > >   def get = throw new NoSuchElementException("None.get")
>> > > }
>> > >
>> > > For reasons of type safety, shouldn't "get" only exist in Some? Or is
>> > this
>> > > just another way of replacing "x.getOrElse(default)" with "try { x.get
>> }
>> > > catch { default }"?
>> > >
>> > > Regards,
>> > > Sean
>> >
>> > --
>> > GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99
>> ¿/mtl.!*
>> > http://portal.gmx.net/de/go/dsl
>> >
>>
>>
>>
>> --
>> Jesper de Jong
>> [hidden email]
>
> --
> GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
> http://portal.gmx.net/de/go/dsl
>
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Paul Phillips-3
On Fri, Aug 13, 2010 at 12:58:14PM -0600, Kris Nuttycombe wrote:
> Yuck! Why is Option a second-class citizen???

The most recent of many trips around that maypole:

http://scala-programming-language.1934581.n4.nabble.com/Why-does-Option-not-extend-the-Iterable-trait-td1944949.html

There are lengthier ones, but that one is probably enough for you.

--
Paul Phillips      | Adultery is the application of democracy to love.
Caged Spirit       |     -- H. L. Mencken
Empiricist         |
i pull his palp!   |----------* http://www.improving.org/paulp/ *----------
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

HamsterofDeath
In reply to this post by Kris Nuttycombe-3
 i think you misunderstood the purpose of map on option.
it maps Some(x) to Some(y) and None to None. the mapping function can be
applied to any option, no matter if it's some or none. you don't have to
check if option is defined. it's not meant to get the value out of a some.

and maybe you misunderstood the option itself. i use it as a return type
where there might be no valid result. for example, if i call
"findPath(from:Position, to:Position), the return type is Option[Path].
if there is a path i get some, if there is none, i get None.
now i want to render that path:
result.foreach(_.renderOnScreen)
no need to check for null. the function is executed if there is a path,
otherwise nothing is going to happen.





Am 13.08.2010 20:58, schrieb Kris Nuttycombe:

> I think that the presence of 'get' in Option (rather than Some) is
> unfortunate as well. It defeats the purpose of using Option in the
> first place, and as such I never use it.
>
> With respect to the example:
>
> // Example 1: You know it will succeed, why check again?
> def f(o: Option[Int]) = o map (i => i + i*i)
> f(Some(7)).get
>
> I thought that there might be a solution to this in a definition like:
>
> scala> def f[T <: Option[Int]](o: T): T = o.map(i => i + i*i)
> <console>:5: error: type mismatch;
>  found   : Option[Int]
>  required: T
>
> but it appears that the type of map does not specialize adequately (at
> least with this construction.) I was surprised when I went to the
> scaladoc to find that Option doesn't extend from TraversableLike. This
> seems very odd to me - it means that this kind of construction fails
> too:
>
> scala> for (v <- Some(2); v2 <- List(4, 5, 6)) yield v * v2
> <console>:6: error: type mismatch;
>  found   : List[Int]
>  required: Option[?]
>        for (v <- Some(2); v2 <- List(4, 5, 6)) yield v * v2
>                              ^
>
> Yuck! Why is Option a second-class citizen???
>
> Kris
>
>
>
> On Fri, Aug 13, 2010 at 8:34 AM, Dennis Haupt <[hidden email]> wrote:
>> that just hides the cast, and it's even longer than using a cast or getOrElse directly.
>>
>> i still vote for a simple "get"
>>
>> -------- Original-Nachricht --------
>>> Datum: Fri, 13 Aug 2010 13:46:27 +0200
>>> Von: Jesper de Jong <[hidden email]>
>>> An: scala-user <[hidden email]>
>>> Betreff: Re: [scala-user] Why have method "get" in Option?
>>> No, it wouldn't force you to cast, because you can use pattern matching
>>> instead of casting:
>>>
>>> val opt: Option[X] = ...
>>>
>>> opt match {
>>>   case Some(x) => println(x)
>>>   case None => println("None")
>>> }
>>>
>>> (Note, you don't even have to call 'get', pattern matching gets the value
>>> out of the Option for you).
>>>
>>> Jesper
>>>
>>> 2010/8/13 Dennis Haupt <[hidden email]>
>>>
>>>> that would force you to cast option to some and every time you now do
>>>> {know that op is defined} op.get
>>>> would turn into
>>>> {know that op is defined} op.asInstanceOf[Some[MyType]].get
>>>>
>>>> with no benefit because if {know that op is defined} is wrong, you'll
>>> just
>>>> replace nosuchelement by a classcast.
>>>>
>>>>
>>>> -------- Original-Nachricht --------
>>>>> Datum: Fri, 13 Aug 2010 12:30:40 +0200
>>>>> Von: Sean Leather <[hidden email]>
>>>>> An: Scala Users Lists <[hidden email]>
>>>>> Betreff: [scala-user] Why have method "get" in Option?
>>>>> Following on from some recent discussion on the design of Option and
>>> in
>>>> my
>>>>> ongoing search to understand Scala, I have a fundamental question.
>>>>>
>>>>> Why does the method "get" exist in the Option class? Here is the
>>>>> abbreviated
>>>>> code from scala/Option.scala.
>>>>>
>>>>> sealed abstract class Option[+A] extends Product {
>>>>>   def get: A
>>>>> }
>>>>>
>>>>> final case class Some[+A](x: A) extends Option[A] {
>>>>>   def get = x
>>>>> }
>>>>>
>>>>> case object None extends Option[Nothing] {
>>>>>   def get = throw new NoSuchElementException("None.get")
>>>>> }
>>>>>
>>>>> For reasons of type safety, shouldn't "get" only exist in Some? Or is
>>>> this
>>>>> just another way of replacing "x.getOrElse(default)" with "try { x.get
>>> }
>>>>> catch { default }"?
>>>>>
>>>>> Regards,
>>>>> Sean
>>>> --
>>>> GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99
>>> ¿/mtl.!*
>>>> http://portal.gmx.net/de/go/dsl
>>>>
>>>
>>>
>>> --
>>> Jesper de Jong
>>> [hidden email]
>> --
>> GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
>> http://portal.gmx.net/de/go/dsl
>>

Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Kris Nuttycombe-3
Hah. I understand the purpose of map quite well, thanks. Perhaps you
should look at my question (and the applicability of TraversableLike)
a little more closely.

If Option were to extend TraversableLike, then it would be possible to
"trace" whether an Option instance were a Some or a None through a a
call to map, and have a safe implementation of get.

But, then, as Paulp's link demonstrates, flatMap would be broken. So
it's not a reasonable idea after all.

:)

Kris

On Fri, Aug 13, 2010 at 1:21 PM, HamsterofDeath <[hidden email]> wrote:

>  i think you misunderstood the purpose of map on option.
> it maps Some(x) to Some(y) and None to None. the mapping function can be
> applied to any option, no matter if it's some or none. you don't have to
> check if option is defined. it's not meant to get the value out of a some.
>
> and maybe you misunderstood the option itself. i use it as a return type
> where there might be no valid result. for example, if i call
> "findPath(from:Position, to:Position), the return type is Option[Path].
> if there is a path i get some, if there is none, i get None.
> now i want to render that path:
> result.foreach(_.renderOnScreen)
> no need to check for null. the function is executed if there is a path,
> otherwise nothing is going to happen.
>
>
>
>
>
> Am 13.08.2010 20:58, schrieb Kris Nuttycombe:
>> I think that the presence of 'get' in Option (rather than Some) is
>> unfortunate as well. It defeats the purpose of using Option in the
>> first place, and as such I never use it.
>>
>> With respect to the example:
>>
>> // Example 1: You know it will succeed, why check again?
>> def f(o: Option[Int]) = o map (i => i + i*i)
>> f(Some(7)).get
>>
>> I thought that there might be a solution to this in a definition like:
>>
>> scala> def f[T <: Option[Int]](o: T): T = o.map(i => i + i*i)
>> <console>:5: error: type mismatch;
>>  found   : Option[Int]
>>  required: T
>>
>> but it appears that the type of map does not specialize adequately (at
>> least with this construction.) I was surprised when I went to the
>> scaladoc to find that Option doesn't extend from TraversableLike. This
>> seems very odd to me - it means that this kind of construction fails
>> too:
>>
>> scala> for (v <- Some(2); v2 <- List(4, 5, 6)) yield v * v2
>> <console>:6: error: type mismatch;
>>  found   : List[Int]
>>  required: Option[?]
>>        for (v <- Some(2); v2 <- List(4, 5, 6)) yield v * v2
>>                              ^
>>
>> Yuck! Why is Option a second-class citizen???
>>
>> Kris
>>
>>
>>
>> On Fri, Aug 13, 2010 at 8:34 AM, Dennis Haupt <[hidden email]> wrote:
>>> that just hides the cast, and it's even longer than using a cast or getOrElse directly.
>>>
>>> i still vote for a simple "get"
>>>
>>> -------- Original-Nachricht --------
>>>> Datum: Fri, 13 Aug 2010 13:46:27 +0200
>>>> Von: Jesper de Jong <[hidden email]>
>>>> An: scala-user <[hidden email]>
>>>> Betreff: Re: [scala-user] Why have method "get" in Option?
>>>> No, it wouldn't force you to cast, because you can use pattern matching
>>>> instead of casting:
>>>>
>>>> val opt: Option[X] = ...
>>>>
>>>> opt match {
>>>>   case Some(x) => println(x)
>>>>   case None => println("None")
>>>> }
>>>>
>>>> (Note, you don't even have to call 'get', pattern matching gets the value
>>>> out of the Option for you).
>>>>
>>>> Jesper
>>>>
>>>> 2010/8/13 Dennis Haupt <[hidden email]>
>>>>
>>>>> that would force you to cast option to some and every time you now do
>>>>> {know that op is defined} op.get
>>>>> would turn into
>>>>> {know that op is defined} op.asInstanceOf[Some[MyType]].get
>>>>>
>>>>> with no benefit because if {know that op is defined} is wrong, you'll
>>>> just
>>>>> replace nosuchelement by a classcast.
>>>>>
>>>>>
>>>>> -------- Original-Nachricht --------
>>>>>> Datum: Fri, 13 Aug 2010 12:30:40 +0200
>>>>>> Von: Sean Leather <[hidden email]>
>>>>>> An: Scala Users Lists <[hidden email]>
>>>>>> Betreff: [scala-user] Why have method "get" in Option?
>>>>>> Following on from some recent discussion on the design of Option and
>>>> in
>>>>> my
>>>>>> ongoing search to understand Scala, I have a fundamental question.
>>>>>>
>>>>>> Why does the method "get" exist in the Option class? Here is the
>>>>>> abbreviated
>>>>>> code from scala/Option.scala.
>>>>>>
>>>>>> sealed abstract class Option[+A] extends Product {
>>>>>>   def get: A
>>>>>> }
>>>>>>
>>>>>> final case class Some[+A](x: A) extends Option[A] {
>>>>>>   def get = x
>>>>>> }
>>>>>>
>>>>>> case object None extends Option[Nothing] {
>>>>>>   def get = throw new NoSuchElementException("None.get")
>>>>>> }
>>>>>>
>>>>>> For reasons of type safety, shouldn't "get" only exist in Some? Or is
>>>>> this
>>>>>> just another way of replacing "x.getOrElse(default)" with "try { x.get
>>>> }
>>>>>> catch { default }"?
>>>>>>
>>>>>> Regards,
>>>>>> Sean
>>>>> --
>>>>> GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99
>>>> ¿/mtl.!*
>>>>> http://portal.gmx.net/de/go/dsl
>>>>>
>>>>
>>>>
>>>> --
>>>> Jesper de Jong
>>>> [hidden email]
>>> --
>>> GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
>>> http://portal.gmx.net/de/go/dsl
>>>
>
>
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Jesper de Jong
In reply to this post by HamsterofDeath
No, when you pattern match, there is no cast at all, and no possibility that a ClassCastException will happen (which is why a cast is bad). Pattern matching is not a "hidden cast".

Jesper

2010/8/13 Dennis Haupt <[hidden email]>
that just hides the cast, and it's even longer than using a cast or getOrElse directly.

i still vote for a simple "get"

-------- Original-Nachricht --------
> Datum: Fri, 13 Aug 2010 13:46:27 +0200
> Von: Jesper de Jong <[hidden email]>
> An: scala-user <[hidden email]>
> Betreff: Re: [scala-user] Why have method "get" in Option?

> No, it wouldn't force you to cast, because you can use pattern matching
> instead of casting:
>
> val opt: Option[X] = ...
>
> opt match {
>   case Some(x) => println(x)
>   case None => println("None")
> }
>
> (Note, you don't even have to call 'get', pattern matching gets the value
> out of the Option for you).
>
> Jesper
>
> 2010/8/13 Dennis Haupt <[hidden email]>
>
> > that would force you to cast option to some and every time you now do
> > {know that op is defined} op.get
> > would turn into
> > {know that op is defined} op.asInstanceOf[Some[MyType]].get
> >
> > with no benefit because if {know that op is defined} is wrong, you'll
> just
> > replace nosuchelement by a classcast.
> >
> >
> > -------- Original-Nachricht --------
> > > Datum: Fri, 13 Aug 2010 12:30:40 +0200
> > > Von: Sean Leather <[hidden email]>
> > > An: Scala Users Lists <[hidden email]>
> > > Betreff: [scala-user] Why have method "get" in Option?
> >
> > > Following on from some recent discussion on the design of Option and
> in
> > my
> > > ongoing search to understand Scala, I have a fundamental question.
> > >
> > > Why does the method "get" exist in the Option class? Here is the
> > > abbreviated
> > > code from scala/Option.scala.
> > >
> > > sealed abstract class Option[+A] extends Product {
> > >   def get: A
> > > }
> > >
> > > final case class Some[+A](x: A) extends Option[A] {
> > >   def get = x
> > > }
> > >
> > > case object None extends Option[Nothing] {
> > >   def get = throw new NoSuchElementException("None.get")
> > > }
> > >
> > > For reasons of type safety, shouldn't "get" only exist in Some? Or is
> > this
> > > just another way of replacing "x.getOrElse(default)" with "try { x.get
> }
> > > catch { default }"?
> > >
> > > Regards,
> > > Sean
> >
> > --
> > GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99
> ¿/mtl.!*
> > http://portal.gmx.net/de/go/dsl
> >
>
>
>
> --
> Jesper de Jong
> [hidden email]

--
GMX DSL SOMMER-SPECIAL: Surf & Phone Flat 16.000 für nur 19,99 ¿/mtl.!*
http://portal.gmx.net/de/go/dsl



--
Jesper de Jong
[hidden email]
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Randall R Schulz-2
On Friday August 13 2010, Jesper de Jong wrote:
> No, when you pattern match, there is no cast at all, and no
> possibility that a ClassCastException will happen (which is why a
> cast is bad). Pattern matching is not a "hidden cast".

It is a cast.

It's just that the asInstanceOf is reliably
conditioned upon a preceding isInstanceOf
(their JVM bytecode equivalents, anyway).


> Jesper


Randall Schulz
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Tony Morris
In reply to this post by Sean Leather
Sean,
Scala *must* have unsafe methods. It's absolutely necessary. Nothing is
solved by moving or removing the get function in this respect.

Sean Leather wrote:

> Thanks for the response. There are quite a few replies here, and I'm
> certain I don't understand most. As a result, I will try to clarify my
> question.
>
>     Why does the method "get" exist in the Option class?
>
>
> The point of this question is that the method "get" is by definition
> unsafe. By unsafe, I mean that it will likely lead a programmer who
> uses it into error. Why is it unsafe? Let's review the code:
>  
>
>     sealed abstract class Option[+A] extends Product { def get: A }
>     final case class Some[+A](x: A) extends Option[A] { def get = x }
>     case object None extends Option[Nothing] { def get = throw new
>     NoSuchElementException("None.get") }
>
>
> Since "get" is defined in the class Option, there is an implication
> that each subclass will override it and return some A value. Looking
> at each inheritor, we see that Some overrides and results in a value,
> but None throws an exception. Since there are only two subclasses and
> half of them are exceptional cases, I'd say it's pretty clear that
> "get" will lead somebody into error. Thus, it is unsafe.
>
>     For reasons of type safety, shouldn't "get" only exist in Some? Or
>     is this just another way of replacing "x.getOrElse(default)" with
>     "try { x.get } catch { default }"?
>
>
> I'm suggesting that "get" not be defined in Option but rather in Some.
> That provides one way to get the value out of Some. But how do you get
> the value out of an Option? Again, I'm new to Scala but I already see
> multiple ways:
>
>     * getOrElse
>     * foreach/for
>     * iterator
>     * opt match { case Some(x) => ... ; case None => ... }
>
> And I'm sure there are others.
>
> Of course, this is not to say that a method equivalent to "get" can't
> still be written outside of Option.
>
> def fromSome(opt: Option[A]) = opt match {
>   case Some(x) => x
>   case None => throw new NoSuchElementException("fromSome")
> }
>
> However, by putting "Option.get" (and even "orNull" and possibly
> others) in the standard library, it encourages programmers to use
> unsafe methods by making it easy. I get the impression that such
> unsafe methods are generally included in the Scala libraries. So, I
> suppose my real question should be: Why are unsafe methods included in
> the standard libraries?
>
> Regards,
> Sean

--
Tony Morris
http://tmorris.net/


Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Sébastien Bocq
In reply to this post by Paul Phillips-3
sealed abstract class Opt[+A] extends Iterable[A]
case object Non extends Opt[Nothing] {
    def iterator: Iterator[Nothing] = Iterator.empty
    def map[B](f:Nothing => B):Opt[B] = Non
    def flatMap[B](f:Nothing => Opt[B]):Opt[B] = Non
    override def filter(p:Nothing => Boolean):Opt[Nothing] = Non
}
case class Som[+A](a:A) extends Opt[A] {
    def iterator: Iterator[A] = Iterator.single(a)
    def map[B](f:A => B):Opt[B] = Som(f(a))
    def flatMap[B](f:A => Opt[B]):Opt[B] = f(a)
    override def filter(p:A => Boolean):Opt[A] = if (p(a)) this else Non
}

object Opt {
  def main(args : Array[String]) : Unit = {
      println(Som(1) flatMap{_:Int => Som(1)})          // Som(1)
      println(Som(1) flatMap{_:Int => Iterable(1, 2)})  // List(1, 2)

      println(for {
           y <- List(1, 2)
           x:Int <- Som(y)
      } yield (x,  y)) // List((1,1), (2,2))
     
  }
}

What is wrong with that?

Thanks,
Sebastien

2010/8/13 Paul Phillips <[hidden email]>
On Fri, Aug 13, 2010 at 12:58:14PM -0600, Kris Nuttycombe wrote:
> Yuck! Why is Option a second-class citizen???

The most recent of many trips around that maypole:

http://scala-programming-language.1934581.n4.nabble.com/Why-does-Option-not-extend-the-Iterable-trait-td1944949.html

There are lengthier ones, but that one is probably enough for you.

--
Paul Phillips      | Adultery is the application of democracy to love.
Caged Spirit       |     -- H. L. Mencken
Empiricist         |
i pull his palp!   |----------* http://www.improving.org/paulp/ *----------

Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: Why have method "get" in Option?

Egon Nijns
In reply to this post by Tony Morris
Tony,

Please elaborate on this. I'm not seeing the necessity.

Kind regards,
Egon.

Tony Morris wrote:

Sean,
Scala *must* have unsafe methods. It's absolutely necessary. Nothing is
solved by moving or removing the get function in this respect.

Sean Leather wrote:

> Thanks for the response. There are quite a few replies here, and I'm
> certain I don't understand most. As a result, I will try to clarify my
> question.
>
>     Why does the method "get" exist in the Option class?
>
>
> The point of this question is that the method "get" is by definition
> unsafe. By unsafe, I mean that it will likely lead a programmer who
> uses it into error. Why is it unsafe? Let's review the code:
>  
>
>     sealed abstract class Option[+A] extends Product { def get: A }
>     final case class Some[+A](x: A) extends Option[A] { def get = x }
>     case object None extends Option[Nothing] { def get = throw new
>     NoSuchElementException("None.get") }
>
>
> Since "get" is defined in the class Option, there is an implication
> that each subclass will override it and return some A value. Looking
> at each inheritor, we see that Some overrides and results in a value,
> but None throws an exception. Since there are only two subclasses and
> half of them are exceptional cases, I'd say it's pretty clear that
> "get" will lead somebody into error. Thus, it is unsafe.
>
>     For reasons of type safety, shouldn't "get" only exist in Some? Or
>     is this just another way of replacing "x.getOrElse(default)" with
>     "try { x.get } catch { default }"?
>
>
> I'm suggesting that "get" not be defined in Option but rather in Some.
> That provides one way to get the value out of Some. But how do you get
> the value out of an Option? Again, I'm new to Scala but I already see
> multiple ways:
>
>     * getOrElse
>     * foreach/for
>     * iterator
>     * opt match { case Some(x) => ... ; case None => ... }
>
> And I'm sure there are others.
>
> Of course, this is not to say that a method equivalent to "get" can't
> still be written outside of Option.
>
> def fromSome(opt: Option[A]) = opt match {
>   case Some(x) => x
>   case None => throw new NoSuchElementException("fromSome")
> }
>
> However, by putting "Option.get" (and even "orNull" and possibly
> others) in the standard library, it encourages programmers to use
> unsafe methods by making it easy. I get the impression that such
> unsafe methods are generally included in the Scala libraries. So, I
> suppose my real question should be: Why are unsafe methods included in
> the standard libraries?
>
> Regards,
> Sean

--
Tony Morris
http://tmorris.net/


1234
Loading...