Thursday, November 12, 2009

Iterator.Sliding

This topic requires Scala 2.8 or higher.

Iterator and Iterable have most of the most useful methods when dealing with collections. Fold, Map, Filter are probably the most common. But other very useful methods include grouped/groupBy, sliding, find, forall, foreach, and many more. I want to cover Iterator's sliding method.

The def sliding[B >: A](size : Int, step : Int) : GroupedIterator[B] method provides a sliding window on the iterator. The first parameter is the size of the window and the second is the number of elements to skip each time the window is moved. If step == size then this method is the same as grouped. Step defaults to one

Examples:
  1. // notice resulting lists are all 3 long and increases by 1
  2. scala> (1 to 5).iterator.sliding(3).toList
  3. res18: List[Sequence[Int]] = List(List(1, 2, 3), List(2, 3, 4), List(3, 4, 5))
  4. // step is 3 so now there are only 2 groups
  5. scala> (1 to 5).iterator.sliding(4, 3).toList
  6. res19: List[Sequence[Int]] = List(List(1, 2, 3, 4), List(4, 5))
  7. // withPartial(false) makes the partial group be ignored
  8. scala> (1 to 5).iterator.sliding(4, 3).withPartial(false).toList
  9. res21: List[Sequence[Int]] = List(List(1, 2, 3, 4))
  10. scala> val it2 = Iterator.iterate(20)(_ + 5)
  11. it2: Iterator[Int] = non-empty iterator
  12. // withPadding fills in the partial group
  13. // notice with padding is by-name (it is executed each time it is called)
  14. scala> (1 to 5).iterator.sliding(4, 3).withPadding(it2.next).toList
  15. res23: List[Sequence[Int]] = List(List(1, 2, 3, 4), List(4, 5, 20, 25))

Wednesday, November 11, 2009

Introduction to Actors

The support for Actors is one of the features that attracts many new developers to Scala. It is not the only concurrancy construct in Scala but it is one of the most recognized.

An actor is essentially an active object. Instead of calling methods on the actor messages are passed to the actor and the message will be handled in a thread. Resources about actors can be found all over the internet a couple pages to look at are:
This is a big topic about how threads are scheduled and so on but for now we will write a simple little program that downloads several webpages in parallel.
  1. scala> import scala.actors.Actor
  2. import scala.actors.Actor
  3. scala> import Actor._
  4. import scala.actors.Actor._
  5. scala>  val collector = actor {
  6.      |   var count = 3
  7.      |   var data = ""
  8.      |   loop {
  9.      |   react { 
  10.      |    case payload:String => {
  11.      |      reply ("thank you")
  12.      |      data += payload + "\n\n"
  13.      |      count -= 1
  14.      |      if (count == 0) {
  15.      |        println (data)
  16.      |        exit()
  17.      |     }
  18.      |    }
  19.      |  }
  20.      | }
  21.      | }
  22. collector: scala.actors.Actor = scala.actors.Actor$$anon$1@2bbef4c6
  23. scala> import scala.io.Source
  24. import scala.io.Source
  25. scala> class Downloader(url:Stringextends Actor {
  26.      |  def act = {
  27.      |   val source = Source.fromURL(new java.net.URL(url))
  28.      |   val data = source.getLines.mkString("\n")
  29.      |   collector ! data
  30.      |   receive { case s => println("Done with "+url) }
  31.      |  }
  32.      | }
  33. defined class Downloader
  34. scala> List("http:/daily-scala.blogspot.com/2009/11/using-objects-as-functions.html",
  35.      |      "http:/daily-scala.blogspot.com/2009/10/boolean-extractors.html",
  36.      |      "http:/daily-scala.blogspot.com/2009/08/java-vs-scala-control-structures.html",
  37.      |      "http:/www.blogger.com/profile/07600430363435495915")
  38. res0: List[java.lang.String] = List(http:/daily-scala.blogspot.com/2009/11/using-objects-as-functions.html, http:/daily-scala.blogspot.com/2009/10/boolean-extractors.html, http:/daily-scala.blogspot.com/2009/08/java-vs-scala-control-structures.html, http:/www.blogger.com/profile/07600430363435495915)
  39. scala> for (url <- res0) { 
  40.      | new Downloader(url).start
  41.      | }
  42. [snip... lots of output]

Update:
If this program is put into a file and executed it will not finish is because the program exits. What is happening is there are 6 "actors" the main thread, collector and the 4 Downloaders. The main thread completes and shutdown the system taking all the Actors with it.

Just add link(collector) as the last line to make the main trhead wait for collector.

Also important to realize is that in Scala 2.7 an actor is lightweight. IE the application can exit while actors are still alive. In Scala 2.8 that is changed. For Scala 2.7 semantics you must use a DaemonActor instead of Actor.

Monday, November 9, 2009

Using objects as functions

A fun but easily overlooked fact is that many classes inherit from a Function class and therefore can be used where "normal" functions can be used.
  1. scala> List(1,2) map (Map(1->"one",2->"two"))
  2. res0: List[java.lang.String] = List(one, two)
  3. scala> List(3,3,2) map (List('a''b''c','d'))
  4. res2: List[Char] = List(d, d, c)

Sunday, November 8, 2009

BigInt in Scala

One of the best examples of why it is so great to use Scala for API design is BigInt. Using BigInt in Java is a real headache because of the limitations of Java with regards to API design. Scala in comparison makes using BigInt no different than using Ints (with execution that there is not a BigInt literal).

  1. // BigInt objects can be created from ints
  2. scala> val x = BigInt(1500)
  3. x: BigInt = 1500
  4. // or longs
  5. scala> val y = BigInt(8839200231L)
  6. y: BigInt = 8839200231
  7. // or strings
  8. scala> val z = BigInt("1234566789008723457802308972345723470589237507")
  9. z: BigInt = 1234566789008723457802308972345723470589237507
  10. // then thanks to scala you can multiply/divide/add/subtract etc...
  11. // as if it was a Scala literal
  12. scala> x * y * z
  13. res0: BigInt = 16368874569886254973831932331037537269641764816982396175500
  14. // by importing implicits you can also directly multiply big ints with integers and longs
  15. // however remember to put the big in first so that the int is converted to big int
  16. // because you cannot do Int * BigInt.  It must be BigInt * Int
  17. scala> import BigInt._
  18. import BigInt._
  19. scala> x * y * z * 124
  20. res1: BigInt = 2029740446665895616755159609048654621435578837305817125762000

Thursday, November 5, 2009

Function._

If you have not looked at the Function object I would recommend you do. It contains several useful methods for combining and converting functions.

Examples:
  1. cala> def twoParamFunc( i:Int, j:String) = println(i,j)
  2. twoParamFunc: (i: Int,j: String)Unit
  3. // the tupled method converts the function with n parameters into
  4. // a function that takes one tupleN
  5. scala> val tupled = Function tupled twoParamFunc _
  6. tupled: ((IntString)) => Unit = < function1>
  7. scala> tupled (1 -> "one"
  8. (1,one)
  9. // A practical use-case is to convert an existing method
  10. // for use with a Map
  11. // Example with out using the tupled method
  12. scala> Map( 1 -> "one", 2 -> "two") map (entry => twoParamFunc(entry._1, entry._2)) 
  13. (1,one)
  14. (2,two)
  15. res5: scala.collection.immutable.Iterable[Unit] = List((), ())
  16. // example using tupled
  17. scala> Map( 1 -> "one", 2 -> "two") map (tupled)  
  18. (1,one)
  19. (2,two)
  20. res7: scala.collection.immutable.Iterable[Unit] = List((), ())
  21. // and for balance the opposite
  22. scala> val untupled = Function untupled tupleParamFunc _
  23. untupled: (IntString) => Unit = < function2>
  24. scala> untupled(1, "one"
  25. tuple = (1,one)
  26. // Chain is for chaining together an arbitrary number of functions
  27. scala> def inc(i:Int) = i + 1 
  28. inc: (i: Int)Int
  29. scala> def double(i:Int) = i*i
  30. double: (i: Int)Int
  31. scala> def decr(i:Int) = i - 1
  32. decr: (i: Int)Int
  33. scala> (Function chain List(inc _, double _, decr _, double _, inc _, inc _))(3)
  34. res10: Int = 227
  35. // Now examples curries two methods then chains them together
  36. // define basic methods
  37. scala> def inc(step:Int,i:Int) = i + step 
  38. inc: (step: Int,i: Int)Int
  39. scala> def multiply(i:Int, j:Int) = i * j
  40. multiply: (i: Int,j: Int)Int
  41. // Convert them to methods where the first argument is 3
  42. scala> val inc3 = (Function curried inc _)(3)
  43. inc3: (Int) => Int = < function1>
  44. scala> val multiplyBy3 = (Function curried multiply _)(3)
  45. multiplyBy3: (Int) => Int = < function1>
  46. // chain the resulting Function1 objects together and execute chain with parameter 3
  47. // (3 + 3)*3 = 18
  48. scala> chain(List(inc3, multiplyBy3))(3)
  49. res12: Int = 18

Access modifiers (public, private, protected)

By default classes, objects and class members (fields, methods) are all public.
IE:
  1. object PublicObject {
  2.   val publicVal
  3.   var publicVar
  4.   def publicMethod = 1
  5. }

In this example everything is public. Similar to Java there is private and protected (there is no public because that is default). Private works as it does in Java but protected is dramatically different.
  • The first difference is that protected can have two forms: protected and protected[foo]. Where foo can be a class, package or object.

  • The second difference is that the non-parameterized protected for is only visible from subclasses not from the same package.
  1. scala> class Class1 {
  2.      | protected def pMethod = "protected"
  3.      | }
  4. defined class Class1
  5. scala> class Class2 { 
  6. // pMethod is not accessible because Class2 is not a subclass of Class1
  7.      | new Class1().pMethod 
  8.      | }
  9. <console>:6: error: method pMethod cannot be accessed in Class1
  10.        new Class1().pMethod
  11.                     ^
  12. scala> class Class3 extends Class1 {
  13. // also unlike Java, protected restricts to the same object
  14.      | new Class1().pMethod
  15.      | }
  16. <console>:6: error: method pMethod cannot be accessed in Class1
  17.        new Class1().pMethod
  18.                     ^
  19. scala> class Class3 extends Class1 {
  20.      | pMethod
  21.      | }
  22. defined class Class3

If the protected is parameterized then only classes that fall into the parameter category can access the parameter:
  1. scala> class Class1 {                                
  2. // protected[Class1] is equivalent to private
  3.      | protected[Class1] def method() = println("hi")
  4.      | method()
  5.      | }
  6. defined class Class1
  7. scala> new Class1()
  8. hi
  9. res0: Class1 = Class1@dc44a6d
  10. // this does not work because method is only accessible in Class1
  11. scala> class Class2 extends Class1 { method() }      
  12. <console>:5: error: not found: value method
  13.        class Class2 extends Class1 { method() }
  14.                                      ^
  15. scala> object Module {                                         
  16.      |   object Inner1 {                                         
  17.      |     protected[Inner1] def innerMethod = println("hi")       
  18.      |     protected[Module] def moduleMethod = println("moduleMethod")
  19.      |
  20.      |     object InnerInner { 
  21.      |       // InnerInner is within Inner1 so the access works
  22.      |       def callInner = innerMethod
  23.      |     }
  24.      |   }
  25.      |   // module method is protected[Module] so anything in Module can access it
  26.      |   def callModuleMethod = Inner1.moduleMethod
  27.      |
  28.      |   object Inner2 {
  29.      |     // Inner1.module method is protected[Module] and 
  30.      |     // Inner2 is within module so therefore has access
  31.      |     def callModuleMethod = Inner1.moduleMethod
  32.      |   }
  33.      | }
  34. defined module Module
  35. scala> Module.callModuleMethod
  36. moduleMethod
  37. scala> Module.Inner1.InnerInner.callInner
  38. hi
  39. scala> Module.Inner1.innerMethod         
  40. <console>:6: error: method innerMethod cannot be accessed in object Module.Inner1
  41.        Module.Inner1.innerMethod
  42.                      ^
  43. scala> Module.Inner1.moduleMethod
  44. <console>:6: error: method moduleMethod cannot be accessed in object Module.Inner1
  45.        Module.Inner1.moduleMethod

The following example shows how package access works in Scala 2.8. They have to be compiled as 2 files.

Root.scala:
  1. package root
  2. class Class1 {
  3.   protected[root] def rootMethod = println("rootMethod")
  4. }
  5. class Class2 {
  6.   // same package so this is legal
  7.   new Class1().rootMethod
  8. }


Subpackage.scala
  1. package root.sub
  2. class Class3 {
  3.   // Class3 is in a subpackage of root so 
  4.   // it can access all objects protected by
  5.   // protected[root] as well as objects
  6.   // protected by protected[root.sub]
  7.   new root.Class1().rootMethod
  8. }

Tuesday, November 3, 2009

Non-strict (lazy) Collections

This topic discusses non-strict collections. There is a fair bit of confusion with regards to non-strict collections: what to call them and what are they. First lets clear up some definitions.

Pre Scala 2.8 collections have a projection method. This returns a non-strict collections. So often non-strict collections are called projections in Pre Scala 2.8
Scala 2.8+ the method was changed to view, so in Scala 2.8+ view sometimes refers to non-strict collections (and sometime to a implicit conversion of a class)
Another name for non-strict collections I have seen is "lazy collections."

All those labels are for the same thing "non-strict collections" which is the functional programming term and which I will use for the rest of this topic.

As an excellent addition to this topic please take a look at Strict Ranges? by Daniel Sobral.

One way to think of non-strict collections are pull collections. A programmer can essentially form a sequence of functions and the evaluation is only performed on request.

Note: I am intentionally adding side effects to the processes in order to demonstrate where processing takes place. In practice the collectionsshould be immutable (ideally) and the processing the collections really should be side-effect free. Otherwise almost guaranteed you will find yourself with a bug that is almost impossible to find.

Example of processing a strict collection:
  1. scala> var x=0
  2. x: Int = 0
  3. scala> def inc = {
  4.      | x += 1
  5.      | x
  6.      | }
  7. inc: Int
  8. scala> var list =  List(inc _, inc _, inc _)
  9. list: List[() => Int] = List(<function0><function0><function0>)
  10. scala> list.map (_()).head
  11. res0: Int = 1
  12. scala> list.map (_()).head
  13. res1: Int = 4
  14. scala> list.map (_()).head
  15. res2: Int = 7

Notice how each time the expression is called x is incremented 3 times. Once for each element in the list. This demonstrates that map is being called for every element of the list even though only head is being calculated. This is strict behaviour.

Example of processing a non-strict collection with Scala 2.7.5
For Scala 2.8 change project => view.
  1. scala> var x=0
  2. x: Int = 0
  3. scala> def inc = {
  4.      | x += 1
  5.      | x
  6.      | }
  7. inc: Int
  8. scala> var list =  List(inc _, inc _, inc _)
  9. list: List[() => Int] = List(<function0><function0><function0>)
  10. scala> list.projection.map (_()).head
  11. res0: Int = 1
  12. scala> list.projection.map (_()).head
  13. res1: Int = 2
  14. scala> list.projection.map (_()).head
  15. res2: Int = 3
  16. scala> list.projection.map (_()).head
  17. res3: Int = 4

Here you can see that only one element in the list is being calculated for the head request. That is the idea behind non-strict collections and can be useful when dealing with large collections and very expensive operations. This also demonstrates why side-effects are so crazy dangerous!.

More examples (Scala 2.8):
  1. scala> var x=0
  2. x: Int = 0
  3. scala> def inc = { x +=1; x }
  4. inc: Int
  5. // strict processing of a range and obtain the 6th element
  6. // this will run inc for every element in the range
  7. scala> (1 to 10).map( _ + inc).apply(5)
  8. res2: Int = 12
  9. scala> x
  10. res3: Int = 10
  11. // reset for comparison
  12. scala> x = 0
  13. x: Int = 0
  14. // now non-strict processing but the same process
  15. // you get a different answer because only one
  16. // element is calculated
  17. scala> (1 to 10).view.map( _ + inc).apply(5)
  18. res6: Int = 7
  19. // verify that x was incremented only once
  20. scala> x
  21. res7: Int = 1
  22. // reset for comparison
  23. scala> x = 0
  24. x: Int = 0
  25. // force forces strict processing
  26. // now we have the same answer as if we did not use view
  27. scala> (1 to 10).view.map( _ + inc).force.apply(5)
  28. res9: Int = 12
  29. scala> x
  30. res10: Int = 10
  31. // reset for comparison
  32. scala> x = 0
  33. x: Int = 0
  34. // first 5 elements are computed only
  35. scala> (1 to 10).view.map( _ + inc).take(5).mkString(",")
  36. res9: String = 2,4,6,8,10
  37. scala> x
  38. res10: Int = 5
  39. // reset for comparison
  40. scala> x = 0
  41. x: Int = 0
  42. // only first two elements are computed
  43. scala> (1 to 10).view.map( _ + inc).takeWhile( _ < 5).mkString(",")
  44. res11: String = 5,7
  45. scala> x
  46. res12: Int = 5
  47. // reset for comparison
  48. scala> x = 0
  49. x: Int = 0
  50. // inc is called 2 for each element but only the last 5 elements are computed so
  51. // x only == 10 not 20
  52. scala> (1 to 10).view.map( _ + inc).map( i => inc ).drop(5).mkString(",")
  53. res16: String = 2,4,6,8,10
  54. scala> x
  55. res17: Int = 10
  56. scala> x = 0                                             
  57. x: Int = 0
  58. // define this for-comprehension in a method so that
  59. // the repl doesn't call toString on the result value and
  60. // as a result force the full list to be processed
  61. scala> def add = for( i <- (1 to 10).view ) yield i + inc
  62. add: scala.collection.IndexedSeqView[Int,IndexedSeq[_]]
  63. scala> add.head                                          
  64. res5: Int = 2
  65. // for-comprehensions will also be non-strict if the generator is non-strict
  66. scala> x
  67. res6: Int = 1