- About Scala
- Documentation
- Code Examples
- Software
- Scala Developers
Scala type system
Fri, 2010-08-06, 00:00
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
Fri, 2010-08-06, 00:47
#2
Re: Scala type system
Thanks so much, this indeed clarified, so much is provided by the compiler... As I understand there is this extra injection of implicit parameter in this case since the conversion function exists (intofloat) its all peachy and it will work on the level of float (when doing computation in the scope of the method) but views can be constructed outside of Predefs and smilar pattern repeated (implicit method +r function rather:) for type converstion and so this guarantees level of control what method or function can accept I have a hard time to decide to call method a method or rather function:) thanks much
Justifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/(check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Sent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 00:31:20 +0100To: Andrew Milkowski<andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch>Subject: Re: [scala-user] Scala type systemJustifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/(check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 01:07
#3
Re: Scala type system
Thanks Kevin (DSL) also now make sense , great slowly unblocking from rigid confines of the OOE crib:) I think it would be of great benefit to anyone to know how to "unwrap" syntactic sugar (love the term btw:) in this way further assistance can be provided to follow compiler "patterns" and repeat them in modified setting (such as creating custom methods and behaviours) is this possible ie to resolve my last "mystery" and uwrap execution pattern for Stream.cons(0, Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
But there could be other examples
Thanks much
Justifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/(check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
But there could be other examples
Thanks much
Sent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 00:31:20 +0100To: Andrew Milkowski<andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch>Subject: Re: [scala-user] Scala type systemJustifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/(check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 02:07
#4
Re: Scala type system
There *is* a formal difference between "function" and "method"
A method is a member of some object, exactly the same as in Java
a function is an Object, you can define functions that aren't methods: val anonfunc = (x : Int) => x * 2anonfunc will now be an instance of Function1[Int,Int]
and when you try to use a method as though it were a function, it becomes one! Autoboxing in Java is a good analogy here.
But be careful, even the "programming in scala" book doesn't use the terms precisely.One of the goals of Scala is that you shouldn't have to worry about the difference all that much :)
On 6 August 2010 00:45, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
A method is a member of some object, exactly the same as in Java
a function is an Object, you can define functions that aren't methods: val anonfunc = (x : Int) => x * 2anonfunc will now be an instance of Function1[Int,Int]
and when you try to use a method as though it were a function, it becomes one! Autoboxing in Java is a good analogy here.
But be careful, even the "programming in scala" book doesn't use the terms precisely.One of the goals of Scala is that you shouldn't have to worry about the difference all that much :)
On 6 August 2010 00:45, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
Thanks so much, this indeed clarified, so much is provided by the compiler... As I understand there is this extra injection of implicit parameter in this case since the conversion function exists (intofloat) its all peachy and it will work on the level of float (when doing computation in the scope of the method) but views can be constructed outside of Predefs and smilar pattern repeated (implicit method +r function rather:) for type converstion and so this guarantees level of control what method or function can accept I have a hard time to decide to call method a method or rather function:) thanks muchSent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 00:31:20 +0100To: Andrew Milkowski<andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch> Subject: Re: [scala-user] Scala type system
Justifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/ (check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 02:27
#5
Re: Scala type system
And I also could use "anonfunc" as a function in another composition. F(F1(anonfunction)).. And so duality occurs method and function all in the same language... Fascinating, I encountered some blogs complaining on language complexity where in fact this email thread unravels soup de joure... Recursion vs functions on lists, method vs function, ... Thanks all so much still long road ahead but can't hide this make CS programming into real fun...
There *is* a formal difference between "function" and "method"
A method is a member of some object, exactly the same as in Java
a function is an Object, you can define functions that aren't methods: val anonfunc = (x : Int) => x * 2anonfunc will now be an instance of Function1[Int,Int]
and when you try to use a method as though it were a function, it becomes one! Autoboxing in Java is a good analogy here.
But be careful, even the "programming in scala" book doesn't use the terms precisely.One of the goals of Scala is that you shouldn't have to worry about the difference all that much :)
On 6 August 2010 00:45, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Sent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 01:58:21 +0100To: <andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch>Subject: Re: [scala-user] Scala type systemThere *is* a formal difference between "function" and "method"
A method is a member of some object, exactly the same as in Java
a function is an Object, you can define functions that aren't methods: val anonfunc = (x : Int) => x * 2anonfunc will now be an instance of Function1[Int,Int]
and when you try to use a method as though it were a function, it becomes one! Autoboxing in Java is a good analogy here.
But be careful, even the "programming in scala" book doesn't use the terms precisely.One of the goals of Scala is that you shouldn't have to worry about the difference all that much :)
On 6 August 2010 00:45, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
Thanks so much, this indeed clarified, so much is provided by the compiler... As I understand there is this extra injection of implicit parameter in this case since the conversion function exists (intofloat) its all peachy and it will work on the level of float (when doing computation in the scope of the method) but views can be constructed outside of Predefs and smilar pattern repeated (implicit method +r function rather:) for type converstion and so this guarantees level of control what method or function can accept I have a hard time to decide to call method a method or rather function:) thanks muchSent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 00:31:20 +0100To: Andrew Milkowski<andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch> Subject: Re: [scala-user] Scala type system
Justifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/ (check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 03:07
#6
Re: Scala type system
I also ordered haskell programming (as suggested) now my curiosity is really up, the idea that a programming construct can contain no mutable values could have an enormous (positive effect) on concurrent programming, I can see that now 0 side effects... I can already have a taste of it in Actors and message passing, I can see now why and how scala was chosen in graph model application where actors and message passing are utilized not so much as a network client/server but an internal object inter communication disregarding semaphors mutexes etc... Haskell will hopefully bring more examples of FP in context and than back to scala from much higher level and perspective... That's the ultimate goal...
And I also could use "anonfunc" as a function in another composition. F(F1(anonfunction)).. And so duality occurs method and function all in the same language... Fascinating, I encountered some blogs complaining on language complexity where in fact this email thread unravels soup de joure... Recursion vs functions on lists, method vs function, ... Thanks all so much still long road ahead but can't hide this make CS programming into real fun...
There *is* a formal difference between "function" and "method"
A method is a member of some object, exactly the same as in Java
a function is an Object, you can define functions that aren't methods: val anonfunc = (x : Int) => x * 2anonfunc will now be an instance of Function1[Int,Int]
and when you try to use a method as though it were a function, it becomes one! Autoboxing in Java is a good analogy here.
But be careful, even the "programming in scala" book doesn't use the terms precisely.One of the goals of Scala is that you shouldn't have to worry about the difference all that much :)
On 6 August 2010 00:45, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Sent from my Verizon Wireless BlackBerry
From: "Andrew Milkowski" <andrewmilkowski@gmail.com> Date: Fri, 6 Aug 2010 01:22:27 +0000To: Kevin Wright<kev.lee.wright@gmail.com>ReplyTo: andrewmilkowski@gmail.com Cc: scala-user<scala-user@listes.epfl.ch>Subject: Re: [scala-user] Scala type systemAnd I also could use "anonfunc" as a function in another composition. F(F1(anonfunction)).. And so duality occurs method and function all in the same language... Fascinating, I encountered some blogs complaining on language complexity where in fact this email thread unravels soup de joure... Recursion vs functions on lists, method vs function, ... Thanks all so much still long road ahead but can't hide this make CS programming into real fun...
Sent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 01:58:21 +0100To: <andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch>Subject: Re: [scala-user] Scala type systemThere *is* a formal difference between "function" and "method"
A method is a member of some object, exactly the same as in Java
a function is an Object, you can define functions that aren't methods: val anonfunc = (x : Int) => x * 2anonfunc will now be an instance of Function1[Int,Int]
and when you try to use a method as though it were a function, it becomes one! Autoboxing in Java is a good analogy here.
But be careful, even the "programming in scala" book doesn't use the terms precisely.One of the goals of Scala is that you shouldn't have to worry about the difference all that much :)
On 6 August 2010 00:45, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
Thanks so much, this indeed clarified, so much is provided by the compiler... As I understand there is this extra injection of implicit parameter in this case since the conversion function exists (intofloat) its all peachy and it will work on the level of float (when doing computation in the scope of the method) but views can be constructed outside of Predefs and smilar pattern repeated (implicit method +r function rather:) for type converstion and so this guarantees level of control what method or function can accept I have a hard time to decide to call method a method or rather function:) thanks muchSent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 00:31:20 +0100To: Andrew Milkowski<andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch> Subject: Re: [scala-user] Scala type system
Justifying an internal DSL is easy :)
This is one of my favourites: http://www.scalatest.org/ (check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat_)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 14:57
#7
Re: Scala type system
Andrew Milkowski wrote:
> but I do want to ask for a bit of assistance, there is this "one
> liner" scala code, that computes Fibonacci sequence it goes like this:
>
> lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
> fib.zip(fib.tail).map(p=> p._1 + p._2)))
>
> fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
>
> I am at loss as to function fib.zip that according to text should
> exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
I am not entirely sure what you are asking, but maybe the Haskell
version of that same code is going to be a little bit clearer:
fib = 0 : 1 : zipWith (+) fib (tail fib)
I find this one much easier to read than the Scala version. It says:
the infinite sequence of Fibonacci numbers is defined to be itself
elementwise-added to itself shifted by one.
> this inability (for me) to translate numerics to Scala functional
> implementations is exactly where I am blocked. ie above
> what is output from Stream.con construction.
Stream.cons constructs a stream (more precisely, a single stream cell)
from a value and the rest of the stream.
> what is zip exactly mapping,
Zip isn't mapping anything, it's zipping. Zip works exactly like a
zipper on your clothes: it takes two sequences and merges them
together into one; in this particular case by taking one element from
each stream, packaging them up into a pair and returning a stream of
pairs.
jwm
Fri, 2010-08-06, 15:27
#8
Re: Re: Scala type system
Lol on zipper analogy:) haskell book on the way to complement study, power of FP is immense... Thanks for further uwrapping this example for me, normally one would (and is) doing recursive implementation to compute number sequence, fact that scala provides an "infinite" stream is mind boggling to me but probably not to seasoned FP professional...
Sent from my Verizon Wireless BlackBerry
-----Original Message-----
From: Jörg W Mittag JoergWMittag+Usenet@GoogleMail.Com
Date: Fri, 6 Aug 2010 15:36:50
To:
Subject: [scala-user] Re: Scala type system
Andrew Milkowski wrote:
> but I do want to ask for a bit of assistance, there is this "one
> liner" scala code, that computes Fibonacci sequence it goes like this:
>
> lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
> fib.zip(fib.tail).map(p=> p._1 + p._2)))
>
> fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
>
> I am at loss as to function fib.zip that according to text should
> exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
I am not entirely sure what you are asking, but maybe the Haskell
version of that same code is going to be a little bit clearer:
fib = 0 : 1 : zipWith (+) fib (tail fib)
I find this one much easier to read than the Scala version. It says:
the infinite sequence of Fibonacci numbers is defined to be itself
elementwise-added to itself shifted by one.
> this inability (for me) to translate numerics to Scala functional
> implementations is exactly where I am blocked. ie above
> what is output from Stream.con construction.
Stream.cons constructs a stream (more precisely, a single stream cell)
from a value and the rest of the stream.
> what is zip exactly mapping,
Zip isn't mapping anything, it's zipping. Zip works exactly like a
zipper on your clothes: it takes two sequences and merges them
together into one; in this particular case by taking one element from
each stream, packaging them up into a pair and returning a stream of
pairs.
jwm
Fri, 2010-08-06, 15:37
#9
Re: Re: Scala type system
On Friday August 6 2010, Jörg W Mittag wrote:
> ...
>
> fib = 0 : 1 : zipWith (+) fib (tail fib)
>
> I find this one much easier to read than the Scala version. It says:
> the infinite sequence of Fibonacci numbers is defined to be itself
> elementwise-added to itself shifted by one.
If you use the infix counterpart to Stream.cons, it's not so bad:
def
fib: Stream[Long] =
1 #:: 2 #:: fibs.zip(fibs.tail).map(p => p._1 + p._2)
> ...
>
> jwm
Randall Schulz
Fri, 2010-08-06, 15:47
#10
Re: Scala type system
Now to the difficult stuff, how does this fib work?
First, I'm going to rewrite it slightly, using the #:: operatorThis is much like :: but works on streams instead of Lists
so, what happens when you want the next term? maybe you've called fib.tail.taillet's evaluate the parts of `fib.zip(fib.tail).map(p=> p._1 + p._2)))` individually (I'll call that expression nextval now, for brevity
`zip` combines 2 sequences into a sequence of pairs (in this case, a stream of pairs) so
this is memo'd, and becomes the tail of the fib, which is now:
repeating for the next term:
It may look as though there's a lot of repetition going on, but the intermediate steps - fib.tail, f.zip(fib.tail), etc. - are themselves Streams, and also memo'd. So it's actually fairly efficient.
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
First, I'm going to rewrite it slightly, using the #:: operatorThis is much like :: but works on streams instead of Lists
lazy val fib: Stream[Int] = 0 #:: 1 #:: fib.zip(fib.tail).map(p=> p._1 + p._2)))
Now a brief aside about streams...They are are (a) lazy and (b) memoized. Meaning that each value is only calculated as needed, and that a value, once calculated, is cached and doesn't need to be calculated again. we rely on both of these qualities...
so, what happens when you want the next term? maybe you've called fib.tail.taillet's evaluate the parts of `fib.zip(fib.tail).map(p=> p._1 + p._2)))` individually (I'll call that expression nextval now, for brevity
fib = 0 #:: 1 #:: nextvalfib.tail = 1 #:: nextval
`zip` combines 2 sequences into a sequence of pairs (in this case, a stream of pairs) so
fib.zip(fib.tail)yields
(0,1) #:: (1,nextval)which is then mapped (p=> p._1 + p._2) to
0+1 #:: 1+nextval(in fact, the expression 0+1 would be eagerly evaluated and you'd just get `1`, but it helps the explanation if I leave it expanded for now)
this is memo'd, and becomes the tail of the fib, which is now:
fib = 0 #:: 1 #:: 0+1 #:: 1+nextval
repeating for the next term:
fib = 0 #:: 1 #:: 0+1 #:: 1+1 #:: 0+1+nextvaland the next:
fib = 0 #:: 1 #:: 0+1 #:: 1+1 #:: #1+2 # 1+1+nextvaland so on...
It may look as though there's a lot of repetition going on, but the intermediate steps - fib.tail, f.zip(fib.tail), etc. - are themselves Streams, and also memo'd. So it's actually fairly efficient.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 15:57
#11
Re: Scala type system
Thanks
Now to the difficult stuff, how does this fib work?
First, I'm going to rewrite it slightly, using the #:: operatorThis is much like :: but works on streams instead of Lists
so, what happens when you want the next term? maybe you've called fib.tail.taillet's evaluate the parts of `fib.zip(fib.tail).map(p=> p._1 + p._2)))` individually (I'll call that expression nextval now, for brevity
`zip` combines 2 sequences into a sequence of pairs (in this case, a stream of pairs) so
this is memo'd, and becomes the tail of the fib, which is now:
repeating for the next term:
It may look as though there's a lot of repetition going on, but the intermediate steps - fib.tail, f.zip(fib.tail), etc. - are themselves Streams, and also memo'd. So it's actually fairly efficient.
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Sent from my Verizon Wireless BlackBerry
From: Kevin Wright <kev.lee.wright@gmail.com> Date: Fri, 6 Aug 2010 15:29:50 +0100To: Andrew Milkowski<andrewmilkowski@gmail.com>Cc: scala-user<scala-user@listes.epfl.ch>Subject: Re: [scala-user] Scala type systemNow to the difficult stuff, how does this fib work?
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
First, I'm going to rewrite it slightly, using the #:: operatorThis is much like :: but works on streams instead of Lists
lazy val fib: Stream[Int] = 0 #:: 1 #:: fib.zip(fib.tail).map(p=> p._1 + p._2)))
Now a brief aside about streams...They are are (a) lazy and (b) memoized. Meaning that each value is only calculated as needed, and that a value, once calculated, is cached and doesn't need to be calculated again. we rely on both of these qualities...
so, what happens when you want the next term? maybe you've called fib.tail.taillet's evaluate the parts of `fib.zip(fib.tail).map(p=> p._1 + p._2)))` individually (I'll call that expression nextval now, for brevity
fib = 0 #:: 1 #:: nextvalfib.tail = 1 #:: nextval
`zip` combines 2 sequences into a sequence of pairs (in this case, a stream of pairs) so
fib.zip(fib.tail)yields
(0,1) #:: (1,nextval)which is then mapped (p=> p._1 + p._2) to
0+1 #:: 1+nextval(in fact, the expression 0+1 would be eagerly evaluated and you'd just get `1`, but it helps the explanation if I leave it expanded for now)
this is memo'd, and becomes the tail of the fib, which is now:
fib = 0 #:: 1 #:: 0+1 #:: 1+nextval
repeating for the next term:
fib = 0 #:: 1 #:: 0+1 #:: 1+1 #:: 0+1+nextvaland the next:
fib = 0 #:: 1 #:: 0+1 #:: 1+1 #:: #1+2 # 1+1+nextvaland so on...
It may look as though there's a lot of repetition going on, but the intermediate steps - fib.tail, f.zip(fib.tail), etc. - are themselves Streams, and also memo'd. So it's actually fairly efficient.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
To enrich my scala user experience I decided to consume O'Reilly
programming scala, some chapters went really fast, like Actors and
surprisingly Functional chapter, but then dreaded "scala type system"
with abstractions in the various type inheritance (reminiscent of
Einstein SR theory Minkowski metric super/subscripts notations:) , who
wrote Scala compiler? a physicist?:) reaching new heights, so this
chapter I will need to read probably n-times where n will be most
definitely > 1 :) actually some paragraphs in this chapter are easier
to comprehend than others ie upper and lower bounds, others like views
and view bounds are still in my todo or to comprehend list. Overall I
see an amazing amount of granularity and thought that went behind this
system of type inheritance , so basically i have work cut out for me
but I do want to ask for a bit of assistance, there is this "one
liner" scala code, that computes Fibonacci sequence it goes like this:
lazy val fib: Stream[Int] = Stream.cons(0, Stream.cons(1,
fib.zip(fib.tail).map(p=> p._1 + p._2)))
fib.take(10).print // produces: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, Stream.empty
I am at loss as to function fib.zip that according to text should
exploit formula that fb(n) = fib(n-1) + fib(n-2), for n > 1
this inability (for me) to translate numerics to Scala functional
implementations is exactly where I am blocked. ie above
what is output from Stream.con construction. what is zip exactly
mapping, it is all deeply buried in scala implementation I know,
but not clear from this example... believe this will (is) problem for
anyone starting this journey...
Second part are these Views, so I am guessing that View is some type
of conversion "assistant" that compiler mysteriously finds and assist
in resolution of certain kind of type inheritance (I could be terribly
wrong here even in my primitive attempt of this generalization!)
Can you provide an example of a simplest possible trait/class/sub
class that would give easiest explanation of this concept
Otherwise, other concepts are not so bad to grasp, ie DSL pales in
comparison to Type system (external less so than internal, internal
DSL is hard to follow and even harder to understand why someone would
wrap a second level of abstraction to assist developers to assist
developer (developer => scala code => developer => DSL => developer =>
scala:) external I see immense advantage , but I welcome counter
examples, also not exactly clear how doing DSL in scala improves over
doing DSL in any other language outside obvious functional programming
constructs that improves creation of parsers
Thans much in advance!
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 16:27
#12
Re: Re: Scala type system
Randall R Schulz wrote:
> On Friday August 6 2010, Jörg W Mittag wrote:
>> ...
>>
>> fib = 0 : 1 : zipWith (+) fib (tail fib)
>>
>> I find this one much easier to read than the Scala version. It says:
>> the infinite sequence of Fibonacci numbers is defined to be itself
>> elementwise-added to itself shifted by one.
> If you use the infix counterpart to Stream.cons, it's not so bad:
>
> def
> fib: Stream[Long] =
> 1 #:: 2 #:: fibs.zip(fibs.tail).map(p => p._1 + p._2)
*There* it is! I was looking for it, but couldn't find it. I still
haven't figured out how to navigate scaladoc. I mean, I *knew* that
the operator would very likely not be a direct member of class Stream,
but I just didn't find it.
Learning something new every day.
Thanks,
jwm
Fri, 2010-08-06, 16:47
#13
Re: Re: Re: Scala type system
On Friday August 6 2010, Jörg W Mittag wrote:
> Randall R Schulz wrote:
> > On Friday August 6 2010, Jörg W Mittag wrote:
> >> ...
> >>
> >> fib = 0 : 1 : zipWith (+) fib (tail fib)
> >>
> >> I find this one much easier to read than the Scala version. It
> >> says: the infinite sequence of Fibonacci numbers is defined to be
> >> itself elementwise-added to itself shifted by one.
> >
> > If you use the infix counterpart to Stream.cons, it's not so bad:
> >
> > def
> > fib: Stream[Long] =
> > 1 #:: 2 #:: fibs.zip(fibs.tail).map(p => p._1 + p._2)
By the way, you can drop some dots, too:
def
fibs: Stream[Long] =
1l #:: 2l #:: fibs zip(fibs.tail) map(p => p._1 + p._2)
Naturally, it's a matter of taste whether this is an improvement here
or in any particular case.
Randall Schulz
Fri, 2010-08-06, 16:57
#14
Re: Re: Re: Scala type system
On Friday August 6 2010, Randall R Schulz wrote:
> On Friday August 6 2010, Jörg W Mittag wrote:
> > Randall R Schulz wrote:
> > > On Friday August 6 2010, Jörg W Mittag wrote:
> > >> ...
> > >>
> > >> fib = 0 : 1 : zipWith (+) fib (tail fib)
> > >>
> > >> I find this one much easier to read than the Scala version. It
> > >> says: the infinite sequence of Fibonacci numbers is defined to
> > >> be itself elementwise-added to itself shifted by one.
> > >
> > > If you use the infix counterpart to Stream.cons, it's not so bad:
> > >
> > > def
> > > fib: Stream[Long] =
> > > 1 #:: 2 #:: fibs.zip(fibs.tail).map(p => p._1 + p._2)
>
> By the way, you can drop some dots, too:
>
> def
> fibs: Stream[Long] =
> 1l #:: 2l #:: fibs zip(fibs.tail) map(p => p._1 + p._2)
...Though I should have tried it, first.
The "reduced-dot" form is not the same and exhibits an OOM error!
Furthermore, this Stream formulation of a Fibonacci number generator,
while lazy, retains grotesquely excessive amounts of memory. The default
Scala heap size (256M) does not allow the production of even 30
Fibonacci numbers from this definition (with the "fibs" method
pre-compiled but using the REPL, which does have some extra RAM
overhead).
A similar pattern is exhibited by the Stream formulation of the Sieve of
Eratosthenes:
def
ints(n: Long): Stream[Long] =
n #:: ints(n + 1)
private
def
primeGen(nums: Stream[Long]): Stream[Long] =
nums.head #:: (primeGen((nums tail) filter (x => x % nums.head != 0)))
def
primeStream: Stream[Long] =
primeGen(ints(2))
Does Haskell suffer from this phenomenon?
Randall Schulz
Fri, 2010-08-06, 17:07
#15
Re: Re: Re: Scala type system
Don't you have to lazy-val it as in the original email instead of def'ing it to get proper memoization and avoid excessive heap usage?
On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz <rschulz@sonic.net> wrote:
On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz <rschulz@sonic.net> wrote:
On Friday August 6 2010, Randall R Schulz wrote:
> On Friday August 6 2010, Jörg W Mittag wrote:
> > Randall R Schulz wrote:
> > > On Friday August 6 2010, Jörg W Mittag wrote:
> > >> ...
> > >>
> > >> fib = 0 : 1 : zipWith (+) fib (tail fib)
> > >>
> > >> I find this one much easier to read than the Scala version. It
> > >> says: the infinite sequence of Fibonacci numbers is defined to
> > >> be itself elementwise-added to itself shifted by one.
> > >
> > > If you use the infix counterpart to Stream.cons, it's not so bad:
> > >
> > > def
> > > fib: Stream[Long] =
> > > 1 #:: 2 #:: fibs.zip(fibs.tail).map(p => p._1 + p._2)
>
> By the way, you can drop some dots, too:
>
> def
> fibs: Stream[Long] =
> 1l #:: 2l #:: fibs zip(fibs.tail) map(p => p._1 + p._2)
...Though I should have tried it, first.
The "reduced-dot" form is not the same and exhibits an OOM error!
Furthermore, this Stream formulation of a Fibonacci number generator,
while lazy, retains grotesquely excessive amounts of memory. The default
Scala heap size (256M) does not allow the production of even 30
Fibonacci numbers from this definition (with the "fibs" method
pre-compiled but using the REPL, which does have some extra RAM
overhead).
A similar pattern is exhibited by the Stream formulation of the Sieve of
Eratosthenes:
def
ints(n: Long): Stream[Long] =
n #:: ints(n + 1)
private
def
primeGen(nums: Stream[Long]): Stream[Long] =
nums.head #:: (primeGen((nums tail) filter (x => x % nums.head != 0)))
def
primeStream: Stream[Long] =
primeGen(ints(2))
Does Haskell suffer from this phenomenon?
Randall Schulz
Fri, 2010-08-06, 17:17
#16
Re: Re: Re: Scala type system
So without lazy val sequence is rebuilt each time (no caching aka memoization) ? That would be indeed critical in the application design and possibly warrant a "warning" during compilation time...
Don't you have to lazy-val it as in the original email instead of def'ing it to get proper memoization and avoid excessive heap usage?
On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz <rschulz@sonic.net> wrote:
Sent from my Verizon Wireless BlackBerry
From: Dan Kang <dartdanfm@gmail.com> Date: Fri, 6 Aug 2010 12:02:28 -0400To: Randall R Schulz<rschulz@sonic.net>Cc: <scala-user@listes.epfl.ch>Subject: Re: [scala-user] Re: Re: Scala type systemDon't you have to lazy-val it as in the original email instead of def'ing it to get proper memoization and avoid excessive heap usage?
On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz <rschulz@sonic.net> wrote:
On Friday August 6 2010, Randall R Schulz wrote:
> On Friday August 6 2010, Jörg W Mittag wrote:
> > Randall R Schulz wrote:
> > > On Friday August 6 2010, Jörg W Mittag wrote:
> > >> ...
> > >>
> > >> fib = 0 : 1 : zipWith (+) fib (tail fib)
> > >>
> > >> I find this one much easier to read than the Scala version. It
> > >> says: the infinite sequence of Fibonacci numbers is defined to
> > >> be itself elementwise-added to itself shifted by one.
> > >
> > > If you use the infix counterpart to Stream.cons, it's not so bad:
> > >
> > > def
> > > fib: Stream[Long] =
> > > 1 #:: 2 #:: fibs.zip(fibs.tail).map(p => p._1 + p._2)
>
> By the way, you can drop some dots, too:
>
> def
> fibs: Stream[Long] =
> 1l #:: 2l #:: fibs zip(fibs.tail) map(p => p._1 + p._2)
...Though I should have tried it, first.
The "reduced-dot" form is not the same and exhibits an OOM error!
Furthermore, this Stream formulation of a Fibonacci number generator,
while lazy, retains grotesquely excessive amounts of memory. The default
Scala heap size (256M) does not allow the production of even 30
Fibonacci numbers from this definition (with the "fibs" method
pre-compiled but using the REPL, which does have some extra RAM
overhead).
A similar pattern is exhibited by the Stream formulation of the Sieve of
Eratosthenes:
def
ints(n: Long): Stream[Long] =
n #:: ints(n + 1)
private
def
primeGen(nums: Stream[Long]): Stream[Long] =
nums.head #:: (primeGen((nums tail) filter (x => x % nums.head != 0)))
def
primeStream: Stream[Long] =
primeGen(ints(2))
Does Haskell suffer from this phenomenon?
Randall Schulz
Fri, 2010-08-06, 17:27
#17
Re: Scala type system
On Fri, Aug 06, 2010 at 03:29:50PM +0100, Kevin Wright wrote:
> lazy val fib: Stream[Int] = Stream.cons(0,
> Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
I should point out this doesn't even have to be lazy.
Fri, 2010-08-06, 17:57
#18
Re: Re: Re: Scala type system
On Friday August 6 2010, Dan Kang wrote:
> On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz wrote:
> > ...
> >
> > Furthermore, this Stream formulation of a Fibonacci number
> > generator, while lazy, retains grotesquely excessive amounts of
> > memory. The default Scala heap size (256M) does not allow the
> > production of even 30 Fibonacci numbers from this definition (with
> > the "fibs" method pre-compiled but using the REPL, which does have
> > some extra RAM overhead).
> >
> > A similar pattern is exhibited by the Stream formulation of the
> > Sieve of Eratosthenes:
> >
> > def
> > ints(n: Long): Stream[Long] =
> > n #:: ints(n + 1)
> >
> > private
> > def
> > primeGen(nums: Stream[Long]): Stream[Long] =
> > nums.head #:: (primeGen((nums tail) filter (x => x % nums.head
> > != 0)))
> >
> > def
> > primeStream: Stream[Long] =
> > primeGen(ints(2))
>
> Don't you have to lazy-val it as in the original email instead of
> def'ing it to get proper memoization and avoid excessive heap usage?
The only thing that does is defer the evaluation of head of the Stream.
Everything else is the same.
Randall Schulz
Fri, 2010-08-06, 18:07
#19
Re: Re: Re: Scala type system
On 6 August 2010 17:47, Randall R Schulz <rschulz@sonic.net> wrote:
On Friday August 6 2010, Dan Kang wrote:
> On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz wrote:
> > ...
> >
> > Furthermore, this Stream formulation of a Fibonacci number
> > generator, while lazy, retains grotesquely excessive amounts of
> > memory. The default Scala heap size (256M) does not allow the
> > production of even 30 Fibonacci numbers from this definition (with
> > the "fibs" method pre-compiled but using the REPL, which does have
> > some extra RAM overhead).
> >
> > A similar pattern is exhibited by the Stream formulation of the
> > Sieve of Eratosthenes:
> >
> > def
> > ints(n: Long): Stream[Long] =
> > n #:: ints(n + 1)
> >
> > private
> > def
> > primeGen(nums: Stream[Long]): Stream[Long] =
> > nums.head #:: (primeGen((nums tail) filter (x => x % nums.head
> > != 0)))
> >
> > def
> > primeStream: Stream[Long] =
> > primeGen(ints(2))
>
> Don't you have to lazy-val it as in the original email instead of
> def'ing it to get proper memoization and avoid excessive heap usage?
The only thing that does is defer the evaluation of head of the Stream.
Everything else is the same.
Depends if you're talking lazy-val vs def or lazy-val vs valYou do need it to be a val (as opposed to a def) for proper memoization, it just doesn't have to be lazy
Randall Schulz
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 18:27
#20
Re: Re: Re: Scala type system
On Friday August 6 2010, Kevin Wright wrote:
> On 6 August 2010 17:47, Randall R Schulz wrote:
> > On Friday August 6 2010, Dan Kang wrote:
> > > On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz wrote:
> > > > ...
> > > >
> > > > Furthermore, this Stream formulation of a Fibonacci number
> > > > generator, while lazy, retains grotesquely excessive amounts of
> > > > memory. The default Scala heap size (256M) does not allow the
> > > > production of even 30 Fibonacci numbers from this definition
> > > > (with the "fibs" method pre-compiled but using the REPL, which
> > > > does have some extra RAM overhead).
> > > >
> > > > A similar pattern is exhibited by the Stream formulation of the
> > > > Sieve of Eratosthenes:
> > > >
> > > > def
> > > > ints(n: Long): Stream[Long] =
> > > > n #:: ints(n + 1)
> > > >
> > > > private
> > > > def
> > > > primeGen(nums: Stream[Long]): Stream[Long] =
> > > > nums.head #:: (primeGen((nums tail) filter (x => x %
> > > > nums.head != 0)))
> > > >
> > > > def
> > > > primeStream: Stream[Long] =
> > > > primeGen(ints(2))
> > >
> > > Don't you have to lazy-val it as in the original email instead of
> > > def'ing it to get proper memoization and avoid excessive heap
> > > usage?
> >
> > The only thing that does is defer the evaluation of head of the
> > Stream. Everything else is the same.
>
> Depends if you're talking lazy-val vs def or lazy-val vs val
> You do need it to be a val (as opposed to a def) for proper
> memoization, it just doesn't have to be lazy
Right. Big difference between val and def, isn't there...?
Randall Schulz
Fri, 2010-08-06, 18:37
#21
Re: Re: Re: Scala type system
On 6 August 2010 18:15, Randall R Schulz <rschulz@sonic.net> wrote:
On Friday August 6 2010, Kevin Wright wrote:erm.... yes... yes there is :)
> On 6 August 2010 17:47, Randall R Schulz <rschulz@sonic.net> wrote:
> > On Friday August 6 2010, Dan Kang wrote:
> > > On Fri, Aug 6, 2010 at 11:54 AM, Randall R Schulz wrote:
> > > > ...
> > > >
> > > > Furthermore, this Stream formulation of a Fibonacci number
> > > > generator, while lazy, retains grotesquely excessive amounts of
> > > > memory. The default Scala heap size (256M) does not allow the
> > > > production of even 30 Fibonacci numbers from this definition
> > > > (with the "fibs" method pre-compiled but using the REPL, which
> > > > does have some extra RAM overhead).
> > > >
> > > > A similar pattern is exhibited by the Stream formulation of the
> > > > Sieve of Eratosthenes:
> > > >
> > > > def
> > > > ints(n: Long): Stream[Long] =
> > > > n #:: ints(n + 1)
> > > >
> > > > private
> > > > def
> > > > primeGen(nums: Stream[Long]): Stream[Long] =
> > > > nums.head #:: (primeGen((nums tail) filter (x => x %
> > > > nums.head != 0)))
> > > >
> > > > def
> > > > primeStream: Stream[Long] =
> > > > primeGen(ints(2))
> > >
> > > Don't you have to lazy-val it as in the original email instead of
> > > def'ing it to get proper memoization and avoid excessive heap
> > > usage?
> >
> > The only thing that does is defer the evaluation of head of the
> > Stream. Everything else is the same.
>
> Depends if you're talking lazy-val vs def or lazy-val vs val
> You do need it to be a val (as opposed to a def) for proper
> memoization, it just doesn't have to be lazy
Right. Big difference between val and def, isn't there...?
Randall Schulz
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 18:57
#22
Re: Scala type system
Correct, I somehow forgot scala allows recursive definitions through val without lazy...
On Fri, Aug 6, 2010 at 12:18 PM, Paul Phillips <paulp@improving.org> wrote:
On Fri, Aug 6, 2010 at 12:18 PM, Paul Phillips <paulp@improving.org> wrote:
On Fri, Aug 06, 2010 at 03:29:50PM +0100, Kevin Wright wrote:
> lazy val fib: Stream[Int] = Stream.cons(0,
> Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
I should point out this doesn't even have to be lazy.
--
Paul Phillips | Simplicity and elegance are unpopular because
Apatheist | they require hard work and discipline to achieve
Empiricist | and education to be appreciated.
up hill, pi pals! | -- Dijkstra
Fri, 2010-08-06, 19:07
#23
Re: Scala type system
scala> val fib: Stream[Int] = 0 #:: 1 #:: fib.zip(fib.tail).map(p=> p._1 + p._2)fib: Stream[Int] = Stream(0, ?)
scala> val x = fib.take(7).toListx: List[Int] = List(0, 1, 1, 2, 3, 5, 8)
I'm sure it's significant here that the whole `fib.zip...` business is a by-name param (as opposed to a function).
On 6 August 2010 18:53, Dan Kang <dartdanfm@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
scala> val x = fib.take(7).toListx: List[Int] = List(0, 1, 1, 2, 3, 5, 8)
I'm sure it's significant here that the whole `fib.zip...` business is a by-name param (as opposed to a function).
On 6 August 2010 18:53, Dan Kang <dartdanfm@gmail.com> wrote:
Correct, I somehow forgot scala allows recursive definitions through val without lazy...
On Fri, Aug 6, 2010 at 12:18 PM, Paul Phillips <paulp@improving.org> wrote:
On Fri, Aug 06, 2010 at 03:29:50PM +0100, Kevin Wright wrote:
> lazy val fib: Stream[Int] = Stream.cons(0,
> Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
I should point out this doesn't even have to be lazy.
--
Paul Phillips | Simplicity and elegance are unpopular because
Apatheist | they require hard work and discipline to achieve
Empiricist | and education to be appreciated.
up hill, pi pals! | -- Dijkstra
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 19:37
#24
Re: Scala type system
Looks like this works too:
val fact:Int=>Int = { _ match { case 0 => 1; case b => fact(b - 1) * b} }
This makes a lot of sense - the distinction between sequential and recursive binding doesn't really buy anything.
On Fri, Aug 6, 2010 at 2:04 PM, Kevin Wright <kev.lee.wright@gmail.com> wrote:
val fact:Int=>Int = { _ match { case 0 => 1; case b => fact(b - 1) * b} }
This makes a lot of sense - the distinction between sequential and recursive binding doesn't really buy anything.
On Fri, Aug 6, 2010 at 2:04 PM, Kevin Wright <kev.lee.wright@gmail.com> wrote:
scala> val fib: Stream[Int] = 0 #:: 1 #:: fib.zip(fib.tail).map(p=> p._1 + p._2)fib: Stream[Int] = Stream(0, ?)
scala> val x = fib.take(7).toListx: List[Int] = List(0, 1, 1, 2, 3, 5, 8)
I'm sure it's significant here that the whole `fib.zip...` business is a by-name param (as opposed to a function).
On 6 August 2010 18:53, Dan Kang <dartdanfm@gmail.com> wrote:Correct, I somehow forgot scala allows recursive definitions through val without lazy...
On Fri, Aug 6, 2010 at 12:18 PM, Paul Phillips <paulp@improving.org> wrote:
On Fri, Aug 06, 2010 at 03:29:50PM +0100, Kevin Wright wrote:
> lazy val fib: Stream[Int] = Stream.cons(0,
> Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
I should point out this doesn't even have to be lazy.
--
Paul Phillips | Simplicity and elegance are unpopular because
Apatheist | they require hard work and discipline to achieve
Empiricist | and education to be appreciated.
up hill, pi pals! | -- Dijkstra
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
Fri, 2010-08-06, 19:47
#25
Re: Scala type system
The difference will show after you've called it a couple of thousand times...
On 6 August 2010 19:20, Dan Kang <dartdanfm@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
On 6 August 2010 19:20, Dan Kang <dartdanfm@gmail.com> wrote:
Looks like this works too:
val fact:Int=>Int = { _ match { case 0 => 1; case b => fact(b - 1) * b} }
This makes a lot of sense - the distinction between sequential and recursive binding doesn't really buy anything.
On Fri, Aug 6, 2010 at 2:04 PM, Kevin Wright <kev.lee.wright@gmail.com> wrote:scala> val fib: Stream[Int] = 0 #:: 1 #:: fib.zip(fib.tail).map(p=> p._1 + p._2)fib: Stream[Int] = Stream(0, ?)
scala> val x = fib.take(7).toListx: List[Int] = List(0, 1, 1, 2, 3, 5, 8)
I'm sure it's significant here that the whole `fib.zip...` business is a by-name param (as opposed to a function).
On 6 August 2010 18:53, Dan Kang <dartdanfm@gmail.com> wrote:Correct, I somehow forgot scala allows recursive definitions through val without lazy...
On Fri, Aug 6, 2010 at 12:18 PM, Paul Phillips <paulp@improving.org> wrote:
On Fri, Aug 06, 2010 at 03:29:50PM +0100, Kevin Wright wrote:
> lazy val fib: Stream[Int] = Stream.cons(0,
> Stream.cons(1,fib.zip(fib.tail).map(p=> p._1 + p._2)))
I should point out this doesn't even have to be lazy.
--
Paul Phillips | Simplicity and elegance are unpopular because
Apatheist | they require hard work and discipline to achieve
Empiricist | and education to be appreciated.
up hill, pi pals! | -- Dijkstra
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda
This is one of my favourites: http://www.scalatest.org/(check out the quick start) Or maybe this: http://squeryl.org/
as for Views...
No, these are not about type inheritance, but about type conversion. For example, Int and Float both derive from AnyVal, but NOT from each other.So you can't say that an Int is-a Float (at least, not in Scala's type system)however, an Int CAN be viewed-as a Float
any method defined in the form: def myMethod[T <% Float](input:T) = ...
will only be valid so long as there is an implicit T=>Float function currently in scope. So if you call myMethod(6), T will be Int and the required implicit will have the signature Int=>Float
In fact, View bounds are just syntactic sugar, so the above example is converted in an early compiler phase to: def myMethod[T](input:T)(implicit view:T=>Float) = ...
(the actual param name wont be `view`, some synthetic name will be generated instead)
In normal use, the second (implicit) parameter block doesn't need to be specified, but it WILL ultimately be provided by the caller. So: myMethod(6)Is actually translated as myMethod(6)(Predef.intToFloat _)
This is achieved by e.g. the "implict" function intToFloat, as defined in Predef (http://www.scala-lang.org/api/current/scala/Predef$.html)
As intToFloat is the only implicit of type Int=>Float that is in scope at the call-site. The compiler correctly knows how to wire together everything for you, and it Just Works(tm). It's clever like that...
Predef._, in case you were wondering, is automatically imported by all your source files.
On 6 August 2010 00:00, Andrew Milkowski <andrewmilkowski@gmail.com> wrote:
--
Kevin Wright
mail/google talk: kev.lee.wright@gmail.com
wave: kev.lee.wright@googlewave.com
skype: kev.lee.wright
twitter: @thecoda