<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-5089773352404981635</id><updated>2012-01-19T05:30:33.039-08:00</updated><category term='yield'/><category term='plans'/><category term='package'/><category term='reduceRight'/><category term='either'/><category term='eq'/><category term='actor'/><category term='String'/><category term='ne'/><category term='conversion'/><category term='type-inference'/><category term='require'/><category term='method'/><category term='variance'/><category term='apply'/><category term='partial-function'/><category term='array'/><category term='roadmap'/><category term='test'/><category term='inheritance'/><category term='with'/><category term='Source'/><category term='beanproperty'/><category term='self-annotation'/><category term='for-comprehension'/><category term='projection'/><category term='classes'/><category term='function'/><category term='xpath'/><category term='default argument'/><category term='abstract type'/><category term='RichString'/><category term='bigint'/><category term='fold'/><category term='traits'/><category term='invariance'/><category term='intermediate'/><category term='future'/><category term='while'/><category term='covariance'/><category term='xml'/><category term='style-guide'/><category term='select'/><category term='type'/><category term='type-bound'/><category term='foreach'/><category term='java'/><category term='refactor'/><category term='copy file'/><category term='collect'/><category term='import alias'/><category term='property'/><category term='object'/><category term='transformation'/><category term='companion'/><category term='regular expression'/><category term='links'/><category term='filter'/><category term='case'/><category term='unfold'/><category term='back-tick'/><category term='Map'/><category term='rule'/><category term='editor'/><category term='protected'/><category term='iterable'/><category term='Advanced'/><category term='try'/><category term='do-while'/><category term='view'/><category term='Product'/><category term='symbol'/><category term='dsl'/><category term='underscore'/><category term='linearization'/><category term='bean'/><category term='project'/><category term='beaninfo'/><category term='case-object'/><category term='self-type'/><category term='error'/><category term='ide'/><category term='fixture'/><category term='named argument'/><category term='data object'/><category term='url'/><category term='reflection'/><category term='daily-scala'/><category term='operator'/><category term='return'/><category term='Enumeration'/><category term='list'/><category term='generic'/><category term='scalatest'/><category term='.Net'/><category term='monad'/><category term='import'/><category term='groupby'/><category term='seq'/><category term='option'/><category term='varargs'/><category term='syntactic sugar'/><category term='assume'/><category term='match'/><category term='Scala'/><category term='extractor'/><category term='for'/><category term='specs'/><category term='case-classes'/><category term='notice'/><category term='contravariance'/><category term='else'/><category term='reduceLeft'/><category term='range'/><category term='casting'/><category term='lazy-val'/><category term='file'/><category term='factory-method'/><category term='matching'/><category term='2.8'/><category term='scripts'/><category term='structural types'/><category term='if'/><category term='update'/><category term='val'/><category term='assert'/><category term='currying'/><category term='tail-recursion'/><category term='enum'/><category term='catch'/><category term='geoscript'/><category term='GenericCanBuildFrom'/><category term='reduce'/><category term='stream'/><category term='random'/><category term='manifest'/><category term='guard'/><category term='predef'/><category term='unapplySeq'/><category term='break'/><category term='MatchError'/><category term='sliding'/><category term='context'/><category term='elidable'/><category term='unapply'/><category term='non-strict'/><category term='flatmap'/><category term='constructor'/><category term='null'/><category term='properties'/><category term='private'/><category term='regex'/><category term='tuple'/><category term='implicit'/><category term='iterator'/><category term='GenericTraversableTemplate'/><category term='swap'/><category term='exception'/><category term='datastructure'/><category term='collections'/><category term='assignment'/><category term='by-name-parameter'/><category term='equals'/><category term='type alias'/><category term='unzip'/><category term='REPL'/><category term='raw strings'/><category term='beginner'/><category term='traversable'/><category term='control structure'/><category term='zip'/><title type='text'>Daily scala</title><subtitle type='html'>A short daily dose of scala examples and occasionally explanations.</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><link rel='next' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default?start-index=101&amp;max-results=100'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>151</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-9110665934253058118</id><published>2010-05-27T23:28:00.000-07:00</published><updated>2010-05-27T23:28:16.347-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='foreach'/><category scheme='http://www.blogger.com/atom/ns#' term='fold'/><category scheme='http://www.blogger.com/atom/ns#' term='filter'/><category scheme='http://www.blogger.com/atom/ns#' term='zip'/><category scheme='http://www.blogger.com/atom/ns#' term='view'/><title type='text'>zipWithIndex</title><content type='html'>A common desire is to have access to the index of an element when using collection methods like foreach, filter, foldLeft/Right, etc...  Fortunately there is a simple way.  &lt;br /&gt; &lt;br /&gt;&lt;code&gt;List(&lt;span class="char"&gt;'a'&lt;/span&gt;,&lt;span class="char"&gt;'b'&lt;/span&gt;,&lt;span class="char"&gt;'c'&lt;/span&gt;,&lt;span class="char"&gt;'d'&lt;/span&gt;).zipWithIndex&lt;/code&gt;.  &lt;br /&gt; &lt;br /&gt;But wait!  &lt;br /&gt; &lt;br /&gt;Does that not trigger an extra iteration through the collection?.  Indeed it does and that is where &lt;a href="http://daily-scala.blogspot.com/search/label/view"&gt;Views&lt;/a&gt; help. &lt;br /&gt;&lt;br /&gt;&lt;code&gt;List(&lt;span class="char"&gt;'a'&lt;/span&gt;,&lt;span class="char"&gt;'b'&lt;/span&gt;,&lt;span class="char"&gt;'c'&lt;/span&gt;,&lt;span class="char"&gt;'d'&lt;/span&gt;).view.zipWithIndex&lt;/code&gt;  &lt;br /&gt;&lt;br /&gt;When using a &lt;a href="http://daily-scala.blogspot.com/search/label/view"&gt;view&lt;/a&gt; the collection is only traversed when required so there is no performance loss.&lt;br /&gt; &lt;br /&gt;Here are some examples of zipWithIndex:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;list&amp;#160;=&amp;#160;List(&lt;span class="char"&gt;'a'&lt;/span&gt;,&lt;span class="char"&gt;'b'&lt;/span&gt;,&lt;span class="char"&gt;'c'&lt;/span&gt;,&lt;span class="char"&gt;'d'&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;list:&amp;#160;List&lt;span class="type-param"&gt;[Char]&lt;/span&gt;&amp;#160;=&amp;#160;List(a,&amp;#160;b,&amp;#160;c,&amp;#160;d)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;I&amp;#160;like&amp;#160;to&amp;#160;use&amp;#160;functions&amp;#160;constructed&amp;#160;with&amp;#160;case&amp;#160;statements&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;in&amp;#160;order&amp;#160;to&amp;#160;clearly&amp;#160;label&amp;#160;the&amp;#160;index.&amp;#160;&amp;#160;The&amp;#160;alternative&amp;#160;is&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;to&amp;#160;use&amp;#160;x._2&amp;#160;for&amp;#160;the&amp;#160;index&amp;#160;and&amp;#160;x._1&amp;#160;for&amp;#160;the&amp;#160;value&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;list.view.zipWithIndex&amp;#160;foreach&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(value,index)&amp;#160;=&gt;&amp;#160;println(value,index)}&lt;/li&gt;&lt;li class="codelist "&gt;(a,0)&lt;/li&gt;&lt;li class="codelist alt"&gt;(b,1)&lt;/li&gt;&lt;li class="codelist "&gt;(c,2)&lt;/li&gt;&lt;li class="codelist alt"&gt;(d,3)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;alternative&amp;#160;syntax&amp;#160;without&amp;#160;case&amp;#160;statement&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;list.view.zipWithIndex&amp;#160;foreach&amp;#160;{e&amp;#160;=&gt;&amp;#160;println(e._1,e._2)}&lt;/li&gt;&lt;li class="codelist alt"&gt;(a,0)&lt;/li&gt;&lt;li class="codelist "&gt;(b,1)&lt;/li&gt;&lt;li class="codelist alt"&gt;(c,2)&lt;/li&gt;&lt;li class="codelist "&gt;(d,3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Fold&amp;#160;left&amp;#160;and&amp;#160;right&amp;#160;functions&amp;#160;have&amp;#160;2&amp;#160;parameters&amp;#160;(accumulator,&amp;#160;nextValue)&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;using&amp;#160;a&amp;#160;case&amp;#160;statement&amp;#160;allows&amp;#160;you&amp;#160;to&amp;#160;expand&amp;#160;that&amp;#160;but&amp;#160;watch&amp;#160;the&amp;#160;brackets!&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(list.view.zipWithIndex&amp;#160;foldLeft&amp;#160;0)&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(acc,(value,index))&amp;#160;=&gt;&amp;#160;acc&amp;#160;+&amp;#160;value.toInt&amp;#160;+&amp;#160;index}&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res14:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;400&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;alternative&amp;#160;syntax&amp;#160;without&amp;#160;case&amp;#160;statement&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(list.view.zipWithIndex&amp;#160;foldLeft&amp;#160;0)&amp;#160;{(acc,e)&amp;#160;=&gt;&amp;#160;acc&amp;#160;+&amp;#160;e._1.toInt&amp;#160;+&amp;#160;e._2}&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res23:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;400&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;alternative&amp;#160;foldLeft&amp;#160;operator.&amp;#160;&amp;#160;The&amp;#160;thing&amp;#160;I&amp;#160;like&amp;#160;about&amp;#160;this&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;syntax&amp;#160;is&amp;#160;that&amp;#160;it&amp;#160;has&amp;#160;the&amp;#160;initial&amp;#160;accumulator&amp;#160;value&amp;#160;on&amp;#160;the&amp;#160;left&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;in&amp;#160;the&amp;#160;same&amp;#160;position&amp;#160;as&amp;#160;the&amp;#160;accumulator&amp;#160;parameter&amp;#160;in&amp;#160;the&amp;#160;function.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;The&amp;#160;other&amp;#160;thing&amp;#160;I&amp;#160;like&amp;#160;about&amp;#160;it&amp;#160;is&amp;#160;that&amp;#160;visually&amp;#160;you&amp;#160;can&amp;#160;see&amp;#160;that&amp;#160;it&amp;#160;starts&amp;#160;with&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;""&amp;#160;and&amp;#160;the&amp;#160;folds&amp;#160;left&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(&lt;span class="string"&gt;""&lt;/span&gt;&amp;#160;/:&amp;#160;list.view.zipWithIndex)&amp;#160;{&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(acc,&amp;#160;(value,&amp;#160;index))&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;index&amp;#160;%&amp;#160;2&amp;#160;==&amp;#160;0&amp;#160;=&gt;&amp;#160;acc&amp;#160;+&amp;#160;value&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(acc,&amp;#160;_)&amp;#160;=&gt;&amp;#160;acc&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;res15:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;ac&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;This&amp;#160;example&amp;#160;filters&amp;#160;based&amp;#160;on&amp;#160;the&amp;#160;index&amp;#160;then&amp;#160;uses&amp;#160;map&amp;#160;to&amp;#160;remove&amp;#160;the&amp;#160;index&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;force&amp;#160;simply&amp;#160;forces&amp;#160;the&amp;#160;view&amp;#160;to&amp;#160;be&amp;#160;processed.&amp;#160;&amp;#160;(I&amp;#160;love&amp;#160;these&amp;#160;collections!)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;list.view.zipWithIndex.filter&amp;#160;{&amp;#160;_._2&amp;#160;%&amp;#160;2&amp;#160;==&amp;#160;0&amp;#160;}.map&amp;#160;{&amp;#160;_._1}.force&lt;/li&gt;&lt;li class="codelist "&gt;res29:&amp;#160;Seq&lt;span class="type-param"&gt;[Char]&lt;/span&gt;&amp;#160;=&amp;#160;List(a,&amp;#160;c)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-9110665934253058118?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/9110665934253058118/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/05/zipwithindex.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/9110665934253058118'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/9110665934253058118'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/05/zipwithindex.html' title='zipWithIndex'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-7155941879432405408</id><published>2010-05-26T23:41:00.000-07:00</published><updated>2010-05-26T23:41:07.546-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='function'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><title type='text'>Return value of a block</title><content type='html'>A common misunderstanding is that a code block (without parameters) is a function.  That is not the case.  A code block is a sequence of statements that are executed and result the last statement is returned.  That sounds like a Function0, however, if the block is passed to a method/function only the last statement will be returned to the function/method.  If that method/function expects a function as the parameter the last statement maybe returned as a function not a value, this means that the block itself is not a function.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;count&amp;#160;=&amp;#160;0&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;count:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;0&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;the&amp;#160;last&amp;#160;statement&amp;#160;is&amp;#160;returned&amp;#160;as&amp;#160;a&amp;#160;function&amp;#160;so&amp;#160;count&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;is&amp;#160;incremented&amp;#160;only&amp;#160;one&amp;#160;during&amp;#160;the&amp;#160;creation&amp;#160;of&amp;#160;the&amp;#160;function&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(1,2,3,4).map{count&amp;#160;+=&amp;#160;1;_&amp;#160;+&amp;#160;1}&lt;/li&gt;&lt;li class="codelist alt"&gt;res9:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(2,&amp;#160;3,&amp;#160;4,&amp;#160;5)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;count&lt;/li&gt;&lt;li class="codelist "&gt;res10:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;now&amp;#160;the&amp;#160;count&amp;#160;increment&amp;#160;is&amp;#160;within&amp;#160;the&amp;#160;function&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(1,2,3,4).map{i&amp;#160;=&gt;&amp;#160;count&amp;#160;+=&amp;#160;1;i&amp;#160;+&amp;#160;1}&lt;/li&gt;&lt;li class="codelist "&gt;res11:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(2,&amp;#160;3,&amp;#160;4,&amp;#160;5)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;count&lt;/li&gt;&lt;li class="codelist alt"&gt;res12:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;5&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;The previous example demonstrates a Gotcha if I ever saw one.  Map expects a function so the block essentially constructs a function.  The last statement being the function.  The first line &lt;code&gt;count&amp;#160;+=&amp;#160;1&lt;/code&gt; executed only once because it is part of creating the function not part of the resulting function.  This is equivalent to:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;{count&amp;#160;+=&amp;#160;1&amp;#160;;&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;i&amp;#160;+1}&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(1,2,3,4).map(x)&lt;/li&gt;&lt;li class="codelist alt"&gt;res15:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(2,&amp;#160;3,&amp;#160;4,&amp;#160;5)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Beginning a block with the parameter list signals that the entire block is a function.&lt;br /&gt; &lt;br /&gt;Rule of thumb: Functions with placeholder parameters should be a single statement.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-7155941879432405408?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/7155941879432405408/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/05/return-value-of-block.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7155941879432405408'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7155941879432405408'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/05/return-value-of-block.html' title='Return value of a block'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-5169502204105236215</id><published>2010-05-20T00:04:00.001-07:00</published><updated>2010-05-20T00:05:31.660-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='type-inference'/><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='abstract type'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><title type='text'>Type Inference with Abstract Types</title><content type='html'>A second "gotcha" that one might get tripped up when dealing with abstract types is the signature of the concrete class contains type information about the abstract type. So if you are not explicit when assigning a variable or defining a function you can get unexpected compiler errors.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;:&amp;#160;x&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;S&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;sample&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;=&amp;#160;3&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;sample:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;S{&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;}&amp;#160;=&amp;#160;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;397af435&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;sample&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;=&amp;#160;3.0&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:7:&amp;#160;error:&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;mismatch;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;S&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;required:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;S{&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;sample&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;In this example &lt;em&gt;sample&lt;/em&gt; uses type inference so the actual type is &lt;em&gt;S with underlying type Int&lt;/em&gt;.  The consequence is that &lt;em&gt;sample&lt;/em&gt; can only be assigned with instances of S with &lt;em&gt;type x = Int&lt;/em&gt;. The fix is to explicitly declare the variable type:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;sample2&amp;#160;:&amp;#160;S&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;=&amp;#160;3&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;sample2:&amp;#160;S&amp;#160;=&amp;#160;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;31602bbc&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;sample2&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;=&amp;#160;3.0&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;sample2:&amp;#160;S&amp;#160;=&amp;#160;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;4de5ed7b&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;The same thing happens when declaring functions and allows type inference for function definition&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Fac&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;newS&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;=&amp;#160;3&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Fac&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;SubFac&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Fac{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;override&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;newS&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;get&amp;#160;=&amp;#160;3.0&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:8:&amp;#160;error:&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;mismatch;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;S&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;required:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;S{&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;override&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;newS&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;S&amp;#160;{&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;The fix for this example is to be explicit in the definition of the function in the superclass&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-5169502204105236215?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/5169502204105236215/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/05/type-inference-with-abstract-types.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5169502204105236215'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5169502204105236215'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/05/type-inference-with-abstract-types.html' title='Type Inference with Abstract Types'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-7703441129559722054</id><published>2010-05-17T02:24:00.000-07:00</published><updated>2010-05-17T02:24:30.019-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='abstract type'/><category scheme='http://www.blogger.com/atom/ns#' term='Advanced'/><category scheme='http://www.blogger.com/atom/ns#' term='daily-scala'/><title type='text'>Instance Type (Abstract type gotcha 1)</title><content type='html'>In a previous post about abstract types I showed one of the benefits of using abstract types over parameterized types.  &lt;a href="http://daily-scala.blogspot.com/2010/05/abstract-types-vs-parameter.html"&gt;Abstract Types vs Parameter&lt;/a&gt;.  The next several posts will feature potential problems you may encounter when using Abstract Types.&lt;br /&gt; &lt;br /&gt;I should point out that abstract types are not inherently difficult to understand but they are rather different from anything you will see when you come from the Java world so if you are new to them I would use them with caution at first.&lt;br /&gt; &lt;br /&gt;In the &lt;a href="http://daily-scala.blogspot.com/2010/05/abstract-types-vs-parameter.html#full_example"&gt;abstract types example&lt;/a&gt; you will notice that the abstract type 'I' in Foreach is not within the trait Source rather it is outside in the Foreach trait.  At first one might consider putting the type in Source rather than Foreach.  The naive change can get you in trouble (but there is a couple easy fixes)&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Foreach&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Source&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;I&amp;#160;&amp;lt;:&amp;#160;java.io.Closeable&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;moved&amp;#160;this&amp;#160;line&amp;#160;into&amp;#160;Source&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;in&amp;#160;:&amp;#160;I&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;next(in&amp;#160;:&amp;#160;I)&amp;#160;:&amp;#160;Option&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;:&amp;#160;Source&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f&amp;#160;:&amp;#160;A&amp;#160;=&gt;&amp;#160;U)&amp;#160;:&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;s&amp;#160;=&amp;#160;source.in&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;try&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;processNext&amp;#160;:&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;#160;=&amp;#160;source.next(s)&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;None&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;()&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;Some(value)&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;f(value)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;processNext&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;processNext&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&amp;#160;&lt;span class="key"&gt;finally&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;correctly&amp;#160;handle&amp;#160;exceptions&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;s.close&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Compiling the class results in a compilation error:&lt;br /&gt;&lt;quot&gt; &lt;br /&gt;jeichar: tmp$ scalac XX.scala &lt;br /&gt;XX.scala:12: error: type mismatch;&lt;br /&gt; found   : s.type (with underlying type Foreach.this.Source#I)&lt;br /&gt; required: _2.I where val _2: Foreach.this.Source&lt;br /&gt;      def processNext : Unit = source.next(s) match {&lt;br /&gt;                                           ^&lt;br /&gt;XX.scala:16: error: type mismatch;&lt;br /&gt; found   : value.type (with underlying type Any)&lt;br /&gt; required: A&lt;br /&gt;          f(value)&lt;br /&gt;            ^&lt;br /&gt;two errors found&lt;br /&gt;&lt;/quot&gt; &lt;br /&gt;So what is the problem?  The problem is simple but subtle.  Notice that source is defined as a &lt;em&gt;def&lt;/em&gt;.  So calling source 2 times may return 2 different instances of Source.  A simple change can fix this.  Either change def source : Source to val source : Source.  Or change the method foreach to assign the result from source to a val.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Foreach&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Source&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;I&amp;#160;&amp;lt;:&amp;#160;java.io.Closeable&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;moved&amp;#160;this&amp;#160;line&amp;#160;into&amp;#160;Source&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;in&amp;#160;:&amp;#160;I&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;next(in&amp;#160;:&amp;#160;I)&amp;#160;:&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;:&amp;#160;Source&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;U)&amp;#160;:&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;this&amp;#160;assignment&amp;#160;allows&amp;#160;this&amp;#160;example&amp;#160;to&amp;#160;compile&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;sameSource&amp;#160;=&amp;#160;source&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;s&amp;#160;=&amp;#160;sameSource.in&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;try&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;processNext&amp;#160;:&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;#160;=&amp;#160;sameSource.next(s)&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;None&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;()&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;Some(value)&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;f(value)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;processNext&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;processNext&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&amp;#160;&lt;span class="key"&gt;finally&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;correctly&amp;#160;handle&amp;#160;exceptions&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;s.close&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-7703441129559722054?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/7703441129559722054/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/05/instance-type-abstract-type-gotcha-1.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7703441129559722054'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7703441129559722054'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/05/instance-type-abstract-type-gotcha-1.html' title='Instance Type (Abstract type gotcha 1)'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1410821673305630616</id><published>2010-05-03T01:15:00.000-07:00</published><updated>2010-05-17T01:09:14.303-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='abstract type'/><category scheme='http://www.blogger.com/atom/ns#' term='generic'/><title type='text'>Abstract Types vs Parameter</title><content type='html'>This topic (and the next) are intended to discuss abstract types.  A class/trait with an abstract type is quite similar to a class/trait type parameter.  For example:&lt;br /&gt;&lt;code&gt;&lt;/code&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;nbsp;C&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;get&amp;nbsp;:&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;doit(a:A):A&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;nbsp;C2&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;get&amp;nbsp;:&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;doit(a:A):A&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Both implementations have similar properties.  However they are &lt;em&gt;NOT&lt;/em&gt; the same.  At first I thought that I could used them inter-changeably.  However, consider the following examples:&lt;br /&gt;&lt;code&gt;&lt;/code&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//compiles&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;p(c:C&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;nbsp;=&amp;nbsp;c.doit(c.get)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;nbsp;doesn't&amp;nbsp;compile&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;p2(c:C2)&amp;nbsp;=&amp;nbsp;c.doit(c.get)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;So why doesn't p2 compile?  Because it returns A.  From the signature of p2 it is impossible to know what p2 returns.  There are several ways to fix this problem.  One make the method return Unit:&lt;br /&gt;&lt;code&gt;&lt;/code&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;nbsp;compiles&amp;nbsp;because&amp;nbsp;the&amp;nbsp;internals&amp;nbsp;of&amp;nbsp;C2&amp;nbsp;does&amp;nbsp;not&amp;nbsp;leak&amp;nbsp;out&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;p(c:C2):&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;nbsp;=&amp;nbsp;c.doit(c.get)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Another fix would be to change doit to return Unit or an explicit return value like Int&lt;br /&gt;&lt;code&gt;&lt;/code&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;nbsp;C2&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;get&amp;nbsp;:&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;doit(a:A):&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;nbsp;compiles&amp;nbsp;correctly&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;p(c:C2)&amp;nbsp;=&amp;nbsp;c.doit(c.get)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;A second difference between parameterized types and types with abstract type values is illustrated below:&lt;br /&gt;&lt;code&gt;&lt;/code&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;nbsp;C2&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;get&amp;nbsp;:&amp;nbsp;A&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&amp;gt;&lt;/span&gt;&amp;nbsp;&lt;span class="key"&gt;var&lt;/span&gt;&amp;nbsp;c&amp;nbsp;:&amp;nbsp;C2&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;C2&amp;nbsp;{&amp;nbsp;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;|&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;A&amp;nbsp;=&amp;nbsp;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;|&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;get&amp;nbsp;=&amp;nbsp;3&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;|&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;c:&amp;nbsp;C2&amp;nbsp;=&amp;nbsp;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;11a40fff&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;nbsp;what&amp;nbsp;is&amp;nbsp;the&amp;nbsp;type&amp;nbsp;of&amp;nbsp;result&amp;nbsp;if&amp;nbsp;at&amp;nbsp;compile&amp;nbsp;time&amp;nbsp;the&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;nbsp;value&amp;nbsp;of&amp;nbsp;c&amp;nbsp;is&amp;nbsp;not&amp;nbsp;known&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&amp;gt;&lt;/span&gt;&amp;nbsp;&lt;span class="key"&gt;var&lt;/span&gt;&amp;nbsp;result&amp;nbsp;=&amp;nbsp;c.get&lt;/li&gt;&lt;li class="codelist alt"&gt;result:&amp;nbsp;C2#A&amp;nbsp;=&amp;nbsp;3&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&amp;gt;&lt;/span&gt;&amp;nbsp;c&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;C2&amp;nbsp;{&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;|&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;A&amp;nbsp;=&amp;nbsp;&lt;span class="basicType"&gt;String&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;|&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;get&amp;nbsp;=&amp;nbsp;&lt;span class="string"&gt;"hi"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;|&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;c:&amp;nbsp;C2&amp;nbsp;=&amp;nbsp;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;5f154718&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;nbsp;crazy&amp;nbsp;eh&amp;nbsp;:)&amp;nbsp;the&amp;nbsp;variable&amp;nbsp;can&amp;nbsp;be&amp;nbsp;anything&amp;nbsp;but&amp;nbsp;does&amp;nbsp;not&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;nbsp;have&amp;nbsp;type&amp;nbsp;Any&amp;nbsp;so&amp;nbsp;you&amp;nbsp;cannot&amp;nbsp;assign&amp;nbsp;arbitrary&amp;nbsp;values&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&amp;gt;&lt;/span&gt;&amp;nbsp;result&amp;nbsp;=&amp;nbsp;c.get&lt;/li&gt;&lt;li class="codelist "&gt;result:&amp;nbsp;C2#A&amp;nbsp;=&amp;nbsp;hi&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&amp;gt;&lt;/span&gt;&amp;nbsp;result.isInstanceOf&lt;span class="type-param"&gt;[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;res0:&amp;nbsp;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;nbsp;=&amp;nbsp;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;nbsp;while&amp;nbsp;the&amp;nbsp;dynamic&amp;nbsp;type&amp;nbsp;of&amp;nbsp;result&amp;nbsp;is&amp;nbsp;a&amp;nbsp;string&amp;nbsp;the&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;nbsp;static&amp;nbsp;type&amp;nbsp;is&amp;nbsp;not&amp;nbsp;so&amp;nbsp;you&amp;nbsp;cannot&amp;nbsp;assign&amp;nbsp;a&amp;nbsp;string&amp;nbsp;to&amp;nbsp;result&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&amp;gt;&lt;/span&gt;&amp;nbsp;result&amp;nbsp;=&amp;nbsp;&lt;span class="string"&gt;"4"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;nbsp;console&amp;gt;&amp;nbsp;:8:&amp;nbsp;error:&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;mismatch;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;found&amp;nbsp;&amp;nbsp;&amp;nbsp;:&amp;nbsp;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;(&lt;span class="string"&gt;"4"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;required:&amp;nbsp;C2#A&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;result&amp;nbsp;=&amp;nbsp;&lt;span class="string"&gt;"4"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;^&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;The obvious question is what use are abstract types.  I don't claim to know them all but the main point is that they do not expose the internal implementation details to the world.  The famous cake pattern is one such example usage of abstract types.&lt;br /&gt;&lt;br /&gt;I read the following as well (wish I could remember where):&lt;br /&gt;&lt;br /&gt;Abstract types are good when extending and there will be concrete subclasses.  Param type good for when a type is useful without extension but can handle several types.&lt;br /&gt;&lt;br /&gt;A simpler example is examined here.  It is loosely based on a real world usecase.  &lt;br /&gt;The example below is contrived so that it is smaller than the actual usecase, so consider the design and not the fact that the example could be easier done with other examples.  In the real scenario this design reduced the lines of duplicated code from around 500 to 10.&lt;br /&gt;&lt;br /&gt;The example below shows how a Traversable like object can be created from InputStreams and Readers.  The important aspect is that the type signature of Foreach does not leak information about the implementation.  Users of a Foreach object don't care whether it is backed onto an InputStream or Reader.  They just care about the type of object contained.  &lt;br /&gt;&lt;br /&gt;I am leaving this already long post here.  The next post will investigate different ways you can get in trouble trying to implement using abstract types.&lt;br /&gt;&lt;br /&gt;&lt;a name="full_example"&gt;&lt;/a&gt;&lt;br /&gt;&lt;code&gt;&lt;/code&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;nbsp;java.io.{InputStream,&amp;nbsp;Reader,&amp;nbsp;ByteArrayInputStream,&amp;nbsp;StringReader}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;nbsp;java.net.URL&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;nbsp;Foreach&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;fromStream(s:&amp;nbsp;=&amp;gt;&amp;nbsp;InputStream)&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;Foreach&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;I&amp;nbsp;=&amp;nbsp;InputStream&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;source&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;Source&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;in&amp;nbsp;=&amp;nbsp;s&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;next(_in&amp;nbsp;:&amp;nbsp;InputStream)&amp;nbsp;=&amp;nbsp;_in.read&amp;nbsp;&lt;span class="key"&gt;match&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;-1&amp;nbsp;=&amp;gt;&amp;nbsp;None&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;i&amp;nbsp;=&amp;gt;&amp;nbsp;Some(i)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;fromReader(s:&amp;nbsp;=&amp;gt;&amp;nbsp;Reader)&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;Foreach&lt;span class="type-param"&gt;[Char]&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;I&amp;nbsp;=&amp;nbsp;Reader&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;source&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;Source&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;in&amp;nbsp;=&amp;nbsp;s&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;next(_in&amp;nbsp;:&amp;nbsp;Reader)&amp;nbsp;=&amp;nbsp;_in.read&amp;nbsp;&lt;span class="key"&gt;match&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;-1&amp;nbsp;=&amp;gt;&amp;nbsp;None&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;i&amp;nbsp;=&amp;gt;&amp;nbsp;Some(i.toChar)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;fromInputAndFunction&lt;span class="type-param"&gt;[A]&lt;/span&gt;(s:&amp;nbsp;=&amp;gt;&amp;nbsp;InputStream,&amp;nbsp;f:&amp;nbsp;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;nbsp;=&amp;gt;&amp;nbsp;A)&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;Foreach&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;I&amp;nbsp;=&amp;nbsp;InputStream&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;source&amp;nbsp;=&amp;nbsp;&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;Source&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;in&amp;nbsp;=&amp;nbsp;s&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;next(_in&amp;nbsp;:&amp;nbsp;InputStream)&amp;nbsp;=&amp;nbsp;_in.read&amp;nbsp;&lt;span class="key"&gt;match&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;-1&amp;nbsp;=&amp;gt;&amp;nbsp;None&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;i&amp;nbsp;=&amp;gt;&amp;nbsp;Some(f(i))&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;nbsp;Foreach&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;type&lt;/span&gt;&amp;nbsp;I&amp;nbsp;&amp;lt;:&amp;nbsp;java.io.Closeable&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;nbsp;Source&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;in&amp;nbsp;:&amp;nbsp;I&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;next(in&amp;nbsp;:&amp;nbsp;I)&amp;nbsp;:&amp;nbsp;Option&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;source&amp;nbsp;:&amp;nbsp;Source&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f&amp;nbsp;:&amp;nbsp;A&amp;nbsp;=&amp;gt;&amp;nbsp;U)&amp;nbsp;:&amp;nbsp;&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;nbsp;=&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;val&lt;/span&gt;&amp;nbsp;s&amp;nbsp;=&amp;nbsp;source.in&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;try&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;processNext&amp;nbsp;:&amp;nbsp;&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;nbsp;=&amp;nbsp;source.next(s)&amp;nbsp;&lt;span class="key"&gt;match&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;None&amp;nbsp;=&amp;gt;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;()&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;case&lt;/span&gt;&amp;nbsp;Some(value)&amp;nbsp;=&amp;gt;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;f(value)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;processNext&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;processNext&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&amp;nbsp;&lt;span class="key"&gt;finally&lt;/span&gt;&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="comment"&gt;//&amp;nbsp;correctly&amp;nbsp;handle&amp;nbsp;exceptions&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;s.close&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;nbsp;Test&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;def&lt;/span&gt;&amp;nbsp;main(args&amp;nbsp;:&amp;nbsp;Array&lt;span class="type-param"&gt;[String]&lt;/span&gt;)&amp;nbsp;=&amp;nbsp;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;val&lt;/span&gt;&amp;nbsp;data&amp;nbsp;=&amp;nbsp;&lt;span class="string"&gt;"Hello&amp;nbsp;World"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;val&lt;/span&gt;&amp;nbsp;bytes&amp;nbsp;=&amp;nbsp;data.toArray.map&amp;nbsp;{&amp;nbsp;_.toByte&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;span class="key"&gt;import&lt;/span&gt;&amp;nbsp;Foreach._&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fromStream(&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;ByteArrayInputStream(bytes)).foreach&amp;nbsp;{a&amp;nbsp;=&amp;gt;&amp;nbsp;print(a.toChar)}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;println&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fromReader(&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;StringReader(data))&amp;nbsp;foreach&amp;nbsp;print&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;println&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fromInputAndFunction(&lt;span class="key"&gt;new&lt;/span&gt;&amp;nbsp;ByteArrayInputStream(bytes),&amp;nbsp;i&amp;nbsp;=&amp;gt;&amp;nbsp;i.toChar)&amp;nbsp;foreach&amp;nbsp;print&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;println&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;nbsp;&amp;nbsp;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1410821673305630616?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1410821673305630616/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/05/abstract-types-vs-parameter.html#comment-form' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1410821673305630616'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1410821673305630616'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/05/abstract-types-vs-parameter.html' title='Abstract Types vs Parameter'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-5081403443109580065</id><published>2010-04-29T00:44:00.001-07:00</published><updated>2010-04-29T00:44:43.159-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='filter'/><category scheme='http://www.blogger.com/atom/ns#' term='collect'/><category scheme='http://www.blogger.com/atom/ns#' term='flatmap'/><title type='text'>Filter with FlatMap (or collect)</title><content type='html'>I picked up this tip from one of Daniel Spiewak's tweets.  He tweeted a pro tip that uses flatMap to create a filtered list: &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;list&amp;#160;flatMap&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;st:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&gt;&amp;#160;Some(st)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;None&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;At a glance one might wonder why not simply use list.filter{_.isInstanceOf[String]}.  The difference is that the flatMap will return a List[String].&lt;br /&gt;&lt;br /&gt;However Scala 2.8 offers the collect method for doing a similar thing.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;strings(list:&amp;#160;List&lt;span class="type-param"&gt;[Any]&lt;/span&gt;)&amp;#160;=&amp;#160;list&amp;#160;flatMap&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;st:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&gt;&amp;#160;Some(st)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;None&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;returned&amp;#160;list&amp;#160;is&amp;#160;a&amp;#160;List[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;strings(&lt;span class="string"&gt;"hi"&lt;/span&gt;&amp;#160;::&amp;#160;1&amp;#160;::&amp;#160;&lt;span class="string"&gt;"world"&lt;/span&gt;&amp;#160;::&amp;#160;4&amp;#160;::&amp;#160;&lt;span class="singleton"&gt;Nil&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;res11:&amp;#160;List&lt;span class="type-param"&gt;[String]&lt;/span&gt;&amp;#160;=&amp;#160;List(hi,&amp;#160;world)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;returned&amp;#160;list&amp;#160;is&amp;#160;a&amp;#160;List[Any]&amp;#160;(not&amp;#160;as&amp;#160;useful)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="string"&gt;"hi"&lt;/span&gt;&amp;#160;::&amp;#160;1&amp;#160;::&amp;#160;&lt;span class="string"&gt;"world"&lt;/span&gt;&amp;#160;::&amp;#160;4&amp;#160;::&amp;#160;&lt;span class="singleton"&gt;Nil&lt;/span&gt;&amp;#160;filter&amp;#160;{_.isInstanceOf&lt;span class="type-param"&gt;[String]&lt;/span&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;res12:&amp;#160;List&lt;span class="type-param"&gt;[Any]&lt;/span&gt;&amp;#160;=&amp;#160;List(hi,&amp;#160;world)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;collect&amp;#160;returns&amp;#160;List[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="string"&gt;"hi"&lt;/span&gt;&amp;#160;::&amp;#160;1&amp;#160;::&amp;#160;&lt;span class="string"&gt;"world"&lt;/span&gt;&amp;#160;::&amp;#160;4&amp;#160;::&amp;#160;&lt;span class="singleton"&gt;Nil&lt;/span&gt;&amp;#160;collect&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;s:&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&gt;&amp;#160;s}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res13:&amp;#160;List&lt;span class="type-param"&gt;[String]&lt;/span&gt;&amp;#160;=&amp;#160;List(hi,&amp;#160;world)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-5081403443109580065?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/5081403443109580065/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/filter-with-flatmap-or-collect.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5081403443109580065'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5081403443109580065'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/filter-with-flatmap-or-collect.html' title='Filter with FlatMap (or collect)'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1637393118943573005</id><published>2010-04-27T23:38:00.001-07:00</published><updated>2010-04-29T11:44:41.044-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><title type='text'>Implicit Parameter Resolution</title><content type='html'>This topic is a continuation of the previous implicit parameter topics:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;&lt;a href="http://daily-scala.blogspot.com/2010/04/implicit-parameters.html"&gt;Implicit Parameters&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://daily-scala.blogspot.com/2010/04/companion-object-implicits.html"&gt;Companion Object Implicits&lt;/a&gt;&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;This topic provides some explanation about how implicit parameters are resulted.  There are very strict rules for which implicit value is to be applied to a implicit parameter.  A simple way to think about it is that the "closest" definition will be used.  Local scope, enclosing class, parent class, companion object of the desired type.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X(&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Y(&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;X&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;xx&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(1)&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Method&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x(implicit&amp;#160;x:X)=println(x.i)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;y(implicit&amp;#160;y:Y)=println(y.i)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;M&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;Method&amp;#160;=&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x1&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(10)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;y1&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y(100)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;testy&amp;#160;=&amp;#160;y&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;testx&amp;#160;=&amp;#160;x&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;SM&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;M&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;Method&amp;#160;=&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x2&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(20)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;y2&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y(200)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;testy2&amp;#160;=&amp;#160;y&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;resolved&amp;#160;from&amp;#160;companion&amp;#160;object&amp;#160;of&amp;#160;X&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method().x&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;explicit&amp;#160;applied&amp;#160;so&amp;#160;that&amp;#160;value&amp;#160;is&amp;#160;used&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method().x(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(3))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;resolved&amp;#160;from&amp;#160;companion&amp;#160;object&amp;#160;of&amp;#160;X&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;NOT&amp;#160;from&amp;#160;M.&amp;#160;&amp;#160;This&amp;#160;is&amp;#160;because&amp;#160;the&amp;#160;call&amp;#160;site&amp;#160;of&amp;#160;x&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;is&amp;#160;not&amp;#160;within&amp;#160;M&amp;#160;therefore&amp;#160;does&amp;#160;not&amp;#160;use&amp;#160;the&amp;#160;implicits&amp;#160;in&amp;#160;M&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;for&amp;#160;resolution.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;M).x&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(30)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;local&amp;#160;scope&amp;#160;overrides&amp;#160;companion&amp;#160;object&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method().x&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;explicit&amp;#160;applied&amp;#160;so&amp;#160;that&amp;#160;value&amp;#160;is&amp;#160;used&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method().x(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(3))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;local&amp;#160;scope&amp;#160;overrides&amp;#160;companion&amp;#160;object&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;M).x&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;testy&amp;#160;is&amp;#160;defined&amp;#160;within&amp;#160;M&amp;#160;so&amp;#160;the&amp;#160;implicits&amp;#160;within&amp;#160;M&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;M).testy&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;testx&amp;#160;is&amp;#160;defined&amp;#160;within&amp;#160;M&amp;#160;so&amp;#160;the&amp;#160;implicit&amp;#160;within&amp;#160;M&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;overrides&amp;#160;the&amp;#160;companion&amp;#160;object&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;M).testx&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;testy&amp;#160;is&amp;#160;within&amp;#160;M&amp;#160;(not&amp;#160;SM)&amp;#160;so&amp;#160;the&amp;#160;implicit&amp;#160;within&amp;#160;M&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;is&amp;#160;used&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;SM).testy&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;testy2&amp;#160;is&amp;#160;within&amp;#160;SM&amp;#160;so&amp;#160;the&amp;#160;implicit&amp;#160;within&amp;#160;SM&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;overrides&amp;#160;the&amp;#160;implicit&amp;#160;in&amp;#160;M&amp;#160;and&amp;#160;the&amp;#160;companion&amp;#160;object&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Method&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;SM).testy2&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Output:&lt;br /&gt;&lt;bq&gt;&lt;br /&gt;1&lt;br /&gt;3&lt;br /&gt;1&lt;br /&gt;30&lt;br /&gt;3&lt;br /&gt;30&lt;br /&gt;100&lt;br /&gt;10&lt;br /&gt;100&lt;br /&gt;200&lt;br /&gt;&lt;bq&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1637393118943573005?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1637393118943573005/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/implicit-parameter-resolution.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1637393118943573005'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1637393118943573005'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/implicit-parameter-resolution.html' title='Implicit Parameter Resolution'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1598423674401089187</id><published>2010-04-26T00:08:00.000-07:00</published><updated>2010-04-27T06:48:20.521-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><title type='text'>Implicit Parameters</title><content type='html'>Evidently the topic of implicit parameters has not yet been correctly addressed.  There have been several topic that refer to implicit parameters but none that directly discuss them.  So before I continue with the topic of implicit parameter resolution I will discuss implicit parameters.&lt;br /&gt;&lt;br /&gt;First, implicit parameters are not the same as implicit object conversions.  Implicit parameters provide a way to allow parameters of a method to be "found".  This is similar to default parameters at a glance but in fact is a different mechanism for finding the "default" value.  It differs from implicit object conversion in that it is only a way for parameters for a method to be resolved.  Implicit object conversion allows methods to appear to be called on one object when in fact that object is being converted behind the scenes to another type.  (more or less)&lt;br /&gt;&lt;br /&gt;An implicit parameter is a parameter to method or constructor that is marked as implicit.  This means that if a parameter value is not supplied then the compiler will search for an "implicit" value defined within scope (according to resolution rules.)  Implicit parameter resolution rules will be discussed soon.&lt;br /&gt;&lt;br /&gt;Example:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;p(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;print(i)&lt;/li&gt;&lt;li class="codelist "&gt;p:&amp;#160;(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;defining&amp;#160;a&amp;#160;val/var/def&amp;#160;as&amp;#160;implicit&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;means&amp;#160;that&amp;#160;it&amp;#160;will&amp;#160;be&amp;#160;considered&amp;#160;during&amp;#160;implicit&amp;#160;resolution&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;v=2&lt;/li&gt;&lt;li class="codelist alt"&gt;v:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;scope&amp;#160;is&amp;#160;searched&amp;#160;for&amp;#160;a&amp;#160;implicit&amp;#160;value&amp;#160;to&amp;#160;sue&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;v&amp;#160;is&amp;#160;found&amp;#160;as&amp;#160;marked&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;p&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;2&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;explicit&amp;#160;declarations&amp;#160;always&amp;#160;overrides&amp;#160;implicit&amp;#160;values&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;p(1)&lt;/li&gt;&lt;li class="codelist "&gt;1&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Implicit parameters are very nice for simplifying APIs.  For example the collections use implicit parameters to supply CanBuildFrom objects for many of the collection methods.  This is because normally the user does not need to be concerned with those parameters.  Another example is supplying an encoding to an IO library so the encoding is defined once (perhaps in a package object) and all methods can use the same encoding without having to define it for every method call.&lt;br /&gt;&lt;br /&gt;One important restriction is that there can only be a single implicit keyword per method.  It must be at the start of a parameter list (which also makes all values of that parameter list be implicit).  I further understand that only the last parameter list may be implicit.&lt;br /&gt;&lt;br /&gt;Here are several illegal examples:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;is&amp;#160;not&amp;#160;in&amp;#160;last&amp;#160;parameter&amp;#160;list&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;a:&lt;span class="basicType"&gt;Int&lt;/span&gt;)(b:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(a,i)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:1:&amp;#160;error:&amp;#160;&lt;span class="char"&gt;'='&lt;/span&gt;&amp;#160;expected&amp;#160;but&amp;#160;&lt;span class="char"&gt;'('&lt;/span&gt;&amp;#160;found.&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;a:&lt;span class="basicType"&gt;Int&lt;/span&gt;)(b:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(a,i)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;there&amp;#160;are&amp;#160;2&amp;#160;implicit&amp;#160;parameters&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(implicit&amp;#160;j:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;a:&lt;span class="basicType"&gt;Int&lt;/span&gt;)(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,b:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(a,i)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:1:&amp;#160;error:&amp;#160;&lt;span class="char"&gt;'='&lt;/span&gt;&amp;#160;expected&amp;#160;but&amp;#160;&lt;span class="char"&gt;'('&lt;/span&gt;&amp;#160;found.&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(implicit&amp;#160;j:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;a:&lt;span class="basicType"&gt;Int&lt;/span&gt;)(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,b:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(a,i)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;is&amp;#160;not&amp;#160;the&amp;#160;first&amp;#160;parameter&amp;#160;of&amp;#160;the&amp;#160;parameter&amp;#160;list&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(a:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(i,j)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:1:&amp;#160;error:&amp;#160;identifier&amp;#160;expected&amp;#160;but&amp;#160;&lt;span class="char"&gt;'implicit'&lt;/span&gt;&amp;#160;found.&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(a:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(i,j)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Here are several legal examples (Updated with useage examples):&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;v&amp;#160;=&amp;#160;7&lt;/li&gt;&lt;li class="codelist "&gt;v:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;10L&lt;/li&gt;&lt;li class="codelist alt"&gt;x:&amp;#160;&lt;span class="basicType"&gt;Long&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;i&amp;#160;is&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(a:&lt;span class="basicType"&gt;Int&lt;/span&gt;)(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(a,i)&lt;/li&gt;&lt;li class="codelist alt"&gt;pp:&amp;#160;(a:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pp(3)&lt;/li&gt;&lt;li class="codelist "&gt;(3,7)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;both&amp;#160;i&amp;#160;and&amp;#160;b&amp;#160;are&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(a:&lt;span class="basicType"&gt;Int&lt;/span&gt;)(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;b:&lt;span class="basicType"&gt;Long&lt;/span&gt;)&amp;#160;=&amp;#160;println(a,i,b)&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;pp:&amp;#160;(a:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;,implicit&amp;#160;b:&amp;#160;&lt;span class="basicType"&gt;Long&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pp(4)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;(4,7,10)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;both&amp;#160;i&amp;#160;and&amp;#160;b&amp;#160;are&amp;#160;implicit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;b:&lt;span class="basicType"&gt;Long&lt;/span&gt;)&amp;#160;=&amp;#160;println(i,b)&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;pp:&amp;#160;(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;,implicit&amp;#160;b:&amp;#160;&lt;span class="basicType"&gt;Long&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pp&lt;/li&gt;&lt;li class="codelist "&gt;(7,10)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;all&amp;#160;or&amp;#160;none&amp;#160;of&amp;#160;the&amp;#160;parameters&amp;#160;must&amp;#160;be&amp;#160;supplied&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pp(2)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:13:&amp;#160;error:&amp;#160;not&amp;#160;enough&amp;#160;arguments&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;method&amp;#160;pp:&amp;#160;(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;,implicit&amp;#160;b:&amp;#160;&lt;span class="basicType"&gt;Long&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;.&lt;/li&gt;&lt;li class="codelist alt"&gt;Unspecified&amp;#160;value&amp;#160;parameter&amp;#160;b.&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;pp(2)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;This&amp;#160;is&amp;#160;syntactically&amp;#160;legal&amp;#160;but&amp;#160;I&amp;#160;cannot&amp;#160;seem&amp;#160;to&amp;#160;implicitly&amp;#160;invoke&amp;#160;this&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;I&amp;#160;would&amp;#160;recommend:&amp;#160;def&amp;#160;pp(b:Long*)(implicit&amp;#160;i:Int)&amp;#160;=&amp;#160;println(i,b)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;b:Long*)&amp;#160;=&amp;#160;println(i,b)&lt;/li&gt;&lt;li class="codelist alt"&gt;pp:&amp;#160;(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;,implicit&amp;#160;b:&amp;#160;Long*)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pp(3,1,2,3)&lt;/li&gt;&lt;li class="codelist "&gt;(3,WrappedArray(1,&amp;#160;2,&amp;#160;3))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pp(b:Long*)(implicit&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;println(i,b)&lt;/li&gt;&lt;li class="codelist alt"&gt;pp:&amp;#160;(b:&amp;#160;Long*)(implicit&amp;#160;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pp(1,2,3)&lt;/li&gt;&lt;li class="codelist "&gt;(7,WrappedArray(1,&amp;#160;2,&amp;#160;3))&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;A related topic is &lt;a href="http://daily-scala.blogspot.com/2010/04/companion-object-implicits.html"&gt;Companion Object implicits&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1598423674401089187?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1598423674401089187/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/implicit-parameters.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1598423674401089187'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1598423674401089187'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/implicit-parameters.html' title='Implicit Parameters'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-8312961293428568620</id><published>2010-04-23T00:32:00.000-07:00</published><updated>2010-04-23T00:35:15.339-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='break'/><title type='text'>Break Performance</title><content type='html'>In the &lt;a href="http://daily-scala.blogspot.com/2010/04/breaks.html"&gt;Breaks&lt;/a&gt; comments there were several questions about the performance of the Scala break command vs the Java break command.  So I decided to take a look. &lt;br /&gt;&lt;br /&gt;The code for the tests is available on GitHub at: &lt;a href="http://github.com/jesseeichar/Scala-Benchmarks"&gt;Scala Benchmarks&lt;/a&gt;.  Feel free to play around with it.&lt;br /&gt;&lt;br /&gt;I personally don't think these tests say anything of particular import because they only test how fast the Java break is vs the Scala break without doing any work in the loop.  So I don't expect these number would ever been seen in the real world.  However that said if you have a tight loop with minimal processing then a Scala break may not be the correct construct to use.  &lt;br /&gt;&lt;br /&gt;Here is the Java test (labelled JavaSimpleBreak)&lt;br /&gt;&lt;code class="Java"&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="basicType"&gt;int&lt;/span&gt;&amp;#160;i&amp;#160;=&amp;#160;0;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;while&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;&amp;#160;10)&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(i==1)&amp;#160;break;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;i&amp;#160;+=&amp;#160;1;&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Here is the Scala test (labelled ScalaSimpleBreak)&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;i&amp;#160;=&amp;#160;0;&lt;/li&gt;&lt;li class="codelist "&gt;breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;while&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;&amp;#160;10)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(i==1)&amp;#160;break;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;i&amp;#160;+=&amp;#160;1;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Out of curiosity I also added a test that created a new Exception each iteration (labelled ScalaException):&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;i&amp;#160;=&amp;#160;0;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;while&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;&amp;#160;10)&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(i==1)&amp;#160;&lt;span class="key"&gt;throw&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Exception();&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;i&amp;#160;+=&amp;#160;1;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;And also a test that just throws the same ScalaBreak exception each time.  This one is weird since Scala Simple Break also throws the same exception but is much much faster so I think there is something about popping the stack in the example compared to the ScalaSimpleBreak test.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;i&amp;#160;=&amp;#160;0;&lt;/li&gt;&lt;li class="codelist "&gt;breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt; &lt;span class="key"&gt;while&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;&amp;#160;10)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;  &lt;span class="key"&gt;if&lt;/span&gt;(i==1)&amp;#160;break;&lt;/li&gt;&lt;li class="codelist alt"&gt;  i&amp;#160;+=&amp;#160;1;&lt;/li&gt;&lt;li class="codelist "&gt; }&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;The results of the tests:&lt;br /&gt;&lt;br /&gt;First, don't compare the break tests to the Exception tests.  They are sufficiently different to not be worth comparing.&lt;br /&gt;Second, remember that this is a micro benchmark and has very little relationship to reality.&lt;br /&gt;&lt;bq&gt;&lt;br /&gt;90000000 iterations.  Swapping every 90000000 tests&lt;br /&gt;JavaSimpleBreak = 254 (0.0016279129387033098)&lt;br /&gt;ScalaSimpleBreak = 2475 (0.015862537493270438)&lt;br /&gt;ScalaBreakException = 18806 (0.12052964852462379)&lt;br /&gt;ScalaException = 156028 (1.0)&lt;br /&gt;&lt;br /&gt;90000000 iterations.  Swapping every 500000 tests&lt;br /&gt;JavaSimpleBreak = 772 (0.005138547761203965)&lt;br /&gt;ScalaSimpleBreak = 2351 (0.015648608531853004)&lt;br /&gt;ScalaBreakException = 19346 (0.12876987692778744)&lt;br /&gt;ScalaException = 150237 (1.0)&lt;br /&gt;&lt;br /&gt;90000000 iterations.  Swapping every 500 tests&lt;br /&gt;JavaSimpleBreak = 790 (0.005242446563543097)&lt;br /&gt;ScalaSimpleBreak = 2247 (0.014911110668710557)&lt;br /&gt;ScalaBreakException = 19213 (0.1274976276270298)&lt;br /&gt;ScalaException = 150693 (1.0)&lt;br /&gt;&lt;/bq&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-8312961293428568620?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/8312961293428568620/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/break-performance.html#comment-form' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8312961293428568620'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8312961293428568620'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/break-performance.html' title='Break Performance'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1037858680265945043</id><published>2010-04-21T23:46:00.000-07:00</published><updated>2010-04-21T23:49:15.796-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='Advanced'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><category scheme='http://www.blogger.com/atom/ns#' term='companion'/><title type='text'>Companion Object Implicits</title><content type='html'>When a method requires an implicit there are several ways that the implicit is resolved.  One way is to search for an implicit definition in the &lt;em&gt;companion object&lt;/em&gt; of the &lt;em&gt;required&lt;/em&gt; type.  For example:  &lt;code&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x(implicit&amp;#160;m:MyClass)&lt;/code&gt; parameter m will search local scope, class hierarchy and the MyClass companion object for an implicit val or def.  (More on implicit resolution later).&lt;br /&gt; &lt;br /&gt;To demonstrate the method put the following code block into a file and run the script:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X(&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;add(implicit&amp;#160;x:X)=println(x.i+i)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;X&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;xx&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(3)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;is&amp;#160;obtained&amp;#160;from&amp;#160;companion&amp;#160;object&amp;#160;of&amp;#160;X&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(3).add&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;other&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;print(implicit&amp;#160;x:X)=println(x.i)&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;is&amp;#160;obtained&amp;#160;from&amp;#160;companion&amp;#160;object&amp;#160;of&amp;#160;X&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;other.print&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X(32)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;is&amp;#160;obtained&amp;#160;local&amp;#160;scope&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;other.print&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Running: scala impl.scala should produce:&lt;br /&gt;6&lt;br /&gt;3&lt;br /&gt;32&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1037858680265945043?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1037858680265945043/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/companion-object-implicits.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1037858680265945043'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1037858680265945043'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/companion-object-implicits.html' title='Companion Object Implicits'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-4672127917535919875</id><published>2010-04-20T23:30:00.001-07:00</published><updated>2010-04-20T23:30:36.564-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='break'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='control structure'/><category scheme='http://www.blogger.com/atom/ns#' term='2.8'/><title type='text'>Breaks</title><content type='html'>Scala 2.8 added the &lt;em&gt;break&lt;/em&gt; control flow option.  It is not implemented as a special language feature.  Rather it is simply implemented as an object/trait using standard Scala mechanisms.  If you are interested in creating a control flow object similar to this look at the &lt;a href="http://daily-scala.blogspot.com/2009/11/defining-custom-control-structures.html"&gt;Defining Custom Control Structures&lt;/a&gt; post.&lt;br /&gt; &lt;br /&gt;The Break functionality is works basically how you would expect:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;Import&amp;#160;the&amp;#160;control&amp;#160;flow&amp;#160;methodsmethods&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;util.control.Breaks._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;util.control.Breaks._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;pass&amp;#160;a&amp;#160;function&amp;#160;to&amp;#160;the&amp;#160;breakable&amp;#160;method&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;-&amp;#160;1&amp;#160;to&amp;#160;10&amp;#160;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(i&amp;#160;&gt;&amp;#160;5)&amp;#160;break&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;call&amp;#160;break&amp;#160;when&amp;#160;done&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;println(i)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;1&lt;/li&gt;&lt;li class="codelist alt"&gt;2&lt;/li&gt;&lt;li class="codelist "&gt;3&lt;/li&gt;&lt;li class="codelist alt"&gt;4&lt;/li&gt;&lt;li class="codelist "&gt;5&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Pretty intuitive but beware, break only breaks out to the first enclosing breakable.  Here is an example of the issue:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;loop(f&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;)&amp;#160;=&amp;#160;breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;-&amp;#160;1&amp;#160;to&amp;#160;300)&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;(f(i))&amp;#160;break&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;println(i)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;loop:&amp;#160;(f:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;This&amp;#160;never&amp;#160;ends&amp;#160;because&amp;#160;break&amp;#160;is&amp;#160;caught&amp;#160;by&amp;#160;breakable&amp;#160;in&amp;#160;the&amp;#160;loop&amp;#160;method&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;while&lt;/span&gt;(&lt;span class="basicType"&gt;true&lt;/span&gt;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;loop{&amp;#160;i&amp;#160;=&gt;&amp;#160;break;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Fortunately the implementers provide an elegant way to handle these sorts of cases.  The Breaks object extends the Breaks class.  By instantiating other instances of Breaks it is possible to control which breaks capture&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.util.control._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.util.control._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;loop(f&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;)&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;Inner&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Breaks&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;Inner.breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;(i&amp;#160;&amp;lt;-&amp;#160;1&amp;#160;to&amp;#160;4)&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;(f(i))&amp;#160;Inner.break&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;println(i)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;loop:&amp;#160;(f:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;Outer&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Breaks&lt;/li&gt;&lt;li class="codelist alt"&gt;Outer:&amp;#160;scala.util.control.Breaks&amp;#160;=&amp;#160;scala.util.control.Breaks&lt;span class="annotation"&gt;@&lt;/span&gt;1ba4806&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;Outer.breakable&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;while&lt;/span&gt;(&lt;span class="basicType"&gt;true&lt;/span&gt;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;loop{&amp;#160;i&amp;#160;=&gt;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(i==4)&amp;#160;Outer.break;&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;1&lt;/li&gt;&lt;li class="codelist alt"&gt;2&lt;/li&gt;&lt;li class="codelist "&gt;3&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-4672127917535919875?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/4672127917535919875/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/breaks.html#comment-form' title='9 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4672127917535919875'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4672127917535919875'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/breaks.html' title='Breaks'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>9</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-2247063578620063806</id><published>2010-04-19T04:23:00.000-07:00</published><updated>2010-04-19T04:24:37.070-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='array'/><category scheme='http://www.blogger.com/atom/ns#' term='traversable'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><title type='text'>Scala 2.8 Arrays are not Traversables</title><content type='html'>One performance/consistency change that has been make in Scala 2.8 is to make Scala Array always be a Java Array.  This has some consequences which we will examine in this post.  The biggest one is that Array &lt;em&gt;is not&lt;/em&gt; a Scala Collection/Traversable.  It is implicitly converted to one but it is not an instance of a Traversable.  There are several reasons this was done.  Probably the biggest is for performance.  Because a Scala array &lt;em&gt;is&lt;/em&gt; a Java array there is no overhead when using a Scala array.  &lt;br /&gt; &lt;br /&gt;Thanks to implicit type conversion all the normal collection methods are useable with an array.  Even better, after running a method like map the result will again be a Java array.  So the API is much more consistent.&lt;br /&gt; &lt;br /&gt;An example illustrating that an Array is not a Traversable:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;This&amp;#160;does&amp;#160;not&amp;#160;compile&amp;#160;(which&amp;#160;is&amp;#160;good)&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;because&amp;#160;Traversable[Int]&amp;#160;can&amp;#160;never&amp;#160;be&amp;#160;an&amp;#160;array&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x(t:Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;#160;=&amp;#160;t&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Array&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:13:&amp;#160;error:&amp;#160;pattern&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;is&amp;#160;incompatible&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;expected&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;Array&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;required:&amp;#160;Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Array&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:13:&amp;#160;error:&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;mismatch;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;Array&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;required:&amp;#160;Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Array&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Another example:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x(t:Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;#160;=&amp;#160;t.isInstanceOf&lt;span class="type-param"&gt;[Array&lt;/span&gt;&lt;span class="type-param"&gt;[_]&lt;/span&gt;]&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;(t:&amp;#160;Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&amp;#160;this&amp;#160;evaluates&amp;#160;to&amp;#160;false&amp;#160;because&amp;#160;Array&amp;#160;is&amp;#160;converted&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;*&amp;#160;to&amp;#160;WrappedArray&amp;#160;because&amp;#160;it&amp;#160;has&amp;#160;to&amp;#160;be&amp;#160;implicitly&amp;#160;converted&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&amp;#160;*&amp;#160;to&amp;#160;a&amp;#160;Traversable.&amp;#160;&amp;#160;Since&amp;#160;Array&amp;#160;is&amp;#160;not&amp;#160;a&amp;#160;Traversable&amp;#160;the&amp;#160;resulting&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;*&amp;#160;object&amp;#160;is&amp;#160;not&amp;#160;an&amp;#160;Array&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&amp;#160;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;x(Array(1,2,3))&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res24:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x(t:Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;#160;=&amp;#160;println(t)&lt;/li&gt;&lt;li class="codelist alt"&gt;x:&amp;#160;(t:&amp;#160;Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;This&amp;#160;method&amp;#160;call&amp;#160;demonstrates&amp;#160;the&amp;#160;previous&amp;#160;assertion&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;x(Array(1,2,3))&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;WrappedArray(1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;So suppose you want to be able to accept and use arrays and Traversables in a method but you want to be able to &lt;br /&gt;check that the parameter is an Array.  Why not match against WrappedArray.  You probably can, but you may get performance improvements in some cases if you don't require wrapping the array.  &lt;br /&gt; &lt;br /&gt;For a more concrete example of why you may want to do this.  In a Input/Output routine I wrote I would write the data one way if the input was an Array: &lt;code&gt;stream.write(array)&lt;/code&gt;.  But if the input was a traversable then I would have to handle it differently.  My particular issue was more complicated than that but that is the basic issue.&lt;br /&gt; &lt;br /&gt;So the work around is to define a Generic parameter for the method:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x&lt;span class="type-param"&gt;[T&amp;#160;&amp;lt;%&amp;#160;Traversable&lt;/span&gt;&lt;span class="type-param"&gt;[Int]&lt;/span&gt;](t:T)&amp;#160;=&amp;#160;t&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Array&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;&lt;span class="type-param"&gt;[T]&lt;/span&gt;(t:&amp;#160;T)(implicit&amp;#160;evidence$1:&amp;#160;(T)&amp;#160;=&gt;&amp;#160;Traversable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;x(Array(1,2,3))&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res27:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-2247063578620063806?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/2247063578620063806/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/scala-28-arrays-are-not-traversables.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/2247063578620063806'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/2247063578620063806'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/scala-28-arrays-are-not-traversables.html' title='Scala 2.8 Arrays are not Traversables'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-4768877119892308699</id><published>2010-04-16T01:56:00.000-07:00</published><updated>2010-04-16T01:58:06.724-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='iterable'/><category scheme='http://www.blogger.com/atom/ns#' term='option'/><category scheme='http://www.blogger.com/atom/ns#' term='list'/><category scheme='http://www.blogger.com/atom/ns#' term='beginner'/><title type='text'></title><content type='html'>A quick note.  ScalaDays Rocks!  Wish you were here :)&lt;br /&gt;&lt;br /&gt;This topic just demonstrates a cute little trick that can occasionally be quite useful:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(1,2,3)&amp;#160;++&amp;#160;Some(4)&lt;/li&gt;&lt;li class="codelist "&gt;res0:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(1,&amp;#160;2,&amp;#160;3,&amp;#160;4)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(1,2,3)&amp;#160;++&amp;#160;None&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res1:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Options are implicitly converted to Iterables, so Options can be appended to collections.  &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Iterable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;None&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;Iterable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List()&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Iterable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;Some(4)&lt;/li&gt;&lt;li class="codelist alt"&gt;x:&amp;#160;Iterable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(4)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-4768877119892308699?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/4768877119892308699/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/quick-note.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4768877119892308699'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4768877119892308699'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/quick-note.html' title=''/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-7052214202323527890</id><published>2010-04-13T01:57:00.000-07:00</published><updated>2010-04-29T00:38:12.378-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='GenericTraversableTemplate'/><category scheme='http://www.blogger.com/atom/ns#' term='collections'/><category scheme='http://www.blogger.com/atom/ns#' term='traversable'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='GenericCanBuildFrom'/><category scheme='http://www.blogger.com/atom/ns#' term='traits'/><title type='text'>Creating Custom Traversable implementations</title><content type='html'>One of the most talked about features of Scala 2.8 is the improved Collections libraries.  Creating your own implementation is trivial, however if you want your new collection to behave the same way as all the included libraries there are a few tips you need to be aware of.&lt;br /&gt;&lt;br /&gt;Note: All of these examples can either be ran in the REPL or put in a file and ran&lt;br /&gt;&lt;br /&gt;Starting with the simple implementation:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection.generic._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyColl&lt;span class="type-param"&gt;[A]&lt;/span&gt;(seq&amp;#160;:&amp;#160;A*)&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Traversable&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;only&amp;#160;abstract&amp;#160;method&amp;#160;in&amp;#160;traversable&amp;#160;is&amp;#160;foreach...&amp;#160;easy&amp;#160;:)&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f:&amp;#160;A&amp;#160;=&gt;&amp;#160;U)&amp;#160;=&amp;#160;util.Random.shuffle(seq.toSeq).foreach(f)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;This is a silly collection I admit but it is custom :).  &lt;br /&gt;&lt;br /&gt;This example works but if you test the result of a map operation (or any other operation that returns a new instance of the collection) you will notice it is not an instance of MyColl.  This is expected because unless otherwise defined Traversable will return a new instance of Traversable.  &lt;br /&gt;&lt;br /&gt;To demonstrate run the following tests:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;c&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyColl(1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;li class="codelist "&gt;println&amp;#160;(c&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;println(c&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;println(c&amp;#160;drop&amp;#160;1&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;this&amp;#160;two&amp;#160;next&amp;#160;assertions&amp;#160;fail&amp;#160;(see&amp;#160;following&amp;#160;explanation)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;assert(c.drop(1).isInstanceOf&lt;span class="type-param"&gt;[MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[_]&lt;/span&gt;])&lt;/li&gt;&lt;li class="codelist alt"&gt;assert((c&amp;#160;map&amp;#160;{_&amp;#160;+&amp;#160;1}).isInstanceOf&lt;span class="type-param"&gt;[MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[_]&lt;/span&gt;])&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Both assertions will fail.  The reason for these failures is because the collection is immutable which dictates by necessity that a new object must be returned from filter/map/etc... Since the Traversable trait returns instances of Traversable these two assertions fail.  The easiest way to make these methods return an instance of MyColl is to make the following changes/additions.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection.generic._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Adding&amp;#160;GenericTraversableTemplate&amp;#160;will&amp;#160;delegate&amp;#160;the&amp;#160;creation&amp;#160;of&amp;#160;new&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;collections&amp;#160;to&amp;#160;the&amp;#160;companion&amp;#160;object.&amp;#160;&amp;#160;Adding&amp;#160;the&amp;#160;trait&amp;#160;and&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;companion&amp;#160;object&amp;#160;causes&amp;#160;all&amp;#160;the&amp;#160;new&amp;#160;collections&amp;#160;to&amp;#160;be&amp;#160;instances&amp;#160;of&amp;#160;MyColl&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyColl&lt;span class="type-param"&gt;[A]&lt;/span&gt;(seq&amp;#160;:&amp;#160;A*)&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Traversable&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;GenericTraversableTemplate&lt;span class="type-param"&gt;[A,&amp;#160;MyColl]&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;override&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;companion&amp;#160;=&amp;#160;MyColl&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f:&amp;#160;A&amp;#160;=&gt;&amp;#160;U)&amp;#160;=&amp;#160;util.Random.shuffle(seq.toSeq).foreach(f)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;The&amp;#160;TraversableFactory&amp;#160;trait&amp;#160;is&amp;#160;required&amp;#160;by&amp;#160;GenericTraversableTemplate&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;MyColl&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;TraversableFactory&lt;span class="type-param"&gt;[MyColl]&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;If&amp;#160;you&amp;#160;look&amp;#160;at&amp;#160;the&amp;#160;signatures&amp;#160;of&amp;#160;many&amp;#160;methods&amp;#160;in&amp;#160;TraversableLike&amp;#160;they&amp;#160;have&amp;#160;an&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;implicit&amp;#160;parameter&amp;#160;canBuildFrom.&amp;#160;&amp;#160;This&amp;#160;allows&amp;#160;one&amp;#160;to&amp;#160;define&amp;#160;how&amp;#160;the&amp;#160;returned&amp;#160;collections&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;are&amp;#160;built.&amp;#160;&amp;#160;For&amp;#160;example&amp;#160;one&amp;#160;could&amp;#160;make&amp;#160;a&amp;#160;list's&amp;#160;map&amp;#160;method&amp;#160;return&amp;#160;a&amp;#160;Set&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;In&amp;#160;this&amp;#160;case&amp;#160;we&amp;#160;define&amp;#160;the&amp;#160;default&amp;#160;canBuildFrom&amp;#160;for&amp;#160;MyColl&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;canBuildFrom&lt;span class="type-param"&gt;[A]&lt;/span&gt;:&amp;#160;CanBuildFrom&lt;span class="type-param"&gt;[Coll,&amp;#160;A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;GenericCanBuildFrom&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;The&amp;#160;method&amp;#160;that&amp;#160;builds&amp;#160;the&amp;#160;new&amp;#160;collection.&amp;#160;&amp;#160;This&amp;#160;is&amp;#160;a&amp;#160;simple&amp;#160;implementation&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;but&amp;#160;it&amp;#160;works.&amp;#160;&amp;#160;There&amp;#160;are&amp;#160;other&amp;#160;implementations&amp;#160;to&amp;#160;assist&amp;#160;with&amp;#160;implementation&amp;#160;if&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;needed&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;newBuilder&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;scala.collection.mutable.LazyBuilder&lt;span class="type-param"&gt;[A,MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;result&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;data&amp;#160;=&amp;#160;parts.foldLeft(List&lt;span class="type-param"&gt;[A]&lt;/span&gt;()){(l,n)&amp;#160;=&gt;&amp;#160;l&amp;#160;++&amp;#160;n}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyColl(data:_*)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Now instances of MyColl will be created by the various filter/map/etc... methods and that is fine as long as the new object is not required at compile-time.  But suppose we added a method to the class and want that accessible after applying methods like map and filter.&lt;br /&gt;&lt;br /&gt;Adding &lt;code&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;o&amp;#160;:&amp;#160;MyColl&lt;span class="type-param"&gt;[Long]&lt;/span&gt;&amp;#160;=&amp;#160;c&amp;#160;map&amp;#160;{_.toLong}&lt;/code&gt; to the assertions will cause a compilation error since statically the class returned is Traversable[Long].  The fix is easy.&lt;br /&gt;&lt;br /&gt;All that needs to be done is to add &lt;code&gt;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;TraversableLike&lt;span class="type-param"&gt;[A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&lt;/code&gt; to MyColl and we are golden.  There may be other methods as well but this works and is simple.&lt;br /&gt;&lt;br /&gt;Note that the order in which the traits are mixed in is important.  &lt;code&gt;TraversableLike&lt;span class="type-param"&gt;[A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&lt;/code&gt; must be mixed in &lt;em&gt;after&lt;/em&gt; &lt;code&gt;Traversable&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/code&gt;.  The reason is that we want methods like map and drop to return instances of MyColl (statically as well as dynamically).  If the order was reversed then those methods would return Traversable event though statically the actual instances would still be MyColl.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection.generic._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyColl&lt;span class="type-param"&gt;[A]&lt;/span&gt;(seq&amp;#160;:&amp;#160;A*)&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Traversable&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;GenericTraversableTemplate&lt;span class="type-param"&gt;[A,&amp;#160;MyColl]&lt;/span&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;TraversableLike&lt;span class="type-param"&gt;[A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;override&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;companion&amp;#160;=&amp;#160;MyColl&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f:&amp;#160;A&amp;#160;=&gt;&amp;#160;U)&amp;#160;=&amp;#160;util.Random.shuffle(seq.toSeq).foreach(f)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;MyColl&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;TraversableFactory&lt;span class="type-param"&gt;[MyColl]&lt;/span&gt;&amp;#160;{&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;canBuildFrom&lt;span class="type-param"&gt;[A]&lt;/span&gt;:&amp;#160;CanBuildFrom&lt;span class="type-param"&gt;[Coll,&amp;#160;A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;GenericCanBuildFrom&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;newBuilder&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;scala.collection.mutable.LazyBuilder&lt;span class="type-param"&gt;[A,MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;result&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;data&amp;#160;=&amp;#160;parts.foldLeft(List&lt;span class="type-param"&gt;[A]&lt;/span&gt;()){(l,n)&amp;#160;=&gt;&amp;#160;l&amp;#160;++&amp;#160;n}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyColl(data:_*)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Now add in a new method to demonstrate that the new collection works as desired and we are done.&lt;br /&gt;&lt;br /&gt;The following is the complete implementation with the tests.  You can put it in a file and run scala &amp;lt;filename&gt; or paste it into a REPL&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection.generic._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.collection.mutable.{&amp;#160;Builder,&amp;#160;ListBuffer&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyColl&lt;span class="type-param"&gt;[A]&lt;/span&gt;(seq&amp;#160;:&amp;#160;A*)&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Traversable&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;GenericTraversableTemplate&lt;span class="type-param"&gt;[A,&amp;#160;MyColl]&lt;/span&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;TraversableLike&lt;span class="type-param"&gt;[A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;override&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;companion&amp;#160;=&amp;#160;MyColl&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach&lt;span class="type-param"&gt;[U]&lt;/span&gt;(f:&amp;#160;A&amp;#160;=&gt;&amp;#160;U)&amp;#160;=&amp;#160;util.Random.shuffle(seq.toSeq).foreach(f)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;sayhi&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"hi!"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;MyColl&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;TraversableFactory&lt;span class="type-param"&gt;[MyColl]&lt;/span&gt;&amp;#160;{&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;canBuildFrom&lt;span class="type-param"&gt;[A]&lt;/span&gt;:&amp;#160;CanBuildFrom&lt;span class="type-param"&gt;[Coll,&amp;#160;A,&amp;#160;MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;]&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;GenericCanBuildFrom&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;newBuilder&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;ListBuffer&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;mapResult&amp;#160;(x&amp;#160;=&gt;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyColl(x:_*))&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;c&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyColl(1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;li class="codelist "&gt;println&amp;#160;(c&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;println(c&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;assert(c.drop(1).isInstanceOf&lt;span class="type-param"&gt;[MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[_]&lt;/span&gt;])&lt;/li&gt;&lt;li class="codelist "&gt;assert((c&amp;#160;map&amp;#160;{_&amp;#160;+&amp;#160;1}).isInstanceOf&lt;span class="type-param"&gt;[MyColl&lt;/span&gt;&lt;span class="type-param"&gt;[_]&lt;/span&gt;])&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;o&amp;#160;:&amp;#160;MyColl&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;c&amp;#160;filter&amp;#160;{_&amp;#160;&amp;lt;&amp;#160;2}&lt;/li&gt;&lt;li class="codelist alt"&gt;println(o&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;&amp;#160;)&lt;/li&gt;&lt;li class="codelist "&gt;o.sayhi&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-7052214202323527890?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/7052214202323527890/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/creating-custom-traversable.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7052214202323527890'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7052214202323527890'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/creating-custom-traversable.html' title='Creating Custom Traversable implementations'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-6211043443458526034</id><published>2010-04-09T00:59:00.000-07:00</published><updated>2010-04-09T01:12:04.581-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='elidable'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><title type='text'>Elidable (remove method calls at compile time)</title><content type='html'>In Scala 2.8 there is a useful annotation called 'elidable'.  This annotation flags a method so that given certain compiler flags all calls to the method will be removed.  This is handy if you are writing a logger.  The log methods can be annotated so that when compiling for production all log calls below a certain level would be removed from the compiled code.  Several of the methods in Predef are annotated with elidable.  Specifically, assume, assert and require.  &lt;br /&gt; &lt;br /&gt;The elidable annotation takes an Int parameter which specifies the priority of the method.  The lower the integer the more likely the method would be removed during compilation.  The elidable object defines several values that are used in our example.&lt;br /&gt; &lt;br /&gt;When compiling with the -Xelide-below &lt;value&gt;, the compiler parameter will remove all calls to elidable methods value and below.&lt;br /&gt; &lt;br /&gt;To try the following example copy the example into a scala file (elidable.scala for example) and compile as indicated below:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;package&amp;#160;example&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.annotation.elidable&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.annotation.elidable._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;ElidableExamples&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(ALL)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;all&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"all"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(ASSERTION)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;assertion&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"assertion"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(CONFIG)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;config&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"config"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(FINE)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;fine&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"fine"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(FINER)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;finer&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"finer"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(FINEST)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;finest&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"finest"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(INFO)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;info&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"info"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(OFF)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;off&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"off"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(SEVERE)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;severe&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"severe"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="annotation"&gt;@elidable&lt;/span&gt;(WARNING)&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;warning&amp;#160;=&amp;#160;println(&lt;span class="string"&gt;"warning"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;Main&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Application&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;println(&lt;span class="string"&gt;"starting"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;ElidableExamples._&lt;/li&gt;&lt;li class="codelist "&gt;all&lt;/li&gt;&lt;li class="codelist alt"&gt;assertion&lt;/li&gt;&lt;li class="codelist "&gt;config&lt;/li&gt;&lt;li class="codelist alt"&gt;fine&lt;/li&gt;&lt;li class="codelist "&gt;finer&lt;/li&gt;&lt;li class="codelist alt"&gt;finest&lt;/li&gt;&lt;li class="codelist "&gt;info&lt;/li&gt;&lt;li class="codelist alt"&gt;off&lt;/li&gt;&lt;li class="codelist "&gt;severe&lt;/li&gt;&lt;li class="codelist alt"&gt;warning&lt;/li&gt;&lt;li class="codelist "&gt;println(&lt;span class="string"&gt;"ending"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;assert(&lt;span class="basicType"&gt;false&lt;/span&gt;,&amp;#160;&lt;span class="string"&gt;"boom!"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt; &lt;br /&gt;&lt;/code&gt; &lt;br /&gt;Output from scalac elidable.scala &amp;&amp; scala example.Main&lt;br /&gt;&lt;blockquote&gt; &lt;br /&gt;starting&lt;br /&gt;assertion&lt;br /&gt;off&lt;br /&gt;ending&lt;br /&gt;java.lang.AssertionError: assertion failed: boom!&lt;br /&gt; at scala.Predef$.assert(Predef.scala:93)&lt;br /&gt; at example.Main$.&lt;init&gt;(elidable.scala:34)&lt;br /&gt; at example.Main$.&lt;clinit&gt;(elidable.scala)&lt;br /&gt; at example.Main.main(elidable.scala)&lt;br /&gt;&lt;/blockquote&gt; &lt;br /&gt;Output from scalac -Xelide-below 0 elidable.scala &amp;&amp; scala example.Main&lt;br /&gt;&lt;blockquote&gt; &lt;br /&gt;starting&lt;br /&gt;assertion&lt;br /&gt;config&lt;br /&gt;fine&lt;br /&gt;finer&lt;br /&gt;finest&lt;br /&gt;info&lt;br /&gt;off&lt;br /&gt;severe&lt;br /&gt;warning&lt;br /&gt;ending&lt;br /&gt;java.lang.AssertionError: assertion failed: boom!&lt;br /&gt; at scala.Predef$.assert(Predef.scala:93)&lt;br /&gt; at example.Main$.&lt;init&gt;(elidable.scala:34)&lt;br /&gt; at example.Main$.&lt;clinit&gt;(elidable.scala)&lt;br /&gt; at example.Main.main(elidable.scala)&lt;br /&gt;&lt;/blockquote&gt; &lt;br /&gt;Output from scalac -Xelide-below 1000 elidable.scala &amp;&amp; scala example.Main&lt;br /&gt;&lt;blockquote&gt; &lt;br /&gt;starting&lt;br /&gt;assertion&lt;br /&gt;off&lt;br /&gt;severe&lt;br /&gt;ending&lt;br /&gt;java.lang.AssertionError: assertion failed: boom!&lt;br /&gt; at scala.Predef$.assert(Predef.scala:93)&lt;br /&gt; at example.Main$.&lt;init&gt;(elidable.scala:34)&lt;br /&gt; at example.Main$.&lt;clinit&gt;(elidable.scala)&lt;br /&gt; at example.Main.main(elidable.scala)&lt;br /&gt;&lt;/blockquote&gt; &lt;br /&gt;Output from scalac -Xelide-below 3000 elidable.scala &amp;&amp; scala example.Main&lt;br /&gt;&lt;blockquote&gt; &lt;br /&gt;starting&lt;br /&gt;off&lt;br /&gt;ending&lt;br /&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-6211043443458526034?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/6211043443458526034/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/elidable-remove-method-calls-at-compile.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6211043443458526034'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6211043443458526034'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/elidable-remove-method-calls-at-compile.html' title='Elidable (remove method calls at compile time)'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-8864162560014296756</id><published>2010-04-06T00:03:00.001-07:00</published><updated>2010-04-06T00:03:36.104-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='2.8'/><title type='text'>Scala 2.7 to 2.8 migration help</title><content type='html'>Scala 2.8 has some very significant differences from Scala 2.7 so if you want to migrate from Scala 2.7 to 2.8 you might want to view this Stack overflow topic:&lt;br /&gt;&lt;br /&gt;&lt;a href="http://stackoverflow.com/questions/1243794/what-are-the-biggest-differences-between-scala-2-8-and-scala-2-7/2550803#2550803"&gt; What are the biggest differences between Scala 2.8 and Scala 2.7?&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;It has some good tips.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-8864162560014296756?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/8864162560014296756/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/scala-27-to-28-migration-help.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8864162560014296756'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8864162560014296756'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/scala-27-to-28-migration-help.html' title='Scala 2.7 to 2.8 migration help'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-8349183603803523696</id><published>2010-04-06T00:01:00.001-07:00</published><updated>2010-04-06T00:02:29.319-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='covariance'/><category scheme='http://www.blogger.com/atom/ns#' term='variance'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='contravariance'/><title type='text'>Variant Positions 3</title><content type='html'>The last few topics all discussed variance in its different forms.  The following is a cheat sheet of the where the different variances exist within a class. &lt;br /&gt;&lt;br /&gt;See &lt;a href="http://daily-scala.blogspot.com/2010/03/variant-positions-1.html"&gt;Variant positions 1&lt;/a&gt; for a discussion on one position in a class that is a contravariant position.  &lt;br /&gt;&lt;br /&gt;The example is:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;In this example A in the method write is an contravariant position.  Which means the previous definition is not legal because A is defined as Covariant in the class definition.  In a class there are several positions with different variance characteristics.  Here's the example from Programming in Scala:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;abstract&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Cat&lt;span class="type-param"&gt;[-T,&amp;#160;+U]&lt;/span&gt;&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;meow&lt;span class="type-param"&gt;[W&amp;lt;sup&amp;gt;-&amp;lt;/sup&amp;gt;]&lt;/span&gt;(volume:&amp;#160;T&lt;sup&gt;-&lt;/sup&gt;,&amp;#160;listener:&amp;#160;Cat&lt;span class="type-param"&gt;[U&amp;lt;sup&amp;gt;+&amp;lt;/sup&amp;gt;,&amp;#160;T&amp;lt;sup&amp;gt;-&amp;lt;/sup&amp;gt;]&lt;/span&gt;&lt;sup&gt;-&lt;/sup&gt;):&amp;#160;Cat&lt;span class="type-param"&gt;[Cat&lt;/span&gt;&lt;span class="type-param"&gt;[U&amp;lt;sup&amp;gt;+&amp;lt;/sup&amp;gt;,&amp;#160;T&amp;lt;sup&amp;gt;-&amp;lt;/sup&amp;gt;]&lt;/span&gt;&lt;sup&gt;-&lt;/sup&gt;,&amp;#160;U&lt;sup&gt;+&lt;/sup&gt;]&lt;sup&gt;+&lt;/sup&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;If you remove the superscript + and - the above example actually compiles.  The + and - indicate if the position is a covariant or contravariant position.  Its not critical to memorize the positions (in my opinion).  Just look it up as needed.  The rule of thumb is that each nested position is inverted (flipped) value of it enclosing position.&lt;br /&gt; &lt;br /&gt;That is all I will say about that :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-8349183603803523696?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/8349183603803523696/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/variant-positions-3.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8349183603803523696'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8349183603803523696'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/variant-positions-3.html' title='Variant Positions 3'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-6240922517862520837</id><published>2010-04-04T05:00:00.000-07:00</published><updated>2010-04-04T05:01:12.408-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='notice'/><title type='text'>Working on Scala IO</title><content type='html'>I just want to let everyone know that I am working hard on a Scala IO library right now and as such I want to dedicate all my spare time to doing that.  So (as has been the case lately) I plan to only update the blog 2-3 times a week.  Once done with the library I will try to increase the frequency of updates on the blog.  &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;If you have any topics or code snippets you think would be fit good with the block please send them to me at jeichar.w@gmail.com.&lt;br /&gt;&lt;br /&gt;Jesse&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-6240922517862520837?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/6240922517862520837/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/04/working-on-scala-io.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6240922517862520837'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6240922517862520837'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/04/working-on-scala-io.html' title='Working on Scala IO'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-7858814394195881474</id><published>2010-03-31T05:13:00.000-07:00</published><updated>2010-03-31T05:14:23.944-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='invariance'/><category scheme='http://www.blogger.com/atom/ns#' term='covariance'/><category scheme='http://www.blogger.com/atom/ns#' term='variance'/><category scheme='http://www.blogger.com/atom/ns#' term='collections'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><title type='text'>Variant Positions 2</title><content type='html'>This is a continuation of post: &lt;a href="http://daily-scala.blogspot.com/2010/03/variant-positions-1.html"&gt;Variant Positions 1&lt;/a&gt; &lt;br /&gt; &lt;br /&gt;...&lt;br /&gt; &lt;br /&gt;My first attempt at the Verified was to make it a mutable object (my Java tourettes kicking in).  But it cannot be covariant and mutable.  Look at the code to see why:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Verified&lt;span class="type-param"&gt;[+A&amp;#160;&amp;lt;:&amp;#160;V,V]&lt;/span&gt;(assertion&amp;#160;:&amp;#160;(V)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;,&amp;#160;&lt;span class="key"&gt;private&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;value&amp;#160;:&amp;#160;A){&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;assert(assertion(value))&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;a&amp;#160;=&amp;#160;value&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;update&amp;#160;is&amp;#160;illegal.&amp;#160;&amp;#160;See&amp;#160;the&amp;#160;example&amp;#160;below&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&lt;span class="type-param"&gt;[&amp;#160;B&amp;#160;&amp;gt;:&amp;#160;A&amp;#160;&amp;lt;:&amp;#160;V]&lt;/span&gt;(a&amp;#160;:&amp;#160;B)&amp;#160;=&amp;#160;value&amp;#160;=&amp;#160;a&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;notNull(obj&amp;#160;:&amp;#160;AnyRef)&amp;#160;=&amp;#160;obj&amp;#160;!=&amp;#160;&lt;span class="singleton"&gt;null&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;v&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Verified(notNull,&amp;#160;&lt;span class="string"&gt;"hi"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Up&amp;#160;to&amp;#160;this&amp;#160;point&amp;#160;everything&amp;#160;looks&amp;#160;ok&amp;#160;but&amp;#160;the&amp;#160;next&amp;#160;line&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;will&amp;#160;assign&amp;#160;an&amp;#160;object&amp;#160;to&amp;#160;value&amp;#160;which&amp;#160;is&amp;#160;a&amp;#160;reference&amp;#160;to&amp;#160;a&amp;#160;String&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;v&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&amp;#160;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Object())&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;For Verified to be mutable A must be invariant.  If you look at the Mutable collections in Scala they are all invariant.  &lt;br /&gt; &lt;br /&gt;Here is an interesting example of both invariant and covariant type parameters in a class hierarchy:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[+A]&lt;/span&gt;(&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:A)&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Y&lt;span class="type-param"&gt;[A]&lt;/span&gt;(&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;a:&amp;#160;A)&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[A]&lt;/span&gt;(a)&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Y&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x:&amp;#160;X&lt;span class="type-param"&gt;[Any]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y&lt;span class="type-param"&gt;[String]&lt;/span&gt;(&lt;span class="string"&gt;"hi"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;X&lt;span class="type-param"&gt;[Any]&lt;/span&gt;&amp;#160;=&amp;#160;Y&lt;span class="annotation"&gt;@&lt;/span&gt;1732a4df&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;x.asInstanceOf&lt;span class="type-param"&gt;[Y&lt;/span&gt;&lt;span class="type-param"&gt;[String]&lt;/span&gt;].a=&lt;span class="string"&gt;"ho"&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;This example is perfectly legal because no matter how X[Any] is used no illegal assignment in Y can occur.  The interesting thing is that the object can be used in covariant usecases when only X is required.  This is now the collections in Scala can work.  &lt;br /&gt; &lt;br /&gt;Here is a little example of collections invariance and covariance in action.  In List the parameter is covariant but in Buffer it is invariant  &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;printList(l&amp;#160;:&amp;#160;List&lt;span class="type-param"&gt;[Any]&lt;/span&gt;)&amp;#160;=&amp;#160;print(l&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;"&amp;#160;::&amp;#160;"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;printList:&amp;#160;(l:&amp;#160;List&lt;span class="type-param"&gt;[Any]&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;buffer&amp;#160;=&amp;#160;Buffer(1,2,3)&lt;/li&gt;&lt;li class="codelist alt"&gt;buffer:&amp;#160;scala.collection.mutable.Buffer&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;ArrayBuffer(1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;printList(buffer)&lt;/li&gt;&lt;li class="codelist "&gt;1&amp;#160;::&amp;#160;2&amp;#160;::&amp;#160;3&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;++&amp;#160;is&amp;#160;part&amp;#160;of&amp;#160;Iterable.&amp;#160;&amp;#160;Since&amp;#160;Iterable&amp;#160;is&amp;#160;covariant&amp;#160;++&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;returns&amp;#160;a&amp;#160;new&amp;#160;buffer&amp;#160;it&amp;#160;does&amp;#160;not&amp;#160;modify&amp;#160;the&amp;#160;existing&amp;#160;buffer&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;All&amp;#160;mutators&amp;#160;are&amp;#160;only&amp;#160;defined&amp;#160;on&amp;#160;invariant&amp;#160;traits&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;buffer&amp;#160;++&amp;#160;List(4)&lt;/li&gt;&lt;li class="codelist "&gt;res16:&amp;#160;scala.collection.mutable.Buffer&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;ArrayBuffer(1,&amp;#160;2,&amp;#160;3,&amp;#160;4)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;res16&amp;#160;eq&amp;#160;buffer&lt;/li&gt;&lt;li class="codelist alt"&gt;res17:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;buffer&amp;#160;defines&amp;#160;+=&amp;#160;to&amp;#160;add&amp;#160;an&amp;#160;element&amp;#160;to&amp;#160;the&amp;#160;buffer&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;so&amp;#160;res27&amp;#160;is&amp;#160;the&amp;#160;same&amp;#160;buffer&amp;#160;with&amp;#160;an&amp;#160;extra&amp;#160;element&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;buffer&amp;#160;+=&amp;#160;10&lt;/li&gt;&lt;li class="codelist "&gt;res27:&amp;#160;buffer.&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;=&amp;#160;ArrayBuffer(1,&amp;#160;2,&amp;#160;3,&amp;#160;10)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;res27&amp;#160;eq&amp;#160;buffer&lt;/li&gt;&lt;li class="codelist alt"&gt;res28:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-7858814394195881474?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/7858814394195881474/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/variant-positions-2.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7858814394195881474'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7858814394195881474'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/variant-positions-2.html' title='Variant Positions 2'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-6403382786498937381</id><published>2010-03-30T13:47:00.000-07:00</published><updated>2010-03-30T13:52:18.056-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='invariance'/><category scheme='http://www.blogger.com/atom/ns#' term='covariance'/><category scheme='http://www.blogger.com/atom/ns#' term='variance'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='contravariance'/><title type='text'>Variant Positions 1</title><content type='html'>An additional topic on variance to finish up the major points on the topic.  The previous two posts: &lt;ul&gt; &lt;li&gt;&lt;a href="http://daily-scala.blogspot.com/2010/03/intra-and-co-variance-of-type.html"&gt;In- and Co- variance of type parameters&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://daily-scala.blogspot.com/2010/03/contravariance.html"&gt;Contravariance&lt;/a&gt;&lt;/li&gt;&lt;/ul&gt; contain required information for following this post.&lt;br /&gt; &lt;br /&gt;In-, co- and contra- variance are the three types of variance expressible in Scala.  I showed how this affects assignments and arguments being pass to methods in the last two topics.  This looks at how the different types of variance influences how classes can be defined.  In the last post we saw how the compiler complained about a method definition in a covariant class because the compiler recognized that such a definition was inherently dangerous and must be prohibited.  The example was:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:5:&amp;#160;error:&amp;#160;covariant&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;A&amp;#160;occurs&amp;#160;in&amp;#160;contravariant&amp;#160;position&amp;#160;in&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;A&amp;#160;of&amp;#160;value&amp;#160;a&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;For an class like Output it does not make sense to have A be covariant so we changed A to be contravariant.  However suppose we have a collection type class.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Verified&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;(assertion&amp;#160;:&amp;#160;(A)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;,&amp;#160;value&amp;#160;:&amp;#160;A){&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;assert(assertion(value))&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;a&amp;#160;=&amp;#160;value&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;a_=(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Verified(assertion,&amp;#160;a)&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;The previous definition is not legal because value and a in the parameter of a_= "occur in a contravariant position."  What to do? Making A contravariant isn't an option:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Verified&lt;span class="type-param"&gt;[+A&amp;#160;&amp;lt;:&amp;#160;V,V]&lt;/span&gt;(assertion&amp;#160;:&amp;#160;(V)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;,&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;value&amp;#160;:&amp;#160;A){&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;assert(assertion(value))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;this&amp;#160;is&amp;#160;the&amp;#160;key.&amp;#160;&amp;#160;Restrict&amp;#160;possible&amp;#160;types&amp;#160;of&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;A&amp;#160;Since&amp;#160;B&amp;#160;is&amp;#160;a&amp;#160;super&amp;#160;(or&amp;#160;equal)&amp;#160;type&amp;#160;of&amp;#160;A&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&lt;span class="type-param"&gt;[&amp;#160;B&amp;#160;&amp;gt;:&amp;#160;A&amp;#160;&amp;lt;:&amp;#160;V]&lt;/span&gt;(a&amp;#160;:&amp;#160;B)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Verified(assertion,&amp;#160;a)&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;example&amp;#160;useage&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;notNull(obj&amp;#160;:&amp;#160;AnyRef)&amp;#160;=&amp;#160;obj&amp;#160;!=&amp;#160;&lt;span class="singleton"&gt;null&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;notNull:&amp;#160;(obj:&amp;#160;AnyRef)&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;v&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Verified(notNull,&amp;#160;&lt;span class="string"&gt;"hi"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;v:&amp;#160;Verified&lt;span class="type-param"&gt;[java.lang.String,AnyRef]&lt;/span&gt;&amp;#160;=&amp;#160;Verified&lt;span class="annotation"&gt;@&lt;/span&gt;307b37df&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;newV&amp;#160;=&amp;#160;v&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&amp;#160;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Object())&lt;/li&gt;&lt;li class="codelist "&gt;newV:&amp;#160;Verified&lt;span class="type-param"&gt;[java.lang.Object,AnyRef]&lt;/span&gt;&amp;#160;=&amp;#160;Verified&lt;span class="annotation"&gt;@&lt;/span&gt;36f72f09&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;3&amp;#160;is&amp;#160;not&amp;#160;legal&amp;#160;because&amp;#160;the&amp;#160;type&amp;#160;parameter&amp;#160;'V'&amp;#160;is&amp;#160;AnyRef.&amp;#160;&amp;#160;Int&amp;#160;is&amp;#160;a&amp;#160;subclass&amp;#160;of&amp;#160;Any&amp;#160;NOT&amp;#160;AnyRef&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;newV&amp;#160;=&amp;#160;v&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&amp;#160;(3)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:8:&amp;#160;error:&amp;#160;inferred&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;arguments&amp;#160;&lt;span class="type-param"&gt;[Any]&lt;/span&gt;&amp;#160;do&amp;#160;not&amp;#160;conform&amp;#160;to&amp;#160;method&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&lt;span class="char"&gt;'s&amp;#160;type&amp;#160;parameter&amp;#160;bounds&amp;#160;[B&amp;#160;&amp;gt;:&amp;#160;java.lang.String&amp;#160;&amp;lt;:&amp;#160;AnyRef]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;newV&amp;#160;=&amp;#160;v&amp;#160;&lt;span class="magic"&gt;update&lt;/span&gt;&amp;#160;(3)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-6403382786498937381?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/6403382786498937381/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/variant-positions-1.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6403382786498937381'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6403382786498937381'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/variant-positions-1.html' title='Variant Positions 1'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1243651165368467743</id><published>2010-03-27T05:57:00.000-07:00</published><updated>2010-03-29T00:06:39.913-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='covariance'/><category scheme='http://www.blogger.com/atom/ns#' term='variance'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='contravariance'/><title type='text'>Contravariance</title><content type='html'>Continuing on with variance and type parameters, this topic will discuss contravariance.  See the post &lt;a href="http://daily-scala.blogspot.com/2010/03/intra-and-co-variance-of-type.html"&gt;In- and Co- variance of type parameters&lt;/a&gt; for the intro material required for this topic.&lt;br /&gt; &lt;br /&gt;Covariant parameters allow for an additional dimension of type compatibility:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;l&amp;#160;:&amp;#160;List&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;List(&lt;span class="string"&gt;"this&amp;#160;is&amp;#160;legal"&lt;/span&gt;)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Contravariance provides the opposite:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;If&amp;#160;the&amp;#160;type&amp;#160;parameter&amp;#160;of&amp;#160;list&amp;#160;was&amp;#160;contravariant&amp;#160;this&amp;#160;would&amp;#160;be&amp;#160;legal:&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;l&amp;#160;:&amp;#160;List&lt;span class="type-param"&gt;[String]&lt;/span&gt;&amp;#160;=&amp;#160;List(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Object())&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;As covariance is indicated by a '+' before the type contravariance is indicated by a '-'&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[-A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;l&amp;#160;:&amp;#160;X&lt;span class="type-param"&gt;[String]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;l:&amp;#160;X&lt;span class="type-param"&gt;[String]&lt;/span&gt;&amp;#160;=&amp;#160;X&lt;span class="annotation"&gt;@&lt;/span&gt;66201d6d&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;I can almost hear the "cool... but why?".  Following the lead in the Programming In Scala book.  Consider OutputStream first and a method in a Collection second.  (The following code is illegal but consider it)&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;writeObject(out&amp;#160;:&amp;#160;Output&lt;span class="type-param"&gt;[Object]&lt;/span&gt;)&amp;#160;=&amp;#160;out.write(&lt;span class="string"&gt;"hello"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Uh&amp;#160;oh&amp;#160;you&amp;#160;this&amp;#160;only&amp;#160;is&amp;#160;for&amp;#160;outputting&amp;#160;lists&amp;#160;not&amp;#160;Objects&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;(certainly&amp;#160;not&amp;#160;the&amp;#160;String&amp;#160;that&amp;#160;is&amp;#160;actually&amp;#160;written)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Runtime&amp;#160;error&amp;#160;for&amp;#160;sure!&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;writeObject(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[List&lt;/span&gt;&lt;span class="type-param"&gt;[String]&lt;/span&gt;])&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;The previous example (if it would compile) would explode because an Output that can only write lists is passed to the method.  In the example a String is written to the Output object.  The Output[List[String]] cannot handle that.  &lt;br /&gt; &lt;br /&gt;Fortunately the compiler sees the definition of the class and recognizes this is an error waiting to happen and makes it illegal:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:5:&amp;#160;error:&amp;#160;covariant&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;A&amp;#160;occurs&amp;#160;in&amp;#160;contravariant&amp;#160;position&amp;#160;in&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;A&amp;#160;of&amp;#160;value&amp;#160;a&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Consider the implications of making A contravariant?&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;The&amp;#160;definition&amp;#160;of&amp;#160;object&amp;#160;is&amp;#160;now&amp;#160;legal&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[-A]&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;write(a&amp;#160;:&amp;#160;A)&amp;#160;=&amp;#160;()&amp;#160;&lt;span class="comment"&gt;/*do&amp;#160;write*/&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;this&amp;#160;is&amp;#160;now&amp;#160;a&amp;#160;safe&amp;#160;method&amp;#160;definition&amp;#160;since&amp;#160;the&amp;#160;parameter&amp;#160;of&amp;#160;Output&amp;#160;must&amp;#160;be&amp;#160;a&amp;#160;Object&amp;#160;or&amp;#160;a&amp;#160;super&amp;#160;class&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;writeObject(out&amp;#160;:&amp;#160;Output&lt;span class="type-param"&gt;[Object]&lt;/span&gt;)&amp;#160;=&amp;#160;out.write(&lt;span class="string"&gt;"hello"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;Now&amp;#160;this&amp;#160;is&amp;#160;illegal&amp;#160;as&amp;#160;it&amp;#160;should&amp;#160;be&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;writeObject(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[List&lt;/span&gt;&lt;span class="type-param"&gt;[String]&lt;/span&gt;])&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:8:&amp;#160;error:&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;mismatch;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;Output&lt;span class="type-param"&gt;[List&lt;/span&gt;&lt;span class="type-param"&gt;[String]&lt;/span&gt;]&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;required:&amp;#160;Output&lt;span class="type-param"&gt;[java.lang.Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;writeObject(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[List&lt;/span&gt;&lt;span class="type-param"&gt;[String]&lt;/span&gt;])&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;this&amp;#160;is&amp;#160;legal...&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;writeObject(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Output&lt;span class="type-param"&gt;[Any]&lt;/span&gt;)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;In this example Output[Any] can be passed to the method.  This makes sense.  If the Output object knows how to write Any oject then it knows how to write an Object; its all good.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1243651165368467743?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1243651165368467743/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/contravariance.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1243651165368467743'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1243651165368467743'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/contravariance.html' title='Contravariance'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-7463794881081527980</id><published>2010-03-24T01:08:00.000-07:00</published><updated>2010-03-26T12:54:26.763-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='invariance'/><category scheme='http://www.blogger.com/atom/ns#' term='covariance'/><category scheme='http://www.blogger.com/atom/ns#' term='variance'/><title type='text'>In- and Co- variance of type parameters</title><content type='html'>In Java most parameterized types are considered to be "invariant".  What does that mean?  Here is an example to explain:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;This&amp;#160;is&amp;#160;an&amp;#160;example&amp;#160;of&amp;#160;a&amp;#160;parameterized&amp;#160;class&amp;#160;that&amp;#160;with&amp;#160;an&amp;#160;invariant&amp;#160;parameter&amp;#160;B&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;In&amp;#160;both&amp;#160;Scala&amp;#160;and&amp;#160;Java&amp;#160;parameters&amp;#160;are&amp;#160;invariant&amp;#160;by&amp;#160;default.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[B]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Invariant&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Invariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;x:&amp;#160;Invariant&lt;span class="type-param"&gt;[java.lang.Object]&lt;/span&gt;&amp;#160;=&amp;#160;Invariant&lt;span class="annotation"&gt;@&lt;/span&gt;2e0c5575&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Note:&amp;#160;Invariant[String]&amp;#160;cannot&amp;#160;be&amp;#160;assigned&amp;#160;to&amp;#160;Invariant[Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;even&amp;#160;though&amp;#160;logically&amp;#160;it&amp;#160;seems&amp;#160;like&amp;#160;it&amp;#160;should&amp;#160;be.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;This&amp;#160;is&amp;#160;the&amp;#160;effect&amp;#160;of&amp;#160;invariance.&amp;#160;&amp;#160;Covariant&amp;#160;parameters&amp;#160;do&amp;#160;not&amp;#160;have&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;this&amp;#160;restriction.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Invariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:6:&amp;#160;error:&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;mismatch;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;Invariant&lt;span class="type-param"&gt;[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;required:&amp;#160;Invariant&lt;span class="type-param"&gt;[java.lang.Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Invariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Since&amp;#160;Sub&amp;#160;is&amp;#160;a&amp;#160;subclass&amp;#160;of&amp;#160;Invariant&amp;#160;it&amp;#160;can&amp;#160;be&amp;#160;assigned&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;(but&amp;#160;not&amp;#160;Sub[String])&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Invariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Sub&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;Invariant&lt;span class="type-param"&gt;[java.lang.Object]&lt;/span&gt;&amp;#160;=&amp;#160;Sub&lt;span class="annotation"&gt;@&lt;/span&gt;26ced1a8&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Assignment compatibility has multiple dimensions: the object type and the types of the parameters.  Unlike object type the compatibility of the type-parameters can be covariant, contravariant and invariant.  Java has invariant parameters and that is demonstrated by the previous example.  Covariant parameters allow subclassing.  Contravariant parameters need their own topic.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;The&amp;#160;'+'&amp;#160;indicates&amp;#160;the&amp;#160;parameter&amp;#160;is&amp;#160;covariant&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Covariant&lt;span class="type-param"&gt;[+B]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Covariant&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Covariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Covariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;x:&amp;#160;Covariant&lt;span class="type-param"&gt;[java.lang.Object]&lt;/span&gt;&amp;#160;=&amp;#160;Covariant&lt;span class="annotation"&gt;@&lt;/span&gt;315cb235&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;Now&amp;#160;this&amp;#160;is&amp;#160;legal&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;Covariant&lt;span class="type-param"&gt;[Object]&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Covariant&lt;span class="type-param"&gt;[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;x:&amp;#160;Covariant&lt;span class="type-param"&gt;[java.lang.Object]&lt;/span&gt;&amp;#160;=&amp;#160;Covariant&lt;span class="annotation"&gt;@&lt;/span&gt;26e2e276&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Warning:&amp;#160;The&amp;#160;following&amp;#160;is&amp;#160;not&amp;#160;legal&amp;#160;because&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;you&amp;#160;cannot&amp;#160;supply&amp;#160;an&amp;#160;invariant&amp;#160;parameter&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;with&amp;#160;a&amp;#160;covariant&amp;#160;value.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:7:&amp;#160;error:&amp;#160;covariant&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;A&amp;#160;occurs&amp;#160;in&amp;#160;invariant&amp;#160;position&amp;#160;in&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;&lt;span class="type-param"&gt;[+A]&lt;/span&gt;Invariant&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;ScalaObject{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;this():&amp;#160;Sub&lt;span class="type-param"&gt;[A]&lt;/span&gt;}&amp;#160;of&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Invariant&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;span class="type-param"&gt;[+A]&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Covariant&lt;span class="type-param"&gt;[A]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Covariant&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Sub&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-7463794881081527980?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/7463794881081527980/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/intra-and-co-variance-of-type.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7463794881081527980'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7463794881081527980'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/intra-and-co-variance-of-type.html' title='In- and Co- variance of type parameters'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-8368361714722329769</id><published>2010-03-22T01:01:00.000-07:00</published><updated>2010-03-23T00:54:52.251-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='operator'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='assignment'/><title type='text'>Implicit '=' operator</title><content type='html'>Continuing on with &lt;a href="http://daily-scala.blogspot.com/2010/03/operators.html"&gt;operators&lt;/a&gt;, There is a special type of operator in Scala.  It is an operator that ends with =.  If a class has operation (methods with an operator identifer) the = can be appended to the effectively creating a new method.  In truth a new method is not created instead the compiler rewrites the line.  &lt;br /&gt; &lt;br /&gt;For example.  If a method (like Int) defines + then a method call += can be used.  It can be used to mutate a variable:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;i&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist "&gt;i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;i&amp;#160;+=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;i&lt;/li&gt;&lt;li class="codelist alt"&gt;res3:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;To illustrate this is not a special case for Int the next example defines several operations and demonstrates in place variable mutation.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyClass(i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;{&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;+(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyClass(j&amp;#160;+&amp;#160;i)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;-(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyClass(i&amp;#160;-&amp;#160;j)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;^(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;MyClass(j)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;+|(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyClass(j&amp;#160;+&amp;#160;i&amp;#160;/&amp;#160;3)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyClass&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;c&amp;#160;=&amp;#160;MyClass(1)&lt;/li&gt;&lt;li class="codelist "&gt;c:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(1)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c+=6&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&lt;/li&gt;&lt;li class="codelist alt"&gt;res5:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(7)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&amp;#160;-=&amp;#160;2&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&lt;/li&gt;&lt;li class="codelist "&gt;res7:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(5)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&amp;#160;^=&amp;#160;10&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&lt;/li&gt;&lt;li class="codelist alt"&gt;res23:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(10)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&amp;#160;+|=&amp;#160;5&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&lt;/li&gt;&lt;li class="codelist "&gt;res25:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(8)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Here are several more examples using existing classes in Scala.  They are all immutable examples.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;l&amp;#160;=&amp;#160;Set(1,2,3)&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;l:&amp;#160;scala.collection.immutable.Set&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;Set(1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;l&amp;#160;+=&amp;#160;10&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;l&lt;/li&gt;&lt;li class="codelist alt"&gt;res7:&amp;#160;scala.collection.immutable.Set&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;Set(1,&amp;#160;2,&amp;#160;3,&amp;#160;10)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;seq&amp;#160;=&amp;#160;Seq(5,6,3)&lt;/li&gt;&lt;li class="codelist "&gt;seq:&amp;#160;Seq&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(5,&amp;#160;6,&amp;#160;3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;seq&amp;#160;:+=&amp;#160;10&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;seq&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res9:&amp;#160;Seq&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(5,&amp;#160;6,&amp;#160;3,&amp;#160;10)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;seq&amp;#160;+:=&amp;#160;10&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;seq&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res11:&amp;#160;Seq&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(10,&amp;#160;5,&amp;#160;6,&amp;#160;3,&amp;#160;10)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;list&amp;#160;=&amp;#160;List(32)&lt;/li&gt;&lt;li class="codelist alt"&gt;list:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(32)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;list&amp;#160;::=&amp;#160;12&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;list&lt;/li&gt;&lt;li class="codelist "&gt;res13:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;List(12,&amp;#160;32)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;Note: assignment operators can also be defined as methods to mutate an object&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyClass(&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;+=&amp;#160;(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;{&amp;#160;i+=j&amp;#160;;&amp;#160;this&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyClass&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;m&amp;#160;=&amp;#160;MyClass(6)&lt;/li&gt;&lt;li class="codelist alt"&gt;m:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(6)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;m&amp;#160;+=&amp;#160;7&lt;/li&gt;&lt;li class="codelist "&gt;res0:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(13)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;m&amp;#160;+=&amp;#160;9&lt;/li&gt;&lt;li class="codelist alt"&gt;res1:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(22)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;res1&amp;#160;eq&amp;#160;m&lt;/li&gt;&lt;li class="codelist "&gt;res2:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-8368361714722329769?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/8368361714722329769/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/implicit-operator.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8368361714722329769'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8368361714722329769'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/implicit-operator.html' title='Implicit &apos;=&apos; operator'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1836447952145124863</id><published>2010-03-19T06:50:00.000-07:00</published><updated>2010-03-21T12:36:52.267-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='operator'/><category scheme='http://www.blogger.com/atom/ns#' term='beginner'/><category scheme='http://www.blogger.com/atom/ns#' term='assignment'/><title type='text'>Operators</title><content type='html'>Since Scala allows one to define the behavior of operators there are some rules involving operators and assignment like +=.  One of the standard method calls in most languages is &lt;code&gt;i&amp;#160;+=&amp;#160;1.&lt;/code&gt; &lt;br /&gt; &lt;br /&gt;Since &lt;code&gt;i+=1&lt;/code&gt;(no spaces) is also valid,  Scala has some rules regarding how statements like &lt;code&gt;i+=1&lt;/code&gt; should be broken up.  Obviously we know it should be 'i' '+=' and '1'.  So there is a special class of characters called operators.  I don't know all of them but a few are: &lt;code&gt;+&amp;#160;-&amp;#160;^&amp;#160;*&amp;#160;/&amp;#160;%&amp;#160;!&amp;#160;|&amp;#160;&amp;amp;&amp;#160;=&lt;/code&gt;( ':' is sort of part of this group but has some special properties as well). &lt;br /&gt; &lt;br /&gt;These characters can be method names but they cannot be combined with other identifier characters.&lt;br /&gt; &lt;br /&gt;Update:  These characters can be combined with other identifier characters if there is an under score so:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x+&amp;#160;=&amp;#160;3&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;not&amp;#160;valid&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x_+&amp;#160;=&amp;#160;3&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;valid&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;+x&amp;#160;=&amp;#160;3&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;not&amp;#160;valid&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt;However these characters &lt;em&gt;are&lt;/em&gt; special because they can be combined in a special way with '=' for a special assignment construct as shown in the next post.&lt;br /&gt; &lt;br /&gt;(end update)&lt;br /&gt; &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MyClass(i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;+(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyClass(j&amp;#160;+&amp;#160;i)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;-(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyClass(i&amp;#160;-&amp;#160;j)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;^(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;MyClass(j)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;+|(j:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;MyClass(j&amp;#160;+&amp;#160;i&amp;#160;/&amp;#160;3)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;c&amp;#160;=&amp;#160;MyClass(3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;c:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(3)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&amp;#160;+&amp;#160;4&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;res26:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(7)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c-2&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;res27:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(1)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&amp;#160;-6&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;res28:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(-3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c&amp;#160;^&amp;#160;3&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;res29:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(3)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;c+|5&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;res31:&amp;#160;MyClass&amp;#160;=&amp;#160;MyClass(6)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1836447952145124863?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1836447952145124863/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/operators.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1836447952145124863'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1836447952145124863'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/operators.html' title='Operators'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-775841458375746934</id><published>2010-03-17T06:39:00.000-07:00</published><updated>2010-03-17T06:43:11.156-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='project'/><category scheme='http://www.blogger.com/atom/ns#' term='geoscript'/><title type='text'>Geoscript.scala</title><content type='html'>This is a bit of a departure from the standard daily-scala format, but it is one of the elements I had always invisioned.  This topic takes a look at &lt;a href="http://geoscript.org/index.html"&gt;Geoscript.scala.&lt;/a&gt;  (Github repo is at: &lt;a href="http://github.com/dwins/geoscript.scala"&gt;http://github.com/dwins/geoscript.scala&lt;/a&gt;)&lt;br /&gt; &lt;br /&gt;Geoscript has been given a Scala implementation.  It is based on the Geotools Java library and thus far provides a script interface to access some of the basic spatial functions.&lt;br /&gt; &lt;br /&gt;For setting up the console with the required libraries follow the instructions at: &lt;a href="http://geoscript.org/scala/quickstart.html#quickstart"&gt;http://geoscript.org/scala/quickstart.html#quickstart&lt;/a&gt; &lt;br /&gt; &lt;br /&gt;Here is an example of Geoscript in action:&lt;br /&gt; &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.geoscript.GeoScript._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.geoscript.GeoScript._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.geoscript.geometry._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.geoscript.geometry._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;line&amp;#160;=&amp;#160;LineString((10,&amp;#160;10),&amp;#160;(20,&amp;#160;20),&amp;#160;(30,&amp;#160;40))&lt;/li&gt;&lt;li class="codelist "&gt;line:&amp;#160;org.geoscript.geometry.LineString&amp;#160;=&amp;#160;LINESTRING&amp;#160;(10&amp;#160;10,&amp;#160;20&amp;#160;20,&amp;#160;30&amp;#160;40)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;create&amp;#160;a&amp;#160;polygon&amp;#160;by&amp;#160;buffering&amp;#160;the&amp;#160;line&amp;#160;(essentially&amp;#160;expanding&amp;#160;the&amp;#160;line&amp;#160;by&amp;#160;10&amp;#160;units&amp;#160;that&amp;#160;is&amp;#160;degrees&amp;#160;if&amp;#160;not&amp;#160;otherwise&amp;#160;specified)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;poly&amp;#160;=&amp;#160;line&amp;#160;buffer&amp;#160;10&lt;/li&gt;&lt;li class="codelist "&gt;poly:&amp;#160;org.geoscript.geometry.Geometry&amp;#160;=&amp;#160;POLYGON&amp;#160;((11.781455848733053&amp;#160;25.923591472464004,&amp;#160;21.05572809000084&amp;#160;44.47213595499958,&amp;#160;22.100060210309515&amp;#160;46.13114600374718,&amp;#160;23.447982586398712&amp;#160;47.55453954995706,&amp;#160;25.04769531727891&amp;#160;48.68761637789669,&amp;#160;26.837722339831622&amp;#160;49.48683298050514,&amp;#160;28.74927391943886&amp;#160;49.921475911950004,&amp;#160;30.708890200906794&amp;#160;49.97484208812642,&amp;#160;32.64126422950409&amp;#160;49.6448806768120...&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;query&amp;#160;the&amp;#160;area&amp;#160;of&amp;#160;the&amp;#160;polygon&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;poly.area&lt;/li&gt;&lt;li class="codelist "&gt;res0:&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;&amp;#160;=&amp;#160;1041.9912814842407&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;get&amp;#160;the&amp;#160;centroids&amp;#160;of&amp;#160;the&amp;#160;polygon&amp;#160;and&amp;#160;line&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;line.centroid&lt;/li&gt;&lt;li class="codelist "&gt;res1:&amp;#160;org.geoscript.geometry.Point&amp;#160;=&amp;#160;POINT&amp;#160;(21.12574113277207&amp;#160;24.188611699158105)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;poly.centroid&lt;/li&gt;&lt;li class="codelist alt"&gt;res2:&amp;#160;org.geoscript.geometry.Point&amp;#160;=&amp;#160;POINT&amp;#160;(20.79088988611118&amp;#160;24.43096430943361)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Obviously&amp;#160;the&amp;#160;polygon&amp;#160;and&amp;#160;line&amp;#160;intersect&amp;#160;since&amp;#160;the&amp;#160;polygon&amp;#160;is&amp;#160;a&amp;#160;buffer&amp;#160;of&amp;#160;the&amp;#160;line&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;poly.intersects(line)&lt;/li&gt;&lt;li class="codelist "&gt;res3:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;poly2&amp;#160;=&amp;#160;Geometry.fromWKT(&lt;span class="string"&gt;"POLYGON&amp;#160;((10&amp;#160;10,&amp;#160;10&amp;#160;20,&amp;#160;20&amp;#160;20,&amp;#160;20&amp;#160;15,&amp;#160;10&amp;#160;10))"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;poly2:&amp;#160;org.geoscript.geometry.Geometry&amp;#160;=&amp;#160;POLYGON&amp;#160;((10&amp;#160;10,&amp;#160;10&amp;#160;20,&amp;#160;20&amp;#160;20,&amp;#160;20&amp;#160;15,&amp;#160;10&amp;#160;10))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;less&amp;#160;trivial&amp;#160;intersects&amp;#160;operation&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;poly&amp;#160;intersects&amp;#160;poly2&lt;/li&gt;&lt;li class="codelist alt"&gt;res3:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;not&amp;#160;make&amp;#160;a&amp;#160;new&amp;#160;geometry&amp;#160;from&amp;#160;the&amp;#160;intersection&amp;#160;of&amp;#160;the&amp;#160;two&amp;#160;geometries&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;intersecting&amp;#160;=&amp;#160;poly&amp;#160;intersection&amp;#160;poly2&lt;/li&gt;&lt;li class="codelist alt"&gt;intersecting:&amp;#160;org.geoscript.geometry.Geometry&amp;#160;=&amp;#160;POLYGON&amp;#160;((10&amp;#160;10,&amp;#160;10&amp;#160;20,&amp;#160;20&amp;#160;20,&amp;#160;20&amp;#160;15,&amp;#160;10&amp;#160;10))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;intersecting.area&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res6:&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;&amp;#160;=&amp;#160;75.0&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.geoscript.projection._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.geoscript.projection._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;None&amp;#160;of&amp;#160;the&amp;#160;previous&amp;#160;geometries&amp;#160;has&amp;#160;a&amp;#160;projection&amp;#160;associated.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;A&amp;#160;new&amp;#160;geometry&amp;#160;can&amp;#160;have&amp;#160;one&amp;#160;created&amp;#160;with&amp;#160;a&amp;#160;projection&amp;#160;by&amp;#160;using&amp;#160;the&amp;#160;&lt;strong&gt;in(Projection)&lt;/strong&gt;&amp;#160;method&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;latLongPoly&amp;#160;=&amp;#160;poly2&amp;#160;in&amp;#160;Projection(&lt;span class="string"&gt;"epsg:4326"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;latLongPoly:&amp;#160;org.geoscript.geometry.Geometry&amp;#160;=&amp;#160;POLYGON&amp;#160;((10&amp;#160;10,&amp;#160;10&amp;#160;20,&amp;#160;20&amp;#160;20,&amp;#160;20&amp;#160;15,&amp;#160;10&amp;#160;10))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;now&amp;#160;reproject&amp;#160;the&amp;#160;latlong&amp;#160;projection&amp;#160;to&amp;#160;a&amp;#160;french&amp;#160;projection&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;latLongPoly&amp;#160;in&amp;#160;Projection(&lt;span class="string"&gt;"epsg:21781"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;res12:&amp;#160;org.geoscript.geometry.Geometry&amp;#160;=&amp;#160;POLYGON&amp;#160;((950650.7690658928&amp;#160;-4203986.192880551,&amp;#160;900363.7533498043&amp;#160;-2900002.601715782,&amp;#160;2061411.5566836582&amp;#160;-2774908.8442438124,&amp;#160;2174910.791185147&amp;#160;-3393231.5380846346,&amp;#160;950650.7690658928&amp;#160;-4203986.192880551))&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-775841458375746934?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/775841458375746934/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/geoscriptscala.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/775841458375746934'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/775841458375746934'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/geoscriptscala.html' title='Geoscript.scala'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-5331825190091340289</id><published>2010-03-16T05:00:00.001-07:00</published><updated>2010-03-17T01:35:13.662-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='assert'/><category scheme='http://www.blogger.com/atom/ns#' term='require'/><category scheme='http://www.blogger.com/atom/ns#' term='assume'/><category scheme='http://www.blogger.com/atom/ns#' term='beginner'/><title type='text'>Assert, Require, Assume</title><content type='html'>Very simple but useful are the methods assert, require and assume which are built into the Predef object.  As you might expect they are methods for performing certain checks during runtime to verify certain conditions.  They do not use the Java assert framework and therefore are always evaluated regardless of whether or not assertions are enabled.&lt;br /&gt;&lt;br /&gt;Update:  Scala 2.8 has an annotation called elidable that will (when 2.8 is complete) allow one to remove method calls at compile time by setting a compiler flag.  The assert, etc... methods are all marked with this flag and as a result can be removed at compile time for production environments.&lt;br /&gt; &lt;br /&gt;Scala2.8&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;called&amp;#160;=&amp;#160;0&lt;/li&gt;&lt;li class="codelist "&gt;called:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;0&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;called&lt;/li&gt;&lt;li class="codelist alt"&gt;res0:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;0&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;assert,&amp;#160;require&amp;#160;and&amp;#160;assume&amp;#160;have&amp;#160;call&amp;#160;by&amp;#160;name&amp;#160;parameters&amp;#160;so&amp;#160;the&amp;#160;message&amp;#160;is&amp;#160;only&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;calculated&amp;#160;when&amp;#160;the&amp;#160;assertion&amp;#160;fails.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;assert&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;require&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;assume&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;called&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist "&gt;called:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;demonstrating&amp;#160;that&amp;#160;the&amp;#160;method&amp;#160;is&amp;#160;in&amp;#160;fact&amp;#160;called&amp;#160;when&amp;#160;the&amp;#160;assertion&amp;#160;fails&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;assert&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;called&amp;#160;is&amp;#160;not&amp;#160;0&lt;/li&gt;&lt;li class="codelist alt"&gt;java.lang.AssertionError:&amp;#160;assertion&amp;#160;failed:&amp;#160;()&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;scala.Predef$.assert(Predef.scala:95)&lt;/li&gt;&lt;li class="codelist alt"&gt; ...&lt;/li&gt;&lt;li class="codelist "&gt; &lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;called&lt;/li&gt;&lt;li class="codelist "&gt;res4:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Require&amp;#160;is&amp;#160;intended&amp;#160;to&amp;#160;be&amp;#160;used&amp;#160;as&amp;#160;a&amp;#160;precondition&amp;#160;of&amp;#160;a&amp;#160;method&amp;#160;so&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;it&amp;#160;throws&amp;#160;an&amp;#160;IllegalArgumentException,&amp;#160;not&amp;#160;an&amp;#160;AssertionError&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;require&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&lt;/li&gt;&lt;li class="codelist alt"&gt;called&amp;#160;is&amp;#160;not&amp;#160;0&lt;/li&gt;&lt;li class="codelist "&gt;java.lang.IllegalArgumentException:&amp;#160;requirement&amp;#160;failed:&amp;#160;()&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;scala.Predef$.require(Predef.scala:117)&lt;/li&gt;&lt;li class="codelist "&gt; ...&lt;/li&gt;&lt;li class="codelist alt"&gt; &lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;called&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res6:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;3&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;assume&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;called&amp;#160;is&amp;#160;not&amp;#160;0&lt;/li&gt;&lt;li class="codelist alt"&gt;java.lang.AssertionError:&amp;#160;assumption&amp;#160;failed:&amp;#160;()&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;scala.Predef$.assume(Predef.scala:107)&lt;/li&gt;&lt;li class="codelist alt"&gt; ...&lt;/li&gt;&lt;li class="codelist "&gt; &lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;called&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res8:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;4&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt; &lt;br /&gt; &lt;br /&gt;scala 2.7.7&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;In&amp;#160;Scala&amp;#160;2.7&amp;#160;the&amp;#160;parameter&amp;#160;is&amp;#160;evaluated&amp;#160;before&amp;#160;the&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;method&amp;#160;is&amp;#160;called&amp;#160;so&amp;#160;the&amp;#160;side&amp;#160;effect&amp;#160;of&amp;#160;the&amp;#160;message&amp;#160;causes&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;the&amp;#160;assertion&amp;#160;to&amp;#160;fail&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;assert&amp;#160;(called&amp;#160;==&amp;#160;0,&amp;#160;{called&amp;#160;+=&amp;#160;1;&amp;#160;println(&lt;span class="string"&gt;"called&amp;#160;is&amp;#160;not&amp;#160;0"&lt;/span&gt;)})&lt;/li&gt;&lt;li class="codelist alt"&gt;called&amp;#160;is&amp;#160;not&amp;#160;0&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;called&lt;/li&gt;&lt;li class="codelist "&gt;res2:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-5331825190091340289?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/5331825190091340289/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/assert-require-assume.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5331825190091340289'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5331825190091340289'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/assert-require-assume.html' title='Assert, Require, Assume'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-9008137555765349941</id><published>2010-03-15T13:12:00.000-07:00</published><updated>2010-03-15T13:13:58.863-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='unzip'/><category scheme='http://www.blogger.com/atom/ns#' term='traversable'/><category scheme='http://www.blogger.com/atom/ns#' term='2.8'/><category scheme='http://www.blogger.com/atom/ns#' term='beginner'/><title type='text'>Unzip</title><content type='html'>_ Scala 2.8 only tip _&lt;br /&gt; &lt;br /&gt;Unzip is a handy companion to partition.  &lt;br /&gt; - Partition divides a traversable into two traversables by a boolean predicate.  &lt;br /&gt; - Unzip divides a traversable into two by dividing each element into two parts (each becomes an element in one traversable).  If an element is a Tuple2 then each tuple is divided into two otherwise a function is required to divide an element into two.&lt;br /&gt; &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;basic&amp;#160;usage&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List((1,2),(2,3)).unzip&lt;/li&gt;&lt;li class="codelist alt"&gt;res2:&amp;#160;(List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;,&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;#160;=&amp;#160;(List(1,&amp;#160;2),List(2,&amp;#160;3))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;tuples&amp;#160;can&amp;#160;be&amp;#160;of&amp;#160;different&amp;#160;types&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;and&amp;#160;the&amp;#160;resulting&amp;#160;traversables&amp;#160;reflect&amp;#160;the&amp;#160;differing&amp;#160;types&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List((2,&lt;span class="string"&gt;"a"&lt;/span&gt;),(3,&lt;span class="string"&gt;"b"&lt;/span&gt;)).unzip&lt;/li&gt;&lt;li class="codelist "&gt;res3:&amp;#160;(List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;,&amp;#160;List&lt;span class="type-param"&gt;[java.lang.String]&lt;/span&gt;)&amp;#160;=&amp;#160;(List(2,&amp;#160;3),List(a,&amp;#160;b))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Maps&amp;#160;are&amp;#160;Traversable[Collection]&amp;#160;so&amp;#160;unzip&amp;#160;works&amp;#160;with&amp;#160;them&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;Map(1&amp;#160;-&gt;&amp;#160;2,&amp;#160;3&amp;#160;-&gt;&amp;#160;4).unzip&lt;/li&gt;&lt;li class="codelist "&gt;res1:&amp;#160;(scala.collection.immutable.Iterable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;,&amp;#160;scala.collection.immutable.Iterable&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;#160;=&amp;#160;(List(1,&amp;#160;3),List(2,&amp;#160;4))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Of&amp;#160;course&amp;#160;sets&amp;#160;result&amp;#160;in&amp;#160;sets&amp;#160;and&amp;#160;duplicates&amp;#160;are&amp;#160;collected&amp;#160;to&amp;#160;a&amp;#160;single&amp;#160;element&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;Set((1,2),(2,2)).unzip&lt;/li&gt;&lt;li class="codelist "&gt;res7:&amp;#160;(scala.collection.immutable.Set&lt;span class="type-param"&gt;[Int]&lt;/span&gt;,&amp;#160;scala.collection.immutable.Set&lt;span class="type-param"&gt;[Int]&lt;/span&gt;)&amp;#160;=&amp;#160;(Set(1,&amp;#160;2),Set(2))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Arbitrary&amp;#160;elements&amp;#160;can&amp;#160;be&amp;#160;unziped&amp;#160;if&amp;#160;a&amp;#160;method&amp;#160;is&amp;#160;provided&amp;#160;to&amp;#160;decompose&amp;#160;each&amp;#160;element&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(&lt;span class="string"&gt;"one&amp;#160;word"&lt;/span&gt;,&amp;#160;&lt;span class="string"&gt;"another&amp;#160;word"&lt;/span&gt;).unzip&amp;#160;{e&amp;#160;=&gt;&amp;#160;(e&amp;#160;takeWhile&amp;#160;{_&amp;#160;!=&amp;#160;&lt;span class="char"&gt;'&amp;#160;'&lt;/span&gt;},&amp;#160;e&amp;#160;dropWhile&amp;#160;{_&amp;#160;!=&amp;#160;&lt;span class="char"&gt;'&amp;#160;'&lt;/span&gt;})}&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res6:&amp;#160;(List&lt;span class="type-param"&gt;[String]&lt;/span&gt;,&amp;#160;List&lt;span class="type-param"&gt;[String]&lt;/span&gt;)&amp;#160;=&amp;#160;(List(one,&amp;#160;another),List(&amp;#160;word,&amp;#160;&amp;#160;word))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;The&amp;#160;following&amp;#160;shows&amp;#160;the&amp;#160;same&amp;#160;function&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;applied&amp;#160;with&amp;#160;map.&amp;#160;&amp;#160;It&amp;#160;results&amp;#160;in&amp;#160;a&amp;#160;single&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;list&amp;#160;of&amp;#160;Tuples&amp;#160;rather&amp;#160;than&amp;#160;two&amp;#160;lists&amp;#160;of&amp;#160;single&amp;#160;elements&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&amp;#160;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(&lt;span class="string"&gt;"one&amp;#160;word"&lt;/span&gt;,&amp;#160;&lt;span class="string"&gt;"another&amp;#160;word"&lt;/span&gt;).map&amp;#160;{e&amp;#160;=&gt;&amp;#160;(e&amp;#160;takeWhile&amp;#160;{_&amp;#160;!=&amp;#160;&lt;span class="char"&gt;'&amp;#160;'&lt;/span&gt;},&amp;#160;e&amp;#160;dropWhile&amp;#160;{_&amp;#160;!=&amp;#160;&lt;span class="char"&gt;'&amp;#160;'&lt;/span&gt;})}&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res8:&amp;#160;List&lt;span class="type-param"&gt;[(String,&amp;#160;String)]&lt;/span&gt;&amp;#160;=&amp;#160;List((one,&amp;#160;word),&amp;#160;(another,&amp;#160;word))&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-9008137555765349941?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/9008137555765349941/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/unzip.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/9008137555765349941'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/9008137555765349941'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/unzip.html' title='Unzip'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1335925860839688713</id><published>2010-03-12T04:04:00.000-08:00</published><updated>2010-03-12T04:05:02.242-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='case-classes'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><title type='text'>Multiple Argument Implicit Conversions</title><content type='html'>Suppose you are creating a DSL and you want to implicitly convert 2 values to a particular object:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;v&amp;#160;:&amp;#160;SomeObject&amp;#160;=&amp;#160;(2,&amp;#160;3)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;This is easily attained.  In this example we will support the previous example as well as the standard 1 object to another implicit conversion.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;v&amp;#160;:&amp;#160;SomeObject&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Example:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;first&amp;#160;lets&amp;#160;define&amp;#160;a&amp;#160;class&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Randomly(x&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;y&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Randomly&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;the&amp;#160;normal&amp;#160;conversion&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;intToRandomly(i&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Randomly(i,0.0)&lt;/li&gt;&lt;li class="codelist alt"&gt;intToRandomly:&amp;#160;(i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)Randomly&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;now&amp;#160;a&amp;#160;tuple&amp;#160;for&amp;#160;the&amp;#160;other&amp;#160;conversion.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Important:&amp;#160;&amp;#160;The&amp;#160;two&amp;#160;conversions&amp;#160;must&amp;#160;have&amp;#160;different&amp;#160;names.&amp;#160;At&amp;#160;least&amp;#160;that&amp;#160;is&amp;#160;the&amp;#160;case&amp;#160;in&amp;#160;Scala&amp;#160;2.8&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;tupleToRandomly(i&amp;#160;:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;))&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Randomly(i._1,&amp;#160;i._2)&lt;/li&gt;&lt;li class="codelist alt"&gt;tupleToRandomly:&amp;#160;(i:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;&lt;span class="basicType"&gt;Double&lt;/span&gt;))Randomly&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;r1&amp;#160;:&amp;#160;Randomly&amp;#160;=&amp;#160;4&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;r1:&amp;#160;Randomly&amp;#160;=&amp;#160;Randomly(4,0.0)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;r2&amp;#160;:&amp;#160;Randomly&amp;#160;=&amp;#160;(4,&amp;#160;6.0)&lt;/li&gt;&lt;li class="codelist alt"&gt;r2:&amp;#160;Randomly&amp;#160;=&amp;#160;Randomly(4,6.0)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Suppose&amp;#160;you&amp;#160;want&amp;#160;to&amp;#160;do&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;val&amp;#160;r&amp;#160;:&amp;#160;Randomly&amp;#160;=&amp;#160;(4,4)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;you&amp;#160;might&amp;#160;think&amp;#160;to&amp;#160;implicitly&amp;#160;convert&amp;#160;from&amp;#160;in&amp;#160;to&amp;#160;double&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;intToDouble(i&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;i.toDouble&lt;/li&gt;&lt;li class="codelist alt"&gt;intToDouble:&amp;#160;(i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;span class="basicType"&gt;Double&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;implicit&amp;#160;chaining&amp;#160;is&amp;#160;not&amp;#160;permitted&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;r3&amp;#160;:&amp;#160;Randomly&amp;#160;=&amp;#160;(4,&amp;#160;6)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:10:&amp;#160;error:&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;mismatch;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;found&amp;#160;&amp;#160;&amp;#160;:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;required:&amp;#160;Randomly&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;r3&amp;#160;:&amp;#160;Randomly&amp;#160;=&amp;#160;(4,&amp;#160;6)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Here&amp;#160;is&amp;#160;the&amp;#160;legal&amp;#160;option&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;intTupleToRandomly(t:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;,Int))&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Randomly(t._1,t._2.toDouble)&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;intTupleToRandomly:&amp;#160;(t:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;))Randomly&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;r3&amp;#160;:&amp;#160;Randomly&amp;#160;=&amp;#160;(4,&amp;#160;6)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;r3:&amp;#160;Randomly&amp;#160;=&amp;#160;Randomly(4,6.0)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1335925860839688713?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1335925860839688713/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/multiple-argument-implicit-conversions.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1335925860839688713'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1335925860839688713'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/multiple-argument-implicit-conversions.html' title='Multiple Argument Implicit Conversions'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-563347759910973025</id><published>2010-03-10T07:15:00.000-08:00</published><updated>2010-03-10T07:16:24.367-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='Map'/><category scheme='http://www.blogger.com/atom/ns#' term='groupby'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='swap'/><title type='text'>How to reverse a map</title><content type='html'>Suppose you wish to take a map and swap the keys with values.  The stackoverflow question &lt;a href="http://stackoverflow.com/questions/2338282/elegant-way-to-reverse-a-map-in-scala"&gt;Elegant way to revers a map in scala&lt;/a&gt; offers some good suggestions&lt;br /&gt; &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;nodupes&amp;#160;=&amp;#160;Map(1&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"a"&lt;/span&gt;,&amp;#160;2-&gt;&amp;#160;&lt;span class="string"&gt;"b"&lt;/span&gt;,&amp;#160;3&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"c"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;nodupes:&amp;#160;scala.collection.immutable.Map&lt;span class="type-param"&gt;[Int,java.lang.String]&lt;/span&gt;&amp;#160;=&amp;#160;Map((1,a),&amp;#160;(2,b),&amp;#160;(3,c))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Scala&amp;#160;2.8+&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;nodupes&amp;#160;map&amp;#160;{_.swap}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res4:&amp;#160;scala.collection.immutable.Map&lt;span class="type-param"&gt;[java.lang.String,Int]&lt;/span&gt;&amp;#160;=&amp;#160;Map((a,1),&amp;#160;(b,2),&amp;#160;(c,3))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Scala&amp;#160;2.7&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;Map()&amp;#160;++&amp;#160;(nodupes&amp;#160;map&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(k,v)&amp;#160;=&gt;&amp;#160;(v,k)})&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res5:&amp;#160;scala.collection.immutable.Map&lt;span class="type-param"&gt;[java.lang.String,Int]&lt;/span&gt;&amp;#160;=&amp;#160;Map((a,1),&amp;#160;(b,2),&amp;#160;(c,3))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;watch&amp;#160;out&amp;#160;if&amp;#160;the&amp;#160;values&amp;#160;have&amp;#160;duplicates&amp;#160;you&amp;#160;will&amp;#160;loose&amp;#160;information:&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;dupes&amp;#160;=&amp;#160;Map(1&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"a"&lt;/span&gt;,&amp;#160;2-&gt;&amp;#160;&lt;span class="string"&gt;"b"&lt;/span&gt;,&amp;#160;3&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"b"&lt;/span&gt;)&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;dupes:&amp;#160;scala.collection.immutable.Map&lt;span class="type-param"&gt;[Int,java.lang.String]&lt;/span&gt;&amp;#160;=&amp;#160;Map((1,a),&amp;#160;(2,b),&amp;#160;(3,b))&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;dupes&amp;#160;map&amp;#160;{_.swap}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res6:&amp;#160;scala.collection.immutable.Map&lt;span class="type-param"&gt;[java.lang.String,Int]&lt;/span&gt;&amp;#160;=&amp;#160;Map((a,1),&amp;#160;(b,3))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;a&amp;#160;way&amp;#160;to&amp;#160;not&amp;#160;loose&amp;#160;any&amp;#160;data&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;dupes&amp;#160;groupBy&amp;#160;{_._2}&amp;#160;map&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(key,value)&amp;#160;=&gt;&amp;#160;(key,&amp;#160;value.unzip._1)}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res12:&amp;#160;scala.collection.Map&lt;span class="type-param"&gt;[java.lang.String,scala.collection.immutable.Iterable&lt;/span&gt;&lt;span class="type-param"&gt;[Int]&lt;/span&gt;]&amp;#160;=&amp;#160;Map((a,List(1)),&amp;#160;(b,List(2,&amp;#160;3)))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;I&amp;#160;wanted&amp;#160;to&amp;#160;do&amp;#160;the&amp;#160;following&amp;#160;for&amp;#160;performance:&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;dupes.view&amp;#160;groupBy&amp;#160;{_._2}&amp;#160;map&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(key,value)&amp;#160;=&gt;&amp;#160;(key,&amp;#160;value.unzip._1)}&lt;/li&gt;&lt;li class="codelist "&gt;java.lang.UnsupportedOperationException:&amp;#160;IterableView((1,a),&amp;#160;(2,b),&amp;#160;(3,b)).newBuilder&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;scala.collection.TraversableViewLike$class.newBuilder(TraversableViewLike.scala:40)&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;scala.collection.IterableLike$$anon$1.newBuilder(IterableLike.scala:363)&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;scala.collection.TraversableLike$$anonfun$groupBy$1.&lt;span class="magic"&gt;apply&lt;/span&gt;(TraversableLike.scala:370)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;but&amp;#160;as&amp;#160;you&amp;#160;can&amp;#160;see&amp;#160;a&amp;#160;view&amp;#160;cannot&amp;#160;yet&amp;#160;be&amp;#160;grouped.&amp;#160;&amp;#160;Perhaps&amp;#160;in&amp;#160;the&amp;#160;future.&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-563347759910973025?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/563347759910973025/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/how-to-reverse-map.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/563347759910973025'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/563347759910973025'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/how-to-reverse-map.html' title='How to reverse a map'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-3583867384533699630</id><published>2010-03-08T00:02:00.000-08:00</published><updated>2010-03-08T00:05:47.246-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='random'/><category scheme='http://www.blogger.com/atom/ns#' term='range'/><title type='text'>Lazy man's random test data</title><content type='html'>A quick tip for generating some random testdata.  &lt;br /&gt; &lt;br /&gt;Note: This is a poor man's solution to using ScalaCheck.  If you can handle the dependency I would really recommend using that library.&lt;br /&gt; &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;Options&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Enumeration&amp;#160;{&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;ONE,&amp;#160;TWO,&amp;#160;THREE,&amp;#160;FOUR&amp;#160;=&amp;#160;Value&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;module&amp;#160;Options&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Randomly&amp;#160;select&amp;#160;zero&amp;#160;or&amp;#160;more&amp;#160;elements&amp;#160;from&amp;#160;the&amp;#160;options&amp;#160;enumeration&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;Options.values.filter&amp;#160;{_&amp;#160;=&gt;&amp;#160;util.Random.nextBoolean}&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;",&amp;#160;"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;res2:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;TWO,&amp;#160;FOUR&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Select&amp;#160;a&amp;#160;random&amp;#160;string.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Warning:&amp;#160;&amp;#160;there&amp;#160;is&amp;#160;no&amp;#160;restriction&amp;#160;on&amp;#160;the&amp;#160;characters&amp;#160;so&amp;#160;control&amp;#160;characters&amp;#160;are&amp;#160;likely&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;util.Random.nextString(10)&lt;/li&gt;&lt;li class="codelist "&gt;res5:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;??????????&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;ASCII&amp;#160;string&amp;#160;is&amp;#160;oftern&amp;#160;more&amp;#160;useful&amp;#160;for&amp;#160;test&amp;#160;data.&amp;#160;&amp;#160;This&amp;#160;selects&amp;#160;a&amp;#160;random&amp;#160;string&amp;#160;up&amp;#160;to&amp;#160;13&amp;#160;characters&amp;#160;long&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;util.Random.nextASCIIString(13)&lt;/li&gt;&lt;li class="codelist "&gt;res6:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;RVPD\#_HqJ8:o&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;creates&amp;#160;a&amp;#160;sequence&amp;#160;of&amp;#160;10&amp;#160;random&amp;#160;strings&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;1&amp;#160;to&amp;#160;10&amp;#160;map&amp;#160;{_&amp;#160;=&gt;&amp;#160;util.Random.nextASCIIString(13)}&lt;/li&gt;&lt;li class="codelist "&gt;res7:&amp;#160;scala.collection.immutable.IndexedSeq&lt;span class="type-param"&gt;[java.lang.String]&lt;/span&gt;&amp;#160;=&amp;#160;IndexedSeq(;E8|Q8H8RI;Q=,&amp;#160;vM-X;&amp;quot;ksBr\:c,&amp;#160;SKyz{uXNQ5E]X,&amp;#160;=Jd8_ll08)s%e,&amp;#160;gRCs)6wj%C-YF,&amp;#160;`x;2Zru?l*c%&lt;span class="annotation"&gt;@&lt;/span&gt;,&amp;#160;XE*/Rx9:qPfpm,&amp;#160;s|u,e.un+-Xm(,&amp;#160;M,TpX9Dq-6$+^,&amp;#160;w;exER&amp;amp;#0|}Ya)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-3583867384533699630?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/3583867384533699630/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/lazy-mans-random-test-data.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/3583867384533699630'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/3583867384533699630'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/lazy-mans-random-test-data.html' title='Lazy man&apos;s random test data'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-8262717705496654013</id><published>2010-03-06T05:08:00.000-08:00</published><updated>2010-03-07T12:28:00.538-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='if'/><title type='text'>Blocks within if statements</title><content type='html'>his is another topic that examines the consistency of Scala.  This topic examines blocks in if statements.  It is related to &lt;a href="http://daily-scala.blogspot.com/2010/02/blocks-within-for-comprehensions.html"&gt;Blocks within for comprehensions&lt;/a&gt; and &lt;a href="http://daily-scala.blogspot.com/2010/02/temporary-variables-during-object.html"&gt;Temporary Variables during object creation&lt;/a&gt;.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;standard&amp;#160;if&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;if&lt;/span&gt;(1&amp;#160;&gt;&amp;#160;2)&amp;#160;-1&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;0&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;since&amp;#160;blocks&amp;#160;return&amp;#160;a&amp;#160;value&amp;#160;you&amp;#160;can&amp;#160;use&amp;#160;a&amp;#160;block&amp;#160;within&amp;#160;the&amp;#160;if&amp;#160;statement&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;(not&amp;#160;sure&amp;#160;when&amp;#160;you&amp;#160;would&amp;#160;want&amp;#160;to&amp;#160;but...)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;({&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;x&amp;#160;==&amp;#160;y&amp;#160;})&amp;#160;1&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;2&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-8262717705496654013?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/8262717705496654013/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/blocks-within-if-statements.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8262717705496654013'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8262717705496654013'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/blocks-within-if-statements.html' title='Blocks within if statements'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-6709833813281060248</id><published>2010-03-04T06:51:00.001-08:00</published><updated>2010-03-04T06:51:44.505-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='collections'/><category scheme='http://www.blogger.com/atom/ns#' term='stream'/><category scheme='http://www.blogger.com/atom/ns#' term='zip'/><title type='text'>Zip with a constant value</title><content type='html'>A simple tip for zipping a List (or other collection) with a single value.&lt;br /&gt; &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;Stream.continually(&lt;span class="string"&gt;"h"&lt;/span&gt;)&amp;#160;zip&amp;#160;List(1,2,3,4)&lt;/li&gt;&lt;li class="codelist "&gt;res2:&amp;#160;scala.collection.immutable.Stream&lt;span class="type-param"&gt;[(java.lang.String,&amp;#160;Int)]&lt;/span&gt;&amp;#160;=&amp;#160;Stream((h,1),&amp;#160;?)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;res2&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;","&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;res3:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;(h,1),(h,2),(h,3),(h,4)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;List(1,2,3,4)&amp;#160;zip&amp;#160;Stream.continually(&lt;span class="string"&gt;"h"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;res4:&amp;#160;List&lt;span class="type-param"&gt;[(Int,&amp;#160;java.lang.String)]&lt;/span&gt;&amp;#160;=&amp;#160;List((1,h),&amp;#160;(2,h),&amp;#160;(3,h),&amp;#160;(4,h))&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-6709833813281060248?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/6709833813281060248/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/zip-with-constant-value.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6709833813281060248'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6709833813281060248'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/zip-with-constant-value.html' title='Zip with a constant value'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-5835029022459095302</id><published>2010-03-03T04:46:00.001-08:00</published><updated>2010-03-03T04:47:04.473-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='function'/><category scheme='http://www.blogger.com/atom/ns#' term='case'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='partial-function'/><title type='text'>Functions using case statements</title><content type='html'>A further tip regarding using case statements to construct functions.  If a case statement is assigned to a Function it will construct a Function object not a PartialFunction.&lt;br /&gt; &lt;br /&gt;I suppose the question is why do you care about this since PartialFunction is a Function.  The fact is that a PartialFunction is a Function1.  But using a case statement you can construct a Function4 very easily.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;run(f&amp;#160;:&amp;#160;Function1&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;)&amp;#160;=&amp;#160;println(f.isInstanceOf&lt;span class="type-param"&gt;[PartialFunction&lt;/span&gt;&lt;span class="type-param"&gt;[_,_]&lt;/span&gt;])&lt;/li&gt;&lt;li class="codelist "&gt;run:&amp;#160;(f:&amp;#160;(Any)&amp;#160;=&gt;&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)Unit&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;since&amp;#160;run&amp;#160;expects&amp;#160;a&amp;#160;Function&amp;#160;calling&amp;#160;run&amp;#160;as&amp;#160;shown&amp;#160;here&amp;#160;will&amp;#160;make&amp;#160;a&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Function&amp;#160;object&amp;#160;not&amp;#160;a&amp;#160;PartialFunction&amp;#160;Object&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;run({&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;f&amp;#160;=&gt;&amp;#160;()})&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;pf(f&amp;#160;:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;)&amp;#160;=&amp;#160;println(f.isInstanceOf&lt;span class="type-param"&gt;[PartialFunction&lt;/span&gt;&lt;span class="type-param"&gt;[_,_]&lt;/span&gt;])&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;pf:&amp;#160;(f:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Now&amp;#160;a&amp;#160;PartialFunction&amp;#160;will&amp;#160;be&amp;#160;created&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf({&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;f&amp;#160;=&gt;&amp;#160;()})&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;run(f&amp;#160;:&amp;#160;Function2&lt;span class="type-param"&gt;[Int,String,Unit]&lt;/span&gt;)&amp;#160;=&amp;#160;f(1,&lt;span class="string"&gt;"2"&lt;/span&gt;)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;run:&amp;#160;(f:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;,&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)Unit&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;This&amp;#160;demonstrates&amp;#160;why&amp;#160;it&amp;#160;is&amp;#160;important&amp;#160;that&amp;#160;a&amp;#160;case&amp;#160;creates&amp;#160;a&amp;#160;Function&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;when&amp;#160;assigned&amp;#160;to&amp;#160;a&amp;#160;Function.&amp;#160;PartialFunctions&amp;#160;are&amp;#160;Function1&amp;#160;objects&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;but&amp;#160;the&amp;#160;following&amp;#160;statement&amp;#160;is&amp;#160;creating&amp;#160;a&amp;#160;Function2&amp;#160;object.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;run({&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(1,b)&amp;#160;=&gt;&amp;#160;println(b)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;(a,b)&amp;#160;=&gt;&amp;#160;println(a,b)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;})&lt;/li&gt;&lt;li class="codelist "&gt;2&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-5835029022459095302?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/5835029022459095302/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/functions-using-case-statements.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5835029022459095302'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5835029022459095302'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/functions-using-case-statements.html' title='Functions using case statements'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-3115670497926052319</id><published>2010-03-02T00:04:00.000-08:00</published><updated>2010-03-02T00:09:17.987-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='case'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='partial-function'/><title type='text'>Methods on PartialFunction</title><content type='html'>This topic inspects the methods defined in the PartialFunction Object.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;PF&amp;#160;=&amp;#160;PartialFunction&lt;span class="type-param"&gt;[Int,Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;alias&amp;#160;PF&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;the&amp;#160;two&amp;#160;partial&amp;#160;functions&amp;#160;that&amp;#160;we&amp;#160;will&amp;#160;use&amp;#160;for&amp;#160;the&amp;#160;examples&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;pf1&amp;#160;:&amp;#160;PF&amp;#160;=&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;1&amp;#160;=&gt;&amp;#160;2}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;pf1:&amp;#160;PF&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;pf2&amp;#160;:&amp;#160;PF&amp;#160;=&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;2&amp;#160;=&gt;&amp;#160;3}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;pf2:&amp;#160;PF&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;As&amp;#160;is&amp;#160;well&amp;#160;known,&amp;#160;when&amp;#160;a&amp;#160;PartialFunction&amp;#160;is&amp;#160;called&amp;#160;with&amp;#160;a&amp;#160;value&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;it&amp;#160;must&amp;#160;be&amp;#160;defined&amp;#160;at&amp;#160;that&amp;#160;value&amp;#160;or&amp;#160;bad&amp;#160;things&amp;#160;will&amp;#160;happen&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1&amp;#160;isDefinedAt&amp;#160;1&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res14:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1&amp;#160;isDefinedAt&amp;#160;2&lt;/li&gt;&lt;li class="codelist alt"&gt;res15:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1(2)&lt;/li&gt;&lt;li class="codelist "&gt;scala.MatchError:&amp;#160;2&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;$anonfun$1.&lt;span class="magic"&gt;apply&lt;/span&gt;(&amp;lt;&amp;#160;console&gt;:5)&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;$anonfun$1.&lt;span class="magic"&gt;apply&lt;/span&gt;(&amp;lt;&amp;#160;console&gt;:5)&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;.&amp;lt;&amp;#160;init&gt;(&amp;lt;&amp;#160;console&gt;:7)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;...&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1(1)&lt;/li&gt;&lt;li class="codelist "&gt;res5:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;It&amp;#160;is&amp;#160;possible&amp;#160;to&amp;#160;compose&amp;#160;two&amp;#160;partial&amp;#160;functions&amp;#160;so&amp;#160;first&amp;#160;one&amp;#160;partialFunction&amp;#160;is&amp;#160;called&amp;#160;and&amp;#160;then&amp;#160;the&amp;#160;next&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;andThen&amp;#160;pf2)&amp;#160;isDefinedAt&amp;#160;2&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res16:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;andThen&amp;#160;pf2)&amp;#160;isDefinedAt&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;res17:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;andThen&amp;#160;pf2)(2)&lt;/li&gt;&lt;li class="codelist "&gt;scala.MatchError:&amp;#160;2&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;$anonfun$1.&lt;span class="magic"&gt;apply&lt;/span&gt;(&amp;lt;&amp;#160;console&gt;:5)&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;$anonfun$1.&lt;span class="magic"&gt;apply&lt;/span&gt;(&amp;lt;&amp;#160;console&gt;:5)&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;scala.PartialFunction$$anon$2.&lt;span class="magic"&gt;apply&lt;/span&gt;(PartialFunction.scala:59)&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;.&amp;lt;&amp;#160;init&gt;(&amp;lt;&amp;#160;console&gt;:8)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;...&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;andThen&amp;#160;pf2)(1)&lt;/li&gt;&lt;li class="codelist alt"&gt;res8:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;3&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;An&amp;#160;alternative&amp;#160;way&amp;#160;of&amp;#160;combining&amp;#160;PartialFunctions&amp;#160;is&amp;#160;to&amp;#160;'or'&amp;#160;them&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;orElse&amp;#160;pf2)&amp;#160;isDefinedAt&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;res18:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;orElse&amp;#160;pf2)&amp;#160;isDefinedAt&amp;#160;2&lt;/li&gt;&lt;li class="codelist "&gt;res19:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;orElse&amp;#160;pf2)&amp;#160;isDefinedAt&amp;#160;3&lt;/li&gt;&lt;li class="codelist alt"&gt;res20:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;orElse&amp;#160;pf2)(1)&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res9:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;2&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(pf1&amp;#160;orElse&amp;#160;pf2)(2)&lt;/li&gt;&lt;li class="codelist alt"&gt;res10:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;3&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Finally&amp;#160;a&amp;#160;PartialFunction&amp;#160;can&amp;#160;be&amp;#160;easily&amp;#160;converted&amp;#160;to&amp;#160;a&amp;#160;function&amp;#160;that&amp;#160;returns&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;an&amp;#160;Option&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1.lift&lt;/li&gt;&lt;li class="codelist "&gt;res21:&amp;#160;(&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1.lift(1)&lt;/li&gt;&lt;li class="codelist alt"&gt;res11:&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;Some(2)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;pf1.lift(2)&lt;/li&gt;&lt;li class="codelist "&gt;res12:&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;None&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-3115670497926052319?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/3115670497926052319/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/methods-on-partialfunction.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/3115670497926052319'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/3115670497926052319'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/methods-on-partialfunction.html' title='Methods on PartialFunction'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-8237131244139868493</id><published>2010-03-01T00:15:00.000-08:00</published><updated>2010-03-01T02:46:50.080-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='inheritance'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='linearization'/><category scheme='http://www.blogger.com/atom/ns#' term='with'/><category scheme='http://www.blogger.com/atom/ns#' term='traits'/><title type='text'>NullPointer when mixed traits (Warning)</title><content type='html'>This tip is mainly to document a 'GOTCHA' that I got caught by recently.  It basically goes like this:&lt;br /&gt;&lt;bq&gt;&lt;br /&gt;Trait Y extends(or has self-type) X. Trait X defines some abstract method 'm'.  The initialization code in Y accesses 'm'.  Creation of an object new X with Y results in: *Boom* NullPointerException (on object creation).&lt;br /&gt;&lt;/bq&gt;&lt;br /&gt;The example in code:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;{&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;X&amp;#160;=&gt;&amp;#160;;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist "&gt;java.lang.NullPointerException&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;Y$class.$init$(&amp;lt;&amp;#160;console&gt;:5)&lt;/li&gt;&lt;li class="codelist "&gt; at&amp;#160;$anon$1.&amp;lt;&amp;#160;init&gt;(&amp;lt;&amp;#160;console&gt;:7)&lt;/li&gt;&lt;li class="codelist alt"&gt; ...&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;At a glance it seems that x should override the abstract value x in trait X.  However the order in which traits are declared is important.  In this case first Y is configured then X.  Since X is not yet configured Y throws an exception.  There are several ways to work around this.&lt;br /&gt;Option 1:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;{&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;X&amp;#160;=&gt;&amp;#160;;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Declaring&amp;#160;Y&amp;#160;with&amp;#160;X&amp;#160;will&amp;#160;work&amp;#160;because&amp;#160;Y&amp;#160;is&amp;#160;initialized&amp;#160;after&amp;#160;X&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;but&amp;#160;remember&amp;#160;that&amp;#160;there&amp;#160;may&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;be&amp;#160;other&amp;#160;reasons&amp;#160;that&amp;#160;X&amp;#160;with&amp;#160;Y&amp;#160;is&amp;#160;required.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Method&amp;#160;resolution&amp;#160;is&amp;#160;one&amp;#160;such&amp;#160;reason&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Option 2:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;{&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;X&amp;#160;=&gt;&amp;#160;;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Since&amp;#160;method&amp;#160;y&amp;#160;is&amp;#160;a&amp;#160;'def'&amp;#160;x.getName&amp;#160;will&amp;#160;not&amp;#160;be&amp;#160;executed&amp;#160;during&amp;#160;initialization.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist alt"&gt;res10:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;=&amp;#160;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;7cb9e9a3&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Option 3:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;{&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;X&amp;#160;=&gt;&amp;#160;;&amp;#160;&lt;span class="key"&gt;lazy&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;'lazy&amp;#160;val'&amp;#160;works&amp;#160;for&amp;#160;the&amp;#160;same&amp;#160;reason&amp;#160;'def'&amp;#160;works:&amp;#160;x.getName&amp;#160;is&amp;#160;not&amp;#160;invoked&amp;#160;during&amp;#160;initialization&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist alt"&gt;res10:&amp;#160;java.lang.Object&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;=&amp;#160;$anon$1&lt;span class="annotation"&gt;@&lt;/span&gt;7cb9e9a3&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Option 4:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;X&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;if&amp;#160;Y&amp;#160;extends&amp;#160;X&amp;#160;then&amp;#160;a&amp;#160;new&amp;#160;Y&amp;#160;can&amp;#160;be&amp;#160;instantiated&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y&amp;#160;{&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Two more warnings.  First, the same error will occur whether 'x' is a def or a val or a var.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File&amp;#160;}&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;{&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;X&amp;#160;=&gt;&amp;#160;;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Second warning: In complex domain models it is easy to have a case where Y extends X but the final object is created as: new X with Y{...}. &lt;br /&gt;&lt;br /&gt;You will get the same error here because (I think) the compiler recognized that Y is being mixed in with X and therefore the X will be initialized as after Y instead of before Y.  &lt;br /&gt;&lt;br /&gt;First the code:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;java.io.File&amp;#160;}&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Y&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;X&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;y&amp;#160;=&amp;#160;x.getName}&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;Y&amp;#160;{&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.File(&lt;span class="string"&gt;"hi"&lt;/span&gt;)}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;If the code instantiated new Y{...} the initialization would be X then Y.  Because X can only be initialized once, the explicit declaration of new X with Y forces Y to be initialized before X.  (X can only be initialized once even when it appears twice in the hierarchy). &lt;br /&gt;&lt;br /&gt;This is a topic called linearization and will be addressed in the future.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-8237131244139868493?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/8237131244139868493/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/03/nullpointer-when-mixed-traits-warning.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8237131244139868493'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/8237131244139868493'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/03/nullpointer-when-mixed-traits-warning.html' title='NullPointer when mixed traits (Warning)'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-1309473104514981484</id><published>2010-02-22T04:00:00.001-08:00</published><updated>2010-02-22T23:54:42.210-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='case'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='partial-function'/><title type='text'>Methods of PartialFunction object</title><content type='html'>This topic looks at the functionality provide in the object PartialFunction.&lt;br /&gt;&lt;br /&gt;This example uses Scala 2.8 which I believe is required.&lt;br /&gt;&lt;br /&gt;Only two methods are focused on.  PartialFunction.cond and PartialFunction.condOpt.&lt;br /&gt;As per request the signature for said methods are:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;cond&lt;span class="type-param"&gt;[T]&lt;/span&gt;(x:&amp;#160;T)(pf:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[T,&amp;#160;Boolean]&lt;/span&gt;):&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;condOpt&lt;span class="type-param"&gt;[T,&amp;#160;U]&lt;/span&gt;(x:&amp;#160;T)(pf:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[T,&amp;#160;U]&lt;/span&gt;):&amp;#160;Option&lt;span class="type-param"&gt;[U]&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Now for some examples:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;PartialFunction._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;PartialFunction._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;strangeConditional(other:&amp;#160;Any):&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;cond(other)&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;x&amp;#160;==&amp;#160;&lt;span class="string"&gt;"abc"&lt;/span&gt;&amp;#160;||&amp;#160;x&amp;#160;==&amp;#160;&lt;span class="string"&gt;"def"&lt;/span&gt;&amp;#160;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;strangeConditional:&amp;#160;(other:&amp;#160;Any)&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;strangeConditional(&lt;span class="string"&gt;"abc"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;res0:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;strangeConditional(&lt;span class="string"&gt;"hello"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;res1:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;false&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;strangeConditional(3)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res2:&amp;#160;&lt;span class="basicType"&gt;Boolean&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="basicType"&gt;true&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;onlyInt(v:&amp;#160;Any):&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;condOpt(v)&amp;#160;{&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;x&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;onlyInt:&amp;#160;(v:&amp;#160;Any)Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;onlyInt(&lt;span class="string"&gt;"hi"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;res3:&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;None&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;onlyInt(3)&lt;/li&gt;&lt;li class="codelist "&gt;res4:&amp;#160;Option&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;Some(3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;util.control.Exception.catching&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;util.control.Exception.catching&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;IntNum&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;number&amp;#160;=&amp;#160;catching(classOf&lt;span class="type-param"&gt;[NumberFormatException]&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;unapply&lt;/span&gt;(x&amp;#160;:&amp;#160;Any)&amp;#160;=&amp;#160;condOpt(x)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;x&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;y&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;number.opt(y.toInt).isDefined&amp;#160;=&gt;&amp;#160;y.toInt&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;module&amp;#160;IntNum&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;1&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;IntNum(x)&amp;#160;=&gt;&amp;#160;println(x+&lt;span class="string"&gt;"&amp;#160;i&amp;#160;win!"&lt;/span&gt;)}&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;1&amp;#160;i&amp;#160;win!&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;3&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;IntNum(x)&amp;#160;=&gt;&amp;#160;println(x+&lt;span class="string"&gt;"&amp;#160;i&amp;#160;win!"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist "&gt;3&amp;#160;i&amp;#160;win!&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-1309473104514981484?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/1309473104514981484/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/methods-of-partialfunction-object.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1309473104514981484'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/1309473104514981484'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/methods-of-partialfunction-object.html' title='Methods of PartialFunction object'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-2212287976509080392</id><published>2010-02-19T02:03:00.000-08:00</published><updated>2010-02-19T02:04:22.198-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='type alias'/><category scheme='http://www.blogger.com/atom/ns#' term='partial-function'/><title type='text'>=&gt;? type alias for PartialFunction</title><content type='html'>A big thanks to &lt;a href="http://scalide.blogspot.com/"&gt;Ben Jackman&lt;/a&gt; for this tip.  &lt;br /&gt;&lt;br /&gt;His tip cleans up the examples in post &lt;a href="http://daily-scala.blogspot.com/2010/02/chaining-partial-functions-with-orelse.html"&gt;Chaining Partial Functions with orElse&lt;/a&gt;&lt;br /&gt;The secret is to define the type alias &lt;code&gt;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;=&gt;?&lt;span class="type-param"&gt;[-A,&amp;#160;+B]&lt;/span&gt;&amp;#160;=&amp;#160;PartialFunction&lt;span class="type-param"&gt;[A,&amp;#160;B]&lt;/span&gt;&lt;/code&gt;.  This alias may be added to Predef in the future but until it is you can add it yourself.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;=&gt;?&lt;span class="type-param"&gt;[-A,&amp;#160;+B]&lt;/span&gt;&amp;#160;=&amp;#160;PartialFunction&lt;span class="type-param"&gt;[A,&amp;#160;B]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;alias&amp;#160;$eq$greater$qmark&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;i&amp;#160;:&amp;#160;(Any&amp;#160;=&gt;?&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)&amp;#160;=&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"int&amp;#160;found"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist alt"&gt;i:&amp;#160;=&gt;?&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;j&amp;#160;:&amp;#160;(Any&amp;#160;=&gt;?&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)&amp;#160;=&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&lt;span class="basicType"&gt;Double&lt;/span&gt;&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"Double&amp;#160;found"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist "&gt;j:&amp;#160;=&gt;?&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;*&amp;#160;:&amp;#160;(Any&amp;#160;=&gt;?&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)&amp;#160;=&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x=&gt;&amp;#160;println(&lt;span class="string"&gt;"Something&amp;#160;else&amp;#160;found"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist alt"&gt;*:&amp;#160;=&gt;?&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(1)&lt;/li&gt;&lt;li class="codelist "&gt;int&amp;#160;found&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(1.0)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="basicType"&gt;Double&lt;/span&gt;&amp;#160;found&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(&lt;span class="basicType"&gt;true&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;Something&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;found&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;=&gt;?&lt;span class="type-param"&gt;[A,&amp;#160;B]&lt;/span&gt;(id&amp;#160;:&amp;#160;A&amp;#160;=&gt;?&amp;#160;B)&amp;#160;=&amp;#160;id&lt;/li&gt;&lt;li class="codelist alt"&gt;$eq$greater$qmark:&amp;#160;&lt;span class="type-param"&gt;[A,B]&lt;/span&gt;(id:&amp;#160;=&gt;?&lt;span class="type-param"&gt;[A,B]&lt;/span&gt;)=&gt;?&lt;span class="type-param"&gt;[A,B]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(&amp;#160;=&gt;?&lt;span class="type-param"&gt;[Any,&amp;#160;Unit]&lt;/span&gt;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;s&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"String&amp;#160;found"&lt;/span&gt;)}&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(&lt;span class="string"&gt;"hello"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;found&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-2212287976509080392?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/2212287976509080392/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/type-alias-for-partialfunction.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/2212287976509080392'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/2212287976509080392'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/type-alias-for-partialfunction.html' title='=&gt;? type alias for PartialFunction'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-732760553178336515</id><published>2010-02-18T00:42:00.001-08:00</published><updated>2010-02-18T01:34:15.626-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='partial-function'/><category scheme='http://www.blogger.com/atom/ns#' term='match'/><category scheme='http://www.blogger.com/atom/ns#' term='matching'/><title type='text'>Chaining Partial Functions with orElse</title><content type='html'>PartialFunctions are extremely valuable  Scala constructs that are used in many APIs. Commonly you will encounter the pattern:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;obj&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;&lt;span class="string"&gt;"Val"&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;do&amp;#160;something&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;handle&amp;#160;all&amp;#160;other&amp;#160;cases&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;It is intuitive and obvious how to share the code of the right hand side if the case statement by factoring that code out to a method. But would it not be useful to be able to factor out an entire case statement (PartialFunction) and later chain them together as needed?&lt;br /&gt;&lt;br /&gt;This is indeed possible and very easy to do:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;We&amp;#160;need&amp;#160;to&amp;#160;declare&amp;#160;Partial&amp;#160;Functions&amp;#160;so&amp;#160;to&amp;#160;add&amp;#160;brevity&amp;#160;I&amp;#160;am&amp;#160;adding&amp;#160;this&amp;#160;alias&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.{PartialFunction&amp;#160;=&gt;&amp;#160;PF}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.{PartialFunction=&gt;PF}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;You&amp;#160;have&amp;#160;to&amp;#160;explicitly&amp;#160;declare&amp;#160;the&amp;#160;type&amp;#160;because&amp;#160;the&amp;#160;type&amp;#160;inferencer&amp;#160;cannot&amp;#160;know&amp;#160;what&amp;#160;type&amp;#160;of&amp;#160;PartialFunction&amp;#160;to&amp;#160;create&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;A&amp;#160;PartialFunction&amp;#160;is&amp;#160;Strictly&amp;#160;type&amp;#160;so&amp;#160;some&amp;#160;functions&amp;#160;can&amp;#160;only&amp;#160;be&amp;#160;used&amp;#160;on&amp;#160;Ints&amp;#160;for&amp;#160;example&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;i&amp;#160;:&amp;#160;PF&lt;span class="type-param"&gt;[Any,&amp;#160;Unit]&lt;/span&gt;&amp;#160;=&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"int&amp;#160;found"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist alt"&gt;i:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;j&amp;#160;:&amp;#160;PF&lt;span class="type-param"&gt;[Any,&amp;#160;Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x:&lt;span class="basicType"&gt;Double&lt;/span&gt;&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"Double&amp;#160;found"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist "&gt;j:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;*&amp;#160;:&amp;#160;PF&lt;span class="type-param"&gt;[Any,&amp;#160;Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;x=&gt;&amp;#160;println(&lt;span class="string"&gt;"Something&amp;#160;else&amp;#160;found"&lt;/span&gt;)}&lt;/li&gt;&lt;li class="codelist alt"&gt;*:&amp;#160;PartialFunction&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;one&amp;#160;might&amp;#160;think&amp;#160;that&amp;#160;you&amp;#160;can&amp;#160;do:&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;1&amp;#160;match&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;but&amp;#160;in&amp;#160;fact&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)&amp;#160;forms&amp;#160;a&amp;#160;PartialFunction&amp;#160;not&amp;#160;a&amp;#160;pattern&amp;#160;so&amp;#160;cannot&amp;#160;be&amp;#160;used&amp;#160;with&amp;#160;match.&amp;#160;&amp;#160;Instead&amp;#160;it&amp;#160;must&amp;#160;be&amp;#160;used&amp;#160;as&amp;#160;a&amp;#160;function&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(1)&lt;/li&gt;&lt;li class="codelist "&gt;int&amp;#160;found&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(1.0)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="basicType"&gt;Double&lt;/span&gt;&amp;#160;found&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(i&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(&lt;span class="basicType"&gt;true&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;Something&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;found&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;for&amp;#160;specific&amp;#160;cases&amp;#160;it&amp;#160;is&amp;#160;possible&amp;#160;to&amp;#160;chain&amp;#160;the&amp;#160;an&amp;#160;anonymous&amp;#160;partial&amp;#160;function&amp;#160;with&amp;#160;the&amp;#160;common&amp;#160;function&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;is&amp;#160;not&amp;#160;so&amp;#160;nice&amp;#160;so&amp;#160;it&amp;#160;is&amp;#160;probably&amp;#160;best&amp;#160;to&amp;#160;declare&amp;#160;a&amp;#160;val&amp;#160;instead&amp;#160;of&amp;#160;inline&amp;#160;like&amp;#160;this&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;(({&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;s:&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"String&amp;#160;found"&lt;/span&gt;)}:PF&lt;span class="type-param"&gt;[Any,Unit]&lt;/span&gt;)&amp;#160;orElse&amp;#160;j&amp;#160;orElse&amp;#160;*)(&lt;span class="string"&gt;"hello"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;found&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;For another example of chaining PartialFunctions the Akka tutorial has a good example in the ChatServer trait: &lt;a href="http://jonasboner.com/2010/01/04/introducing-akka.html"&gt;http://jonasboner.com/2010/01/04/introducing-akka.html&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-732760553178336515?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/732760553178336515/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/chaining-partial-functions-with-orelse.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/732760553178336515'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/732760553178336515'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/chaining-partial-functions-with-orelse.html' title='Chaining Partial Functions with orElse'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-605381364791984934</id><published>2010-02-16T01:03:00.001-08:00</published><updated>2010-02-16T01:03:39.123-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='match'/><category scheme='http://www.blogger.com/atom/ns#' term='extractor'/><category scheme='http://www.blogger.com/atom/ns#' term='matching'/><title type='text'>And Case Statements</title><content type='html'>Recently I encountered a good question on Stack Overflow about matching.&lt;br /&gt;&lt;a href="http://stackoverflow.com/questions/2261358/pattern-matching-with-conjunctions-patterna-and-patternb"&gt;http://stackoverflow.com/questions/2261358/pattern-matching-with-conjunctions-patterna-and-patternb&lt;/a&gt;.  &lt;br /&gt;&lt;br /&gt;As mentioned in an earlier post &lt;a href="http://daily-scala.blogspot.com/2010/01/matching-with-or.html"&gt;Matching with Or&lt;/a&gt; case expressions suppose 'or' expression combination using the '|' character.  However 'and' combinations are not possible.&lt;br /&gt;&lt;br /&gt;One solution is to build an &amp;amp;&amp;amp; extractor object as follows:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;&amp;amp;&amp;amp;&amp;#160;{&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;unapply&lt;/span&gt;&lt;span class="type-param"&gt;[A]&lt;/span&gt;(a:&amp;#160;A)&amp;#160;=&amp;#160;Some((a,&amp;#160;a))}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;module&amp;#160;$amp$amp&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;StartsWith&amp;#160;{&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;unapply&lt;/span&gt;(s:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;=&amp;#160;s.headOption}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;module&amp;#160;StartsWith&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;EndsWith&amp;#160;{&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;unapply&lt;/span&gt;(s:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;=&amp;#160;s.reverse.headOption}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;module&amp;#160;EndsWith&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="string"&gt;"foo"&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;StartsWith(&lt;span class="char"&gt;'f'&lt;/span&gt;)&amp;#160;&amp;amp;&amp;amp;&amp;#160;EndsWith(&lt;span class="char"&gt;'o'&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;println(&lt;span class="string"&gt;"f*o"&lt;/span&gt;)&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;f*o&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Note: this is a scala 2.7 solution Scala 2.8 can be used to improve the EndsWith extractor by using the method lastOption instead of s.reverse.headOption.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-605381364791984934?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/605381364791984934/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/and-case-statements.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/605381364791984934'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/605381364791984934'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/and-case-statements.html' title='And Case Statements'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-5345455631780153998</id><published>2010-02-15T04:09:00.000-08:00</published><updated>2010-02-15T04:14:49.528-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='self-annotation'/><category scheme='http://www.blogger.com/atom/ns#' term='inheritance'/><category scheme='http://www.blogger.com/atom/ns#' term='Advanced'/><category scheme='http://www.blogger.com/atom/ns#' term='self-type'/><title type='text'>Self Annotation vs inheritance</title><content type='html'>At first glance the "sself annotation" declaration seems similar to extending another class.  (For a look at self annotations read the topic: &lt;a href="http://daily-scala.blogspot.com/search/label/self-type"&gt;Self Type&lt;/a&gt;.)  They are completely different but the comparison is understandable since both of them provide access to the functionality of referenced class.  &lt;br /&gt;&lt;br /&gt;For example both of the following compile:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Base&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;magic&amp;#160;=&amp;#160;&lt;span class="string"&gt;"bibbity&amp;#160;bobbity&amp;#160;boo!!"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Extender&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Base&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;myMethod&amp;#160;=&amp;#160;&lt;span class="string"&gt;"I&amp;#160;can&amp;#160;"&lt;/span&gt;+magic&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;SelfTyper&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;Base&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;myMethod&amp;#160;=&amp;#160;&lt;span class="string"&gt;"I&amp;#160;can&amp;#160;"&lt;/span&gt;+magic&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;But the two are completely different.  Extender can be mixed in with any class and adds both the "magic" and "myMethod" to the class it is mixed with.  SelfType can only be mixed in with a class that extends Base and SelfTyper only adds the method "myMethod" NOT "magic".  &lt;br /&gt;&lt;br /&gt;Why is the "self annotations" useful?  Because it allows several provides a way of declaring dependencies.  One can think of the self annotation declaration as the phrase "I am useable with" or "I require a".&lt;br /&gt;&lt;br /&gt;The following example demonstrates one possible reason to use self annotations instead of extend. &lt;br /&gt;&lt;br /&gt;Note: These examples can be pasted into the REPL but I have shown that here because it would make the examples too long.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.io._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.util.{Properties&amp;#160;=&gt;&amp;#160;JProps}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;Properties&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;apply&lt;/span&gt;(key:&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;XmlProperties&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Properties&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;scala.xml._&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;xml(key:&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;=&amp;#160;Elem(&lt;span class="singleton"&gt;null&lt;/span&gt;,key,&lt;span class="singleton"&gt;Null&lt;/span&gt;,TopScope,&amp;#160;Text(&lt;span class="magic"&gt;apply&lt;/span&gt;(key)))&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;JSonProperties&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Properties&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;json(key:&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;span class="string"&gt;"%s&amp;#160;:&amp;#160;%s"&lt;/span&gt;.format(key,&amp;#160;&lt;span class="magic"&gt;apply&lt;/span&gt;(key))&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;StreamProperties&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;Properties&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;protected&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;:&amp;#160;InputStream&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;private&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;props&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;JProps()&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;props.load(source)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;apply&lt;/span&gt;(key:&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;=&amp;#160;props.get(key).asInstanceOf&lt;span class="type-param"&gt;[String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;MapProperties&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;Properties&amp;#160;=&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;protected&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;:&amp;#160;Map&lt;span class="type-param"&gt;[String,String]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;apply&lt;/span&gt;(key:&lt;span class="basicType"&gt;String&lt;/span&gt;)&amp;#160;=&amp;#160;source.&lt;span class="magic"&gt;apply&lt;/span&gt;(key)&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;sampleMap&amp;#160;=&amp;#160;Map(&lt;span class="string"&gt;"1"&lt;/span&gt;&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"one"&lt;/span&gt;,&amp;#160;&lt;span class="string"&gt;"2"&lt;/span&gt;&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"two"&lt;/span&gt;,&amp;#160;&lt;span class="string"&gt;"3"&lt;/span&gt;&amp;#160;-&gt;&amp;#160;&lt;span class="string"&gt;"three"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;sampleData&amp;#160;=&amp;#160;&lt;span class="string"&gt;"""1=one&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="string"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;2=two&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="string"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;3=three"""&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;sXml&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;XmlProperties()&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;StreamProperties{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;ByteArrayInputStream(sampleData.getBytes)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;mXml&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;XmlProperties()&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;MapProperties{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;=&amp;#160;sampleMap&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;sJSon&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;JSonProperties()&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;StreamProperties{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;ByteArrayInputStream(sampleData.getBytes)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;mJSon&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;JSonProperties()&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;MapProperties{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;=&amp;#160;sampleMap&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;sXml.xml(&lt;span class="string"&gt;"1"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;mXml.xml(&lt;span class="string"&gt;"2"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;sJSon.json(&lt;span class="string"&gt;"1"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;mJSon.json(&lt;span class="string"&gt;"2"&lt;/span&gt;)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;The justification for using self annotations here is flexibility.  A couple other solutions would be &lt;br /&gt;&lt;ol&gt;&lt;li&gt;Use subclassing - this is poor solution because there would be an explosion of classes.  Instead of having 5 traits you would need 7 traits.  Properties, XmlProperties, JSonProperties, XmlStreamProperties, XmlMapProperties, JsonStreamProperties and JsonMapProperties.  And if you later wanted to add a new type of properties or a new source like reading from a database then you need 2 new subclasses.&lt;/li&gt;&lt;li&gt;Composition - Another strategy is to use construct the XmlProperties with a strategy that reads from the source.  This is essentially the same mechanism except that you need to build and maintain the the dependencies.  It also makes layering more difficult.  For example:&lt;br /&gt;  &lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;trait&lt;/span&gt;&amp;#160;IterableXmlProperties&amp;#160;{&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;self&lt;/span&gt;&amp;#160;:&amp;#160;MapProperties&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;XmlProperties&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;xmlIterable&amp;#160;=&amp;#160;source.keySet&amp;#160;map&amp;#160;{xml&amp;#160;_}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;XmlProperties&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;MapProperties&amp;#160;&lt;span class="key"&gt;with&lt;/span&gt;&amp;#160;IterableXmlProperties&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;source&amp;#160;=&amp;#160;sampleMap}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;/li&gt;&lt;/ol&gt;&lt;br /&gt;The next question that comes to mind is why use extends then if self annotation is so flexible?  My answer (and I welcome discussion on this point) has three points.  &lt;br /&gt;&lt;ol&gt;&lt;li&gt;The first is of semantics and modeling.  When designing a model it is often more logical to use inheritance because of the semantics that comes with inheriting from another object.&lt;/li&gt;&lt;li&gt;Another argument is pragmatism.  &lt;br /&gt;Imagine the collections library where there is no inheritance.  If you wanted a map with Iterable functionality you would have to always declare Traversable with Iterable with Map (and this is greatly simplified).  That declaration would have to be used for virtually all methods that require both the Iterable and Map functionality.  To say that is impractical is an understatement.  Also the semantics of Map is changed from what it is now.  The trait Map currently includes the concept of Iterable.&lt;/li&gt;&lt;li&gt;The last point is sealed traits/classes.  When a trait is "sealed" all of its subclasses are declared within the same file and that makes the set of subclasses finite which allows certain compiler checks.  This (as far as I know) cannot be done with self annotations.&lt;/li&gt;&lt;/ol&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-5345455631780153998?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/5345455631780153998/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/self-annotation-vs-inheritance.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5345455631780153998'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5345455631780153998'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/self-annotation-vs-inheritance.html' title='Self Annotation vs inheritance'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-6842790659544848575</id><published>2010-02-12T04:07:00.001-08:00</published><updated>2010-02-14T23:38:11.136-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='context'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='specs'/><category scheme='http://www.blogger.com/atom/ns#' term='test'/><category scheme='http://www.blogger.com/atom/ns#' term='fixture'/><title type='text'>Specs and Fixtures/Contexts</title><content type='html'>This topic revisits the &lt;a href="http://code.google.com/p/specs/"&gt;Specs BDD testing library.&lt;/a&gt;  It is a continuation of the previous post &lt;a href="http://daily-scala.blogspot.com/2009/12/specs-bdd-testing-framework.html"&gt;Specs BDD Testing Framework&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;This topic will look at how to setup fixtures in Specs.  This is only a sample to give a feeling of Specs a much more complete guide is available on the Specs website.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;jeichar:&amp;#160;git-src$&amp;#160;scala&amp;#160;-classpath&amp;#160;~/.m2/repository/org/scala-tools/testing/specs/1.6.1/specs-1.6.1.jar&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.specs._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.specs._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;example&amp;#160;demonstrates&amp;#160;before&amp;#160;and&amp;#160;after&amp;#160;actions&amp;#160;similar&amp;#160;to&amp;#160;what&amp;#160;is&amp;#160;found&amp;#160;in&amp;#160;XUnit.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;mySpec&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Specification&amp;#160;{&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="string"&gt;"my&amp;#160;system"&lt;/span&gt;&amp;#160;should&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;doFirst{println(&lt;span class="string"&gt;"before"&lt;/span&gt;)}&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;ran&amp;#160;once&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;doBefore{println(&lt;span class="string"&gt;"before"&lt;/span&gt;)}&amp;#160;&lt;span class="comment"&gt;//&amp;#160;ran&amp;#160;for&amp;#160;each&amp;#160;test&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;doAfter{println(&lt;span class="string"&gt;"after"&lt;/span&gt;)}&amp;#160;&lt;span class="comment"&gt;//&amp;#160;ran&amp;#160;for&amp;#160;each&amp;#160;test&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="string"&gt;"test&amp;#160;spec&amp;#160;1"&lt;/span&gt;&amp;#160;in&amp;#160;{&amp;#160;println(&lt;span class="string"&gt;"test1"&lt;/span&gt;);&amp;#160;1&amp;#160;must_==&amp;#160;1}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="string"&gt;"test&amp;#160;spec&amp;#160;2"&lt;/span&gt;&amp;#160;in&amp;#160;{&amp;#160;println(&lt;span class="string"&gt;"test2"&lt;/span&gt;);&amp;#160;1&amp;#160;must_==&amp;#160;2}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;doLast{println(&lt;span class="string"&gt;"last"&lt;/span&gt;)}&amp;#160;&lt;span class="comment"&gt;//&amp;#160;ran&amp;#160;once&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;module&amp;#160;mySpec&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;mySpec.main(Array())&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;Specification&amp;#160;&lt;span class="string"&gt;"mySpec"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;my&amp;#160;system&amp;#160;should&lt;/li&gt;&lt;li class="codelist "&gt;before&lt;/li&gt;&lt;li class="codelist alt"&gt;before&lt;/li&gt;&lt;li class="codelist "&gt;test1&lt;/li&gt;&lt;li class="codelist alt"&gt;after&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;+&amp;#160;test&amp;#160;spec&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;before&lt;/li&gt;&lt;li class="codelist "&gt;test2&lt;/li&gt;&lt;li class="codelist alt"&gt;after&lt;/li&gt;&lt;li class="codelist "&gt;last&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;x&amp;#160;test&amp;#160;spec&amp;#160;2&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="char"&gt;'1'&lt;/span&gt;&amp;#160;is&amp;#160;not&amp;#160;equal&amp;#160;to&amp;#160;&lt;span class="char"&gt;'2'&lt;/span&gt;&amp;#160;(&amp;lt;&amp;#160;console&gt;:14)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;Total&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;specification&amp;#160;&lt;span class="string"&gt;"mySpec"&lt;/span&gt;:&lt;/li&gt;&lt;li class="codelist alt"&gt;Finished&amp;#160;in&amp;#160;0&amp;#160;second,&amp;#160;307&amp;#160;ms&lt;/li&gt;&lt;li class="codelist "&gt;2&amp;#160;examples,&amp;#160;2&amp;#160;expectations,&amp;#160;1&amp;#160;failure,&amp;#160;0&amp;#160;error&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Example using Contexts there many more examples at: &lt;a href="http://code.google.com/p/specs/wiki/DeclareSpecifications#Shared_contexts"&gt;Shared contexts&lt;/a&gt;&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.specs._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;org.specs._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;specification&amp;#160;uses&amp;#160;contexts&amp;#160;instead&amp;#160;of&amp;#160;before&amp;#160;and&amp;#160;after&amp;#160;actions.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;My&amp;#160;personal&amp;#160;preference&amp;#160;is&amp;#160;to&amp;#160;use&amp;#160;contexts&amp;#160;because&amp;#160;they&amp;#160;are&amp;#160;more&amp;#160;flexible&amp;#160;and&amp;#160;can&amp;#160;have&amp;#160;names&amp;#160;associated&amp;#160;with&amp;#160;them.&amp;#160;&amp;#160;In&amp;#160;addition&amp;#160;contexts&amp;#160;can&amp;#160;be&amp;#160;shared&amp;#160;between&amp;#160;specifications&amp;#160;and&amp;#160;multiple&amp;#160;contexts&amp;#160;can&amp;#160;be&amp;#160;used&amp;#160;within&amp;#160;a&amp;#160;single&amp;#160;specification.&amp;#160;&amp;#160;This&amp;#160;example&amp;#160;is&amp;#160;kept&amp;#160;very&amp;#160;simple&amp;#160;for&amp;#160;demonstration&amp;#160;purposes&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;StackSpecification&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Specification&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;var&lt;/span&gt;&amp;#160;list&amp;#160;:&amp;#160;List&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;_&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;empty&amp;#160;=&amp;#160;beforeContext(list&amp;#160;=&amp;#160;&lt;span class="singleton"&gt;Nil&lt;/span&gt;)&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;nonEmpty&amp;#160;=&amp;#160;beforeContext(list&amp;#160;=&amp;#160;List(1,2,3))&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="string"&gt;"A&amp;#160;full&amp;#160;stack"&lt;/span&gt;&amp;#160;definedAs&amp;#160;nonEmpty&amp;#160;should&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="string"&gt;"size&amp;#160;of&amp;#160;3"&lt;/span&gt;&amp;#160;in&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;list&amp;#160;must&amp;#160;haveSize&amp;#160;(3)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&lt;span class="string"&gt;"A&amp;#160;stack"&lt;/span&gt;&amp;#160;when&amp;#160;empty&amp;#160;should&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="string"&gt;"is&amp;#160;empty"&lt;/span&gt;&amp;#160;in&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;list&amp;#160;must&amp;#160;beEmpty&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;module&amp;#160;StackSpecification&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;StackSpecification.main(Array())&lt;/li&gt;&lt;li class="codelist "&gt;Specification&amp;#160;&lt;span class="string"&gt;"StackSpecification"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;A&amp;#160;full&amp;#160;stack&amp;#160;should&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;+&amp;#160;size&amp;#160;of&amp;#160;3&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;Total&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;SUS&amp;#160;&lt;span class="string"&gt;"A&amp;#160;full&amp;#160;stack"&lt;/span&gt;:&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;Finished&amp;#160;in&amp;#160;0&amp;#160;second,&amp;#160;42&amp;#160;ms&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;1&amp;#160;example,&amp;#160;1&amp;#160;expectation,&amp;#160;0&amp;#160;failure,&amp;#160;0&amp;#160;error&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;A&amp;#160;stack&amp;#160;should&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;+&amp;#160;is&amp;#160;empty&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;Total&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;SUS&amp;#160;&lt;span class="string"&gt;"A&amp;#160;stack"&lt;/span&gt;:&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;Finished&amp;#160;in&amp;#160;0&amp;#160;second,&amp;#160;4&amp;#160;ms&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;1&amp;#160;example,&amp;#160;1&amp;#160;expectation,&amp;#160;0&amp;#160;failure,&amp;#160;0&amp;#160;error&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;Total&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;specification&amp;#160;&lt;span class="string"&gt;"StackSpecification"&lt;/span&gt;:&lt;/li&gt;&lt;li class="codelist "&gt;Finished&amp;#160;in&amp;#160;0&amp;#160;second,&amp;#160;85&amp;#160;ms&lt;/li&gt;&lt;li class="codelist alt"&gt;2&amp;#160;examples,&amp;#160;2&amp;#160;expectations,&amp;#160;0&amp;#160;failure,&amp;#160;0&amp;#160;error&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-6842790659544848575?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/6842790659544848575/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/specs-and-fixtuescontexts.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6842790659544848575'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/6842790659544848575'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/specs-and-fixtuescontexts.html' title='Specs and Fixtures/Contexts'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-49587984898776514</id><published>2010-02-11T00:06:00.000-08:00</published><updated>2010-02-11T00:14:09.686-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='Advanced'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><title type='text'>Selection with Implicit Methods</title><content type='html'>This tip is a cool tip based on Daniel's &lt;a href="http://dcsobral.blogspot.com/2009/06/using-implicits-to-select-types.html"&gt;Use Implicits to Select Types&lt;/a&gt; post.  That post goes into more detail.&lt;br /&gt;&lt;br /&gt;The idea is that depending on a given parameter of type T a particular type of object is required.  There are several ways to do this.  One would be to use matching to match the type T and create the correct object.  Most likely the biggest draw back to matching is caused by type erasure.  The following solution gets around that issue. &lt;br /&gt;&lt;br /&gt;Two very interesting points.  &lt;br /&gt;&lt;ol&gt;&lt;li&gt;Implicit methods do not require parameters.  They can be selected based only on type parameters&lt;/li&gt;&lt;li&gt;Implicit methods are not subject to type erasure&lt;/li&gt;&lt;/ol&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;the&amp;#160;base&amp;#160;class&amp;#160;we&amp;#160;need&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;abstract&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[T]&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;id&amp;#160;:&lt;span class="singleton"&gt;Unit&lt;/span&gt;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;One&amp;#160;of&amp;#160;the&amp;#160;types&amp;#160;we&amp;#160;need&amp;#160;created.&amp;#160;&amp;#160;It&amp;#160;is&amp;#160;the&amp;#160;catch&amp;#160;all&amp;#160;case&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;a&lt;span class="type-param"&gt;[T]&lt;/span&gt;&amp;#160;=&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[T]&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;id&amp;#160;=println(&lt;span class="string"&gt;"generic"&lt;/span&gt;)&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;a:&amp;#160;&lt;span class="type-param"&gt;[T]&lt;/span&gt;X&lt;span class="type-param"&gt;[T]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;A&amp;#160;specific&amp;#160;subclass&amp;#160;for&amp;#160;integers&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;implicit&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;b&amp;#160;=&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;X&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;id&amp;#160;=println(&lt;span class="string"&gt;"Int"&lt;/span&gt;)&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;b:&amp;#160;X&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;One&amp;#160;simple&amp;#160;usage.&amp;#160;&amp;#160;The&amp;#160;most&amp;#160;specific&amp;#160;implicit&amp;#160;will&amp;#160;be&amp;#160;used&amp;#160;to&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;create&amp;#160;the&amp;#160;object&amp;#160;to&amp;#160;be&amp;#160;passed&amp;#160;to&amp;#160;g.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;f&lt;span class="type-param"&gt;[T]&lt;/span&gt;(a&amp;#160;:T)(implicit&amp;#160;g&amp;#160;:X&lt;span class="type-param"&gt;[T]&lt;/span&gt;)&amp;#160;=&amp;#160;g.id&lt;/li&gt;&lt;li class="codelist "&gt;f:&amp;#160;&lt;span class="type-param"&gt;[T]&lt;/span&gt;(a:&amp;#160;T)(implicit&amp;#160;g:&amp;#160;X&lt;span class="type-param"&gt;[T]&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;f(5)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;f(&lt;span class="char"&gt;'c'&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;generic&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;example&amp;#160;demonstrates&amp;#160;how&amp;#160;erasure&amp;#160;is&amp;#160;not&amp;#160;an&amp;#160;issue&amp;#160;because&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;the&amp;#160;selection&amp;#160;of&amp;#160;the&amp;#160;implicit&amp;#160;is&amp;#160;done&amp;#160;at&amp;#160;compile&amp;#160;time&amp;#160;so&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;the&amp;#160;correct&amp;#160;type&amp;#160;is&amp;#160;selected.&amp;#160;&amp;#160;If&amp;#160;a&amp;#160;match&amp;#160;was&amp;#160;used&amp;#160;instead&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;then&amp;#160;a&amp;#160;more&amp;#160;complicated&amp;#160;solution&amp;#160;would&amp;#160;be&amp;#160;required&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;g&lt;span class="type-param"&gt;[T]&lt;/span&gt;(l:List&lt;span class="type-param"&gt;[T]&lt;/span&gt;)(implicit&amp;#160;i:X&lt;span class="type-param"&gt;[T]&lt;/span&gt;)&amp;#160;=&amp;#160;i.id&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;g:&amp;#160;&lt;span class="type-param"&gt;[T]&lt;/span&gt;(l:&amp;#160;List&lt;span class="type-param"&gt;[T]&lt;/span&gt;)(implicit&amp;#160;i:&amp;#160;X&lt;span class="type-param"&gt;[T]&lt;/span&gt;)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;g(List(1,2,3))&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;g(List(&lt;span class="string"&gt;"a"&lt;/span&gt;,2,3))&lt;/li&gt;&lt;li class="codelist alt"&gt;generic&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-49587984898776514?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/49587984898776514/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/selection-with-implicit-methods.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/49587984898776514'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/49587984898776514'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/selection-with-implicit-methods.html' title='Selection with Implicit Methods'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-2051973455710075167</id><published>2010-02-09T02:01:00.000-08:00</published><updated>2010-02-11T00:13:53.732-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='type alias'/><category scheme='http://www.blogger.com/atom/ns#' term='type'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='structural types'/><title type='text'>Structural Types: Multiple Methods and Type Aliasing</title><content type='html'>There are two more aspects related to structural typing that are useful to look at.  Structural types with multiple methods and type aliases.&lt;br /&gt;&lt;br /&gt;For background on this topic also look at:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;&lt;a href="http://daily-scala.blogspot.com/2010/02/introducing-structural-types.html"&gt;Introducing Structual Types&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://daily-scala.blogspot.com/2010/02/dynamic-calls-using-structural-types.html"&gt;Dynamic Calls Using Structural Types&lt;/a&gt;&lt;/li&gt;&lt;/ul&gt;Structural Types are not limited to defining a single method.  In that regard they are very similar to interfaces without the binary incompatibility issues.  However do not be fooled into thinking they are the same thing.  For one reason reflection is used so performance can be an issue in certain cases and also interfaces/traits have semantics that structural types do not.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Defining&amp;#160;a&amp;#160;types&amp;#160;that&amp;#160;has&amp;#160;both&amp;#160;a&amp;#160;length&amp;#160;and&amp;#160;charAt&amp;#160;method.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Just&amp;#160;a&amp;#160;warning.&amp;#160;&amp;#160;If&amp;#160;you&amp;#160;leave&amp;#160;off&amp;#160;the&amp;#160;()&amp;#160;after&amp;#160;length&amp;#160;this&amp;#160;will&amp;#160;not&amp;#160;work.&amp;#160;&amp;#160;This&amp;#160;is&amp;#160;not&amp;#160;a&amp;#160;bug.&amp;#160;&amp;#160;Martin&amp;#160;kindly&amp;#160;left&amp;#160;a&amp;#160;comment&amp;#160;on&amp;#160;why&amp;#160;it&amp;#160;is&amp;#160;not.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;foreach(t&amp;#160;:&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;length():&lt;span class="basicType"&gt;Int&lt;/span&gt;;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;charAt(i:&lt;span class="basicType"&gt;Int&lt;/span&gt;):&lt;span class="basicType"&gt;Char&lt;/span&gt;},&amp;#160;f&amp;#160;:&amp;#160;&lt;span class="basicType"&gt;Char&lt;/span&gt;&amp;#160;=&gt;&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;0&amp;#160;until&amp;#160;t.length&amp;#160;foreach&amp;#160;{i&amp;#160;=&gt;&amp;#160;f(t.charAt(i))}&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;foreach:&amp;#160;(t:&amp;#160;AnyRef{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;length():&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;charAt(i:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;):&amp;#160;&lt;span class="basicType"&gt;Char&lt;/span&gt;},f:&amp;#160;(&lt;span class="basicType"&gt;Char&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;&lt;span class="singleton"&gt;Unit&lt;/span&gt;)Unit&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;A&amp;#160;string&amp;#160;matches&amp;#160;the&amp;#160;structural&amp;#160;type&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;foreach&amp;#160;(&lt;span class="string"&gt;"hello"&lt;/span&gt;,&amp;#160;println&amp;#160;_)&lt;/li&gt;&lt;li class="codelist alt"&gt;h&lt;/li&gt;&lt;li class="codelist "&gt;e&lt;/li&gt;&lt;li class="codelist alt"&gt;l&lt;/li&gt;&lt;li class="codelist "&gt;l&lt;/li&gt;&lt;li class="codelist alt"&gt;o&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Pretty unexpected I would say.  A feature of Scala which complements Structural types are type aliases.  They are useful in many situations and one is with use with Structural Types:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;With&amp;#160;type&amp;#160;aliasing&amp;#160;you&amp;#160;can&amp;#160;assign&amp;#160;a&amp;#160;structural&amp;#160;type&amp;#160;a&amp;#160;name&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;IChar&amp;#160;=&amp;#160;{&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;length():&lt;span class="basicType"&gt;Int&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;charAt(i:&lt;span class="basicType"&gt;Int&lt;/span&gt;):&lt;span class="basicType"&gt;Char&lt;/span&gt;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;alias&amp;#160;IChar&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;print(&amp;#160;t&amp;#160;:&amp;#160;IChar)&amp;#160;=&amp;#160;0&amp;#160;until&amp;#160;t.length()&amp;#160;foreach&amp;#160;{i&amp;#160;=&gt;&amp;#160;println(t.charAt(i))}&lt;/li&gt;&lt;li class="codelist alt"&gt;print:&amp;#160;(t:&amp;#160;IChar)&lt;span class="singleton"&gt;Unit&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;print(&lt;span class="string"&gt;"gurk"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;g&lt;/li&gt;&lt;li class="codelist alt"&gt;u&lt;/li&gt;&lt;li class="codelist "&gt;r&lt;/li&gt;&lt;li class="codelist alt"&gt;k&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-2051973455710075167?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/2051973455710075167/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/structural-types-multiple-methods-and.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/2051973455710075167'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/2051973455710075167'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/structural-types-multiple-methods-and.html' title='Structural Types: Multiple Methods and Type Aliasing'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-849891573213541183</id><published>2010-02-08T01:10:00.001-08:00</published><updated>2010-02-09T02:04:29.288-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='structural types'/><category scheme='http://www.blogger.com/atom/ns#' term='casting'/><title type='text'>Dynamic calls using Structural Types</title><content type='html'>Using reflection can be a real pain in Java since the API is a Java API and consists of many gets and searches through collections not to mention so many exceptions that need to be handled.  In Scala there is a wonderful way to clean up a reflective call down to a single line (assuming you don't want to worry about handling exceptions.)  Here structural typing can really be a pleasure.  &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;I&amp;#160;am&amp;#160;assigning&amp;#160;a&amp;#160;string&amp;#160;to&amp;#160;an&amp;#160;Any&amp;#160;reference&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;s:Any&amp;#160;=&amp;#160;&lt;span class="string"&gt;"hello&amp;#160;:D"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;s:&amp;#160;Any&amp;#160;=&amp;#160;hello&amp;#160;:D&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;Any&amp;#160;does&amp;#160;not&amp;#160;have&amp;#160;a&amp;#160;length&amp;#160;method&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;s.length&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;lt;&amp;#160;console&gt;:6:&amp;#160;error:&amp;#160;value&amp;#160;length&amp;#160;is&amp;#160;not&amp;#160;a&amp;#160;member&amp;#160;of&amp;#160;Any&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;s.length&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;^&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;But&amp;#160;I&amp;#160;can&amp;#160;cast&amp;#160;it&amp;#160;to&amp;#160;a&amp;#160;structural&amp;#160;type&amp;#160;with&amp;#160;a&amp;#160;length&amp;#160;method&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;s.asInstanceOf&lt;span class="type-param"&gt;[{def&amp;#160;length:Int}]&lt;/span&gt;.length&lt;/li&gt;&lt;li class="codelist alt"&gt;res2:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;8&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;There are restrictions to this.  For example implicits will not work:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;The&amp;#160;method&amp;#160;r&amp;#160;is&amp;#160;part&amp;#160;of&amp;#160;StringLike&amp;#160;(or&amp;#160;RichString&amp;#160;in&amp;#160;Scala&amp;#160;2.7)&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;and&amp;#160;there&amp;#160;is&amp;#160;an&amp;#160;implicit&amp;#160;conversion&amp;#160;from&amp;#160;String&amp;#160;to&amp;#160;RichString/StringLike.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;The&amp;#160;structural&amp;#160;type&amp;#160;does&amp;#160;not&amp;#160;try&amp;#160;to&amp;#160;apply&amp;#160;the&amp;#160;implicits&amp;#160;because&amp;#160;implicits&amp;#160;are&amp;#160;a&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;compile&amp;#160;time&amp;#160;artifact&amp;#160;and&amp;#160;that&amp;#160;information&amp;#160;is&amp;#160;not&amp;#160;kept&amp;#160;at&amp;#160;run&amp;#160;time.&amp;#160;&amp;#160;Perhaps&amp;#160;this&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;will&amp;#160;be&amp;#160;added&amp;#160;in&amp;#160;the&amp;#160;future&amp;#160;but&amp;#160;it&amp;#160;is&amp;#160;not&amp;#160;present&amp;#160;now.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;s.asInstanceOf&lt;span class="type-param"&gt;[{def&amp;#160;r:util.matching.Regex}]&lt;/span&gt;.r&lt;/li&gt;&lt;li class="codelist alt"&gt;java.lang.NoSuchMethodException:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;.r()&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;More examples:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;s:Any&amp;#160;=&amp;#160;&lt;span class="string"&gt;"hello&amp;#160;:D"&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;s:&amp;#160;Any&amp;#160;=&amp;#160;hello&amp;#160;:D&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;s.asInstanceOf&lt;span class="type-param"&gt;[{def&amp;#160;charAt(x:Int):Char}]&lt;/span&gt;.charAt(2)&lt;/li&gt;&lt;li class="codelist alt"&gt;res9:&amp;#160;&lt;span class="basicType"&gt;Char&lt;/span&gt;&amp;#160;=&amp;#160;l&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;This&amp;#160;is&amp;#160;interesting.&amp;#160;&amp;#160;The&amp;#160;actual&amp;#160;method&amp;#160;returns&amp;#160;Char,&amp;#160;but&amp;#160;Char&amp;#160;is&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;compatible&amp;#160;with&amp;#160;Any&amp;#160;so&amp;#160;this&amp;#160;cast&amp;#160;works.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;s.asInstanceOf&lt;span class="type-param"&gt;[{def&amp;#160;charAt(x:Int):Any}]&lt;/span&gt;.charAt(2)&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res10:&amp;#160;Any&amp;#160;=&amp;#160;l&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;//&amp;#160;Now&amp;#160;lets&amp;#160;test&amp;#160;to&amp;#160;see&amp;#160;if&amp;#160;that&amp;#160;lenience&amp;#160;is&amp;#160;available&amp;#160;for&amp;#160;parameters:&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;X&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Y&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;X&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Y&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;T&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;x(x:X):&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;T&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;a:Any&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;T()&lt;/li&gt;&lt;li class="codelist alt"&gt;a:&amp;#160;Any&amp;#160;=&amp;#160;T&lt;span class="annotation"&gt;@&lt;/span&gt;687c3b99&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;a.asInstanceOf&lt;span class="type-param"&gt;[{def&amp;#160;x(x:X):Any}]&lt;/span&gt;.x(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y())&lt;/li&gt;&lt;li class="codelist "&gt;res11:&amp;#160;Any&amp;#160;=&amp;#160;1&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Ok&amp;#160;so&amp;#160;return&amp;#160;values&amp;#160;can&amp;#160;be&amp;#160;subclasses&amp;#160;but&amp;#160;not&amp;#160;params&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;a.asInstanceOf&lt;span class="type-param"&gt;[{def&amp;#160;x(x:Y):Any}]&lt;/span&gt;.x(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Y())&lt;/li&gt;&lt;li class="codelist "&gt;java.lang.NoSuchMethodException:&amp;#160;T.x(Y)&lt;/li&gt;&lt;li class="codelist alt"&gt; at&amp;#160;java.lang.Class.getMethod(Class.ja&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Use with care :-D&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-849891573213541183?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/849891573213541183/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/dynamic-calls-using-structural-types.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/849891573213541183'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/849891573213541183'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/dynamic-calls-using-structural-types.html' title='Dynamic calls using Structural Types'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-7633562475467147612</id><published>2010-02-05T00:05:00.000-08:00</published><updated>2010-02-05T22:31:34.077-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='control structure'/><category scheme='http://www.blogger.com/atom/ns#' term='structural types'/><title type='text'>Introducing Structural Types</title><content type='html'>Structural types allows one to declare types based on the methods the type has.  For example you could define a method that takes a class containing a close method.  This is fairy analogous to duck-typing in dynamic languages.  Except that it is statically enforced.  &lt;br /&gt;&lt;br /&gt;The main example used here was from a comment on the &lt;a href="http://codemonkeyism.com/scala-goodness-structural-typing/"&gt;Code Monkeyism Blog&lt;/a&gt;.  The commenter further explains that this example is in fact from Beginning Scala chapter 4 (which I would like to read but have not yet had the time.)&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;A&amp;#160;can&amp;#160;be&amp;#160;any&amp;#160;object&amp;#160;that&amp;#160;has&amp;#160;a&amp;#160;close&amp;#160;method.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;This&amp;#160;is&amp;#160;statically&amp;#160;typed&amp;#160;which&amp;#160;makes&amp;#160;some&amp;#160;restrictions&amp;#160;which&amp;#160;are&amp;#160;explained&amp;#160;later&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;using&lt;span class="type-param"&gt;[A&amp;#160;&amp;lt;:&amp;#160;{def&amp;#160;close():&amp;#160;Unit},&amp;#160;B]&lt;/span&gt;(param:&amp;#160;A)(f:&amp;#160;A&amp;#160;=&gt;&amp;#160;B):&amp;#160;B&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;try&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;f(param)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&amp;#160;&lt;span class="key"&gt;finally&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;try&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;param.close()&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&amp;#160;&lt;span class="key"&gt;catch&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;()&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;using:&amp;#160;&lt;span class="type-param"&gt;[A&amp;#160;&amp;lt;:&amp;#160;AnyRef{def&amp;#160;close():&amp;#160;Unit},B]&lt;/span&gt;(param:&amp;#160;=&gt;&amp;#160;A)(f:&amp;#160;(A)&amp;#160;=&gt;&amp;#160;B)B&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;using(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.ByteArrayInputStream(&lt;span class="string"&gt;"hello&amp;#160;world"&lt;/span&gt;.getBytes)){&amp;#160;in&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;io.Source.fromInputStream(in)&amp;#160;foreach&amp;#160;(print)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;hello&amp;#160;world&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;using(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.ByteArrayInputStream(&lt;span class="string"&gt;"hello&amp;#160;world"&lt;/span&gt;.getBytes)){&amp;#160;in&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;io.Source.fromInputStream(in)&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;""&lt;/span&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;res8:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;hello&amp;#160;world&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;That is extremely powerful and the consequences will be visited more in the future.  But because structural typing is statically enforced it is not quite as flexible as dynamic language's version of duck typing.  For example you cannot do:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;i:Any&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.ByteArrayInputStream(&lt;span class="string"&gt;"hello&amp;#160;world"&lt;/span&gt;.getBytes)&lt;/li&gt;&lt;li class="codelist "&gt;i:&amp;#160;Any&amp;#160;=&amp;#160;java.io.ByteArrayInputStream&lt;span class="annotation"&gt;@&lt;/span&gt;145a25f3&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;does&amp;#160;not&amp;#160;work&amp;#160;because&amp;#160;'i'&amp;#160;is&amp;#160;defined&amp;#160;as&amp;#160;type&amp;#160;Any.&amp;#160;&amp;#160;Not&amp;#160;a&amp;#160;type&amp;#160;that&amp;#160;is&amp;#160;closeable.&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Casting&amp;#160;can&amp;#160;be&amp;#160;used&amp;#160;to&amp;#160;get&amp;#160;around&amp;#160;this&amp;#160;issue.&amp;#160;&amp;#160;I&amp;#160;will&amp;#160;address&amp;#160;that&amp;#160;in&amp;#160;its&amp;#160;own&amp;#160;post&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;using(i){&amp;#160;in&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;io.Source.fromInputStream(in)&amp;#160;mkString&amp;#160;&lt;span class="string"&gt;""&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;lt;&amp;#160;console&gt;:8:&amp;#160;error:&amp;#160;inferred&amp;#160;&lt;span class="key"&gt;type&lt;/span&gt;&amp;#160;arguments&amp;#160;&lt;span class="type-param"&gt;[Any,B]&lt;/span&gt;&amp;#160;do&amp;#160;not&amp;#160;conform&amp;#160;to&amp;#160;method&amp;#160;using&lt;span class="char"&gt;'s&amp;#160;type&amp;#160;parameter&amp;#160;bounds&amp;#160;[A&amp;#160;&amp;lt;:&amp;#160;AnyRef{def&amp;#160;close():&amp;#160;Unit},B]&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;using(i){&amp;#160;in&amp;#160;=&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;An alternative to the first using example is to use call by name to construct the closeable.  The reason one might want to do that is because it allows currying of the method:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;using&lt;span class="type-param"&gt;[A&amp;#160;&amp;lt;:&amp;#160;{def&amp;#160;close():&amp;#160;Unit},&amp;#160;B]&lt;/span&gt;(param:&amp;#160;=&gt;A)(f:&amp;#160;A&amp;#160;=&gt;&amp;#160;B):&amp;#160;B&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;closeable&amp;#160;=&amp;#160;param&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;notice&amp;#160;param&amp;#160;is&amp;#160;only&amp;#160;referenced&amp;#160;once&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&lt;span class="key"&gt;try&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;f(closeable)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&amp;#160;&lt;span class="key"&gt;finally&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;try&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;closeable.close()&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&amp;#160;&lt;span class="key"&gt;catch&lt;/span&gt;&amp;#160;{&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;()&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;using:&amp;#160;&lt;span class="type-param"&gt;[A&amp;#160;&amp;lt;:&amp;#160;AnyRef{def&amp;#160;close():&amp;#160;Unit},B]&lt;/span&gt;(param:&amp;#160;=&gt;&amp;#160;A)(f:&amp;#160;(A)&amp;#160;=&gt;&amp;#160;B)B&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;if&amp;#160;this&amp;#160;was&amp;#160;accessing&amp;#160;a&amp;#160;database&amp;#160;a&amp;#160;new&amp;#160;connection&amp;#160;would&amp;#160;be&amp;#160;made&amp;#160;automatically&amp;#160;each&amp;#160;time&amp;#160;this&amp;#160;function&amp;#160;was&amp;#160;used&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;usingTheWorld&amp;#160;=&amp;#160;using&lt;span class="type-param"&gt;[BStream,Int]&lt;/span&gt;(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;java.io.ByteArrayInputStream(&lt;span class="string"&gt;"hello&amp;#160;world"&lt;/span&gt;.getBytes))_&lt;/li&gt;&lt;li class="codelist "&gt;usingTheWorld:&amp;#160;((java.io.ByteArrayInputStream)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&gt;&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;&amp;lt;&amp;#160;function1&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;usingTheWorld&amp;#160;{&amp;#160;s&amp;#160;=&gt;&amp;#160;io.Source.fromInputStream(s).length}&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;res3:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;11&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;usingTheWorld&amp;#160;{&amp;#160;s&amp;#160;=&gt;&amp;#160;io.Source.fromInputStream(s).getLines().length}&lt;/li&gt;&lt;li class="codelist "&gt;res5:&amp;#160;&lt;span class="basicType"&gt;Int&lt;/span&gt;&amp;#160;=&amp;#160;0&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-7633562475467147612?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/7633562475467147612/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/introducing-structural-types.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7633562475467147612'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/7633562475467147612'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/introducing-structural-types.html' title='Introducing Structural Types'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-4262542102813258115</id><published>2010-02-03T23:54:00.001-08:00</published><updated>2010-02-13T05:10:32.436-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='regular expression'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='regex'/><title type='text'>Regex ReplaceAllIn</title><content type='html'>Note: Updated on Feb 13th for the newer API on Scala 2.8 trunk. (This is life on the bleeding edge, thanks Daniel).&lt;br /&gt;&lt;br /&gt;A couple new methods have just been added to Scala 2.8 Regex.  You will need to download a version of Scala 2.8 more recent than Scala2.8-Beta1.  &lt;br /&gt;&lt;br /&gt;The methods are related to replacing text using a regular expression and to say they are useful is an understatement.  Lets take a look:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;quote&amp;#160;=&amp;#160;&lt;span class="string"&gt;"""I&amp;#160;don&amp;apos;t&amp;#160;like&amp;#160;to&amp;#160;commit&amp;#160;myself&amp;#160;about&amp;#160;heaven&amp;#160;and&amp;#160;hell&amp;#160;-&amp;#160;you&amp;#160;see,&amp;#160;I&amp;#160;have&amp;#160;friends&amp;#160;in&amp;#160;both&amp;#160;places.&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="string"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;Mark&amp;#160;Twain"""&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;quote:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;I&amp;#160;don&amp;apos;t&amp;#160;like&amp;#160;to&amp;#160;commit&amp;#160;myself&amp;#160;about&amp;#160;heaven&amp;#160;and&amp;#160;hell&amp;#160;-&amp;#160;you&amp;#160;see,&amp;#160;I&amp;#160;have&amp;#160;friends&amp;#160;in&amp;#160;both&amp;#160;places.&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;Mark&amp;#160;Twain&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;expr&amp;#160;=&amp;#160;&lt;span class="string"&gt;"e"&lt;/span&gt;.r&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;expr:&amp;#160;scala.util.matching.Regex&amp;#160;=&amp;#160;e&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;This&amp;#160;first&amp;#160;method&amp;#160;is&amp;#160;not&amp;#160;new&amp;#160;or&amp;#160;is&amp;#160;it&amp;#160;interesting.&amp;#160;&amp;#160;But&amp;#160;the&amp;#160;new&amp;#160;methods&amp;#160;are&amp;#160;both&amp;#160;related&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;so&amp;#160;lets&amp;#160;start&amp;#160;with&amp;#160;the&amp;#160;basic&amp;#160;form&amp;#160;of&amp;#160;replaceAllIn&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;expr.replaceAllIn(quote,&amp;#160;&lt;span class="string"&gt;"**"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;res1:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;I&amp;#160;don&amp;apos;t&amp;#160;lik**&amp;#160;to&amp;#160;commit&amp;#160;mys**lf&amp;#160;about&amp;#160;h**av**n&amp;#160;and&amp;#160;h**ll&amp;#160;-&amp;#160;you&amp;#160;s****,&amp;#160;I&amp;#160;hav**&amp;#160;fri**nds&amp;#160;in&amp;#160;both&amp;#160;plac**s.&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;Mark&amp;#160;Twain&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;this&amp;#160;does&amp;#160;the&amp;#160;same&amp;#160;thing&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;quote.replaceAll(&lt;span class="string"&gt;"e"&lt;/span&gt;,&lt;span class="string"&gt;"**"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;res2:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;I&amp;#160;don&amp;apos;t&amp;#160;lik**&amp;#160;to&amp;#160;commit&amp;#160;mys**lf&amp;#160;about&amp;#160;h**av**n&amp;#160;and&amp;#160;h**ll&amp;#160;-&amp;#160;you&amp;#160;s****,&amp;#160;I&amp;#160;hav**&amp;#160;fri**nds&amp;#160;in&amp;#160;both&amp;#160;plac**s.&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;Mark&amp;#160;Twain&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;Now&amp;#160;things&amp;#160;get&amp;#160;interesting.&amp;#160;&amp;#160;Using&amp;#160;this&amp;#160;form&amp;#160;of&amp;#160;replaceAllIn&amp;#160;we&amp;#160;can&amp;#160;determine&amp;#160;the&amp;#160;replacement&amp;#160;on&amp;#160;a&amp;#160;case&amp;#160;by&amp;#160;case&amp;#160;basis.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;It&amp;#160;provides&amp;#160;the&amp;#160;Match&amp;#160;object&amp;#160;as&amp;#160;the&amp;#160;parameter&amp;#160;so&amp;#160;you&amp;#160;have&amp;#160;complete&amp;#160;access&amp;#160;to&amp;#160;all&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;the&amp;#160;matched&amp;#160;groups,&amp;#160;the&amp;#160;location&amp;#160;of&amp;#160;the&amp;#160;match&amp;#160;etc...&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;The&amp;#160;method&amp;#160;takes&amp;#160;a&amp;#160;Match&amp;#160;=&gt;&amp;#160;String&amp;#160;function.&amp;#160;&amp;#160;Very,&amp;#160;&lt;em&gt;very&lt;/em&gt;&amp;#160;powerful.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;expr.replaceAllIn(quote,&amp;#160;s&amp;#160;=&gt;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(util.Random.nextBoolean)&amp;#160;&lt;span class="string"&gt;"?"&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;&lt;span class="string"&gt;"*"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;res5:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;I&amp;#160;don&amp;apos;t&amp;#160;lik?&amp;#160;to&amp;#160;commit&amp;#160;mys?lf&amp;#160;about&amp;#160;h?av?n&amp;#160;and&amp;#160;h?ll&amp;#160;-&amp;#160;you&amp;#160;s*?,&amp;#160;I&amp;#160;hav?&amp;#160;fri*nds&amp;#160;in&amp;#160;both&amp;#160;plac*s.&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;Mark&amp;#160;Twain&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Another&amp;#160;example&amp;#160;using&amp;#160;some&amp;#160;of&amp;#160;the&amp;#160;matcher&amp;#160;functionality&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;expr.replaceAllIn(quote,&amp;#160;m&amp;#160;=&gt;&amp;#160;m.start.toString)&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;res6:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;I&amp;#160;don&amp;apos;t&amp;#160;lik11&amp;#160;to&amp;#160;commit&amp;#160;mys26lf&amp;#160;about&amp;#160;h37av40n&amp;#160;and&amp;#160;h48ll&amp;#160;-&amp;#160;you&amp;#160;s5960,&amp;#160;I&amp;#160;hav68&amp;#160;fri73nds&amp;#160;in&amp;#160;both&amp;#160;plac90s.&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;Mark&amp;#160;Twain&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;Another&amp;#160;crazy&amp;#160;useful&amp;#160;method&amp;#160;is&amp;#160;the&amp;#160;replaceSomeIn.&amp;#160;&amp;#160;It&amp;#160;is&amp;#160;similar&amp;#160;to&amp;#160;the&amp;#160;replaceAllIn&amp;#160;that&amp;#160;takes&amp;#160;a&amp;#160;function&amp;#160;except&amp;#160;that&amp;#160;the&amp;#160;function&amp;#160;in&amp;#160;replaceSomeIn&amp;#160;returns&amp;#160;an&amp;#160;Option.&amp;#160;&amp;#160;If&amp;#160;None&amp;#160;then&amp;#160;there&amp;#160;is&amp;#160;no&amp;#160;replacement.&amp;#160;&amp;#160;Otherwise&amp;#160;a&amp;#160;replacement&amp;#160;is&amp;#160;performed.&amp;#160;&amp;#160;Very&amp;#160;nice&amp;#160;when&amp;#160;dealing&amp;#160;with&amp;#160;complex&amp;#160;regular&amp;#160;expressions.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;In&amp;#160;this&amp;#160;example&amp;#160;we&amp;#160;are&amp;#160;replacing&amp;#160;all&amp;#160;'e's&amp;#160;start&amp;#160;are&amp;#160;before&amp;#160;the&amp;#160;50th&amp;#160;character&amp;#160;in&amp;#160;the&amp;#160;string&amp;#160;with&amp;#160;-&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;expr.replaceSomeIn(quote,&amp;#160;m&amp;#160;=&gt;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(m.start&amp;#160;&gt;&amp;#160;50)&amp;#160;None&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;Some(&lt;span class="string"&gt;"-"&lt;/span&gt;))&lt;/li&gt;&lt;li class="codelist "&gt;res3:&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;I&amp;#160;don&lt;span class="char"&gt;'t&amp;#160;lik-&amp;#160;to&amp;#160;commit&amp;#160;mys-lf&amp;#160;about&amp;#160;h-av-n&amp;#160;and&amp;#160;h-ll&amp;#160;-&amp;#160;you&amp;#160;see,&amp;#160;I&amp;#160;have&amp;#160;friends&amp;#160;in&amp;#160;both&amp;#160;places.&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;Mark&amp;#160;Twain&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-4262542102813258115?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/4262542102813258115/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/regex-replaceallin.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4262542102813258115'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4262542102813258115'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/regex-replaceallin.html' title='Regex ReplaceAllIn'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-5250702910109603523</id><published>2010-02-03T14:25:00.000-08:00</published><updated>2010-02-03T23:28:25.686-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='option'/><category scheme='http://www.blogger.com/atom/ns#' term='beginner'/><title type='text'>Chaining Options with orElse</title><content type='html'>A simple but handy use for Option is to select the first valid option from a selection of possible choices.  Sound vague? Well it is because it can be used in many different situations.  The one presented here is: the program needs a directory that can be set by the user either as a system variable, and environment variable or the default value.  The java code is a nightmare of if (xxx == null) statements.  The Scala code is beautiful.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;propsTemplates&amp;#160;=&amp;#160;Option(System&amp;#160;getProperty&amp;#160;&lt;span class="string"&gt;"MVN_CREATOR_TEMPLATES"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;propsTemplates:&amp;#160;Option&lt;span class="type-param"&gt;[java.lang.String]&lt;/span&gt;&amp;#160;=&amp;#160;None&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;envTemplates&amp;#160;=&amp;#160;Option(System&amp;#160;getenv&amp;#160;&lt;span class="string"&gt;"MVN_CREATOR_TEMPLATES"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;envTemplates:&amp;#160;Option&lt;span class="type-param"&gt;[java.lang.String]&lt;/span&gt;&amp;#160;=&amp;#160;None&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;defaultHome&amp;#160;=&amp;#160;Some(System&amp;#160;getProperty&amp;#160;&lt;span class="string"&gt;"user.home"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;defaultHome:&amp;#160;Some&lt;span class="type-param"&gt;[java.lang.String]&lt;/span&gt;&amp;#160;=&amp;#160;Some(/Users/jeichar)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;chain&amp;#160;the&amp;#160;different&amp;#160;options&amp;#160;together&amp;#160;in&amp;#160;order&amp;#160;of&amp;#160;priority&amp;#160;and&amp;#160;get&amp;#160;the&amp;#160;value&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;I&amp;#160;am&amp;#160;taking&amp;#160;a&amp;#160;small&amp;#160;liberty&amp;#160;here&amp;#160;because&amp;#160;I&amp;#160;am&amp;#160;assuming&amp;#160;that&amp;#160;user.home&amp;#160;is&amp;#160;always&amp;#160;available&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;propsTemplates.orElse(envTemplates).orElse(defaultHome).get&lt;/li&gt;&lt;li class="codelist alt"&gt;res0:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;/Users/jeichar&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;alternative&amp;#160;form:&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;propsTemplates&amp;#160;orElse&amp;#160;envTemplates&amp;#160;orElse&amp;#160;defaultHome&amp;#160;get&lt;/li&gt;&lt;li class="codelist alt"&gt;res1:&amp;#160;java.lang.&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;=&amp;#160;/Users/jeichar&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-5250702910109603523?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/5250702910109603523/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/chaining-options-with-orelse.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5250702910109603523'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/5250702910109603523'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/chaining-options-with-orelse.html' title='Chaining Options with orElse'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-4299537058660677433</id><published>2010-02-02T03:59:00.000-08:00</published><updated>2010-02-02T05:04:05.939-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='for-comprehension'/><title type='text'>Blocks within for-comprehensions</title><content type='html'>In another example of uniformity it is possible to use blocks within a for-comprehension when creating a generator or making an assignment.  The basic form of a for-comprehension is &lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;{i&amp;#160;&amp;lt;-&amp;#160;generator&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;guard&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;j&amp;#160;=&amp;#160;assignment&amp;#160;}&amp;#160;&lt;span class="key"&gt;yield&lt;/span&gt;&amp;#160;result&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;The &lt;em&gt;generator&lt;/em&gt;, &lt;em&gt;guard&lt;/em&gt;, &lt;em&gt;assignment&lt;/em&gt; and &lt;em&gt;result&lt;/em&gt; are all expressions which means they can all be blocks or simple statements.  Most commonly you will see them as simple statements:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;{i&amp;#160;&amp;lt;-&amp;#160;1&amp;#160;to&amp;#160;10&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;i&amp;#160;%&amp;#160;2&amp;#160;==&amp;#160;0&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;j&amp;#160;=&amp;#160;i&amp;#160;}&amp;#160;&lt;span class="key"&gt;yield&lt;/span&gt;&amp;#160;j&lt;/li&gt;&lt;li class="codelist "&gt;res50:&amp;#160;scala.collection.immutable.IndexedSeq&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;IndexedSeq(2,&amp;#160;4,&amp;#160;6,&amp;#160;8,&amp;#160;10)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;But since they are expressions they can be more complex:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;for&lt;/span&gt;&amp;#160;{&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;i&amp;#160;&amp;lt;-&amp;#160;{&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;start&amp;#160;=&amp;#160;nextInt(3)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;end&amp;#160;=&amp;#160;nextInt(10)+start&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;start&amp;#160;to&amp;#160;end&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;cut&amp;#160;=&amp;#160;nextInt(3)+1&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;i&amp;#160;%&amp;#160;cut&amp;#160;==&amp;#160;0&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;j&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;x&amp;#160;=&amp;#160;i+1&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;x&amp;#160;/&amp;#160;2&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;}&amp;#160;&amp;#160;&lt;span class="key"&gt;yield&lt;/span&gt;&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="comment"&gt;//&amp;#160;do&amp;#160;a&amp;#160;debug&amp;#160;println&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;println(j)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;j&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;1&lt;/li&gt;&lt;li class="codelist alt"&gt;1&lt;/li&gt;&lt;li class="codelist "&gt;2&lt;/li&gt;&lt;li class="codelist alt"&gt;3&lt;/li&gt;&lt;li class="codelist "&gt;res53:&amp;#160;scala.collection.immutable.IndexedSeq&lt;span class="type-param"&gt;[Int]&lt;/span&gt;&amp;#160;=&amp;#160;IndexedSeq(1,&amp;#160;1,&amp;#160;2,&amp;#160;3)&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-4299537058660677433?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/4299537058660677433/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/blocks-within-for-comprehensions.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4299537058660677433'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/4299537058660677433'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/blocks-within-for-comprehensions.html' title='Blocks within for-comprehensions'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-860279868301735642</id><published>2010-02-01T02:04:00.000-08:00</published><updated>2010-02-03T14:29:45.251-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='constructor'/><category scheme='http://www.blogger.com/atom/ns#' term='intermediate'/><category scheme='http://www.blogger.com/atom/ns#' term='assignment'/><title type='text'>Temporary variables during object instantiation</title><content type='html'>In Java a common pattern with class constructors is to assign field values and often there are several intermediate values used for the calculation.  If the code is ported to Scala the resulting class will have the intermediate values as fields, which take up space in the object.  However the issue is easily worked around.  Lets look at a couple examples.&lt;br /&gt;&lt;br /&gt;Example 1: Assigning a single field&lt;br /&gt;&lt;code class="Java"&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;&amp;#160;Java&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.io.File&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="javadoc"&gt;/**&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="javadoc"&gt;No&amp;#160;real&amp;#160;logic&amp;#160;behind&amp;#160;class.&amp;#160;&amp;#160;But&amp;#160;for&amp;#160;some&amp;#160;reason&amp;#160;it&amp;#160;needs&amp;#160;the&amp;#160;path&amp;#160;of&amp;#160;a&amp;#160;tmp&amp;#160;directory&amp;#160;in&amp;#160;the&amp;#160;working&amp;#160;directory&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="javadoc"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;OneAssignment&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;final&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;field;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;public&lt;/span&gt;&amp;#160;OneAssignment()&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;File&amp;#160;file&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(&lt;span class="string"&gt;"tmp"&lt;/span&gt;);&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(!file.exists())&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;file.mkdirs();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;field&amp;#160;=&amp;#160;file.getAbsolutePath();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;In Scala the naive way to port this would be:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;&amp;#160;Scala&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.io.File&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;OneAssignment&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;file&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(&lt;span class="string"&gt;"tmp"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(!file.exists())&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;file.mkdirs()&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;field&amp;#160;=&amp;#160;file.getAbsolutePath()&lt;/li&gt;&lt;li class="codelist alt"&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;Problem is that it has an extra field "file" now.  The correct way to port this would be as follows:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;&amp;#160;Scala&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.io.File&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;OneAssignment&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;notice&amp;#160;that&amp;#160;assignment&amp;#160;is&amp;#160;in&amp;#160;a&amp;#160;block&amp;#160;so&amp;#160;file&amp;#160;is&amp;#160;only&amp;#160;visible&amp;#160;within&amp;#160;the&amp;#160;block&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;field&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;file&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(&lt;span class="string"&gt;"tmp"&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(!file.exists())&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;file.mkdirs()&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;file.getAbsolutePath()&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;&lt;br /&gt;Example 2:  Assigning multiple fields&lt;br /&gt;&lt;code class="Java"&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;&amp;#160;Java&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.io.File&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="javadoc"&gt;/**&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="javadoc"&gt;Basically&amp;#160;the&amp;#160;same&amp;#160;as&amp;#160;last&amp;#160;example&amp;#160;but&amp;#160;multiple&amp;#160;fields&amp;#160;are&amp;#160;assigned&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="javadoc"&gt;Notice&amp;#160;that&amp;#160;2&amp;#160;fields&amp;#160;depend&amp;#160;on&amp;#160;the&amp;#160;temporary&amp;#160;file&amp;#160;variable&amp;#160;but&amp;#160;count&amp;#160;does&amp;#160;not&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="javadoc"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MultipleAssignments&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;final&amp;#160;&lt;span class="basicType"&gt;String&lt;/span&gt;&amp;#160;tmp,mvn_repo;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;find&amp;#160;&lt;span class="basicType"&gt;int&lt;/span&gt;&amp;#160;count;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;public&lt;/span&gt;&amp;#160;OneAssignment()&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;File&amp;#160;file&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(&lt;span class="string"&gt;"tmp"&lt;/span&gt;);&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(!file.exists())&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;file.mkdirs();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;tmp&amp;#160;=&amp;#160;file.getAbsolutePath();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;count&amp;#160;=&amp;#160;file.listFiles.length;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;File&amp;#160;home&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(System.getProperty(&lt;span class="string"&gt;"user.home"&lt;/span&gt;));&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;mvn_repo&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(home,&amp;#160;&lt;span class="string"&gt;".m2"&lt;/span&gt;).getPath();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;The Scala port:&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;//&amp;#160;&amp;#160;Scala&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;java.io.File&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;MultipleAssignments&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;/*&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="comment"&gt;When&amp;#160;multiple&amp;#160;fields&amp;#160;depend&amp;#160;on&amp;#160;the&amp;#160;same&amp;#160;temporary&amp;#160;variables&amp;#160;the&amp;#160;fields&amp;#160;can&amp;#160;be&amp;#160;assigned&amp;#160;together&amp;#160;from&amp;#160;one&amp;#160;block&amp;#160;by&amp;#160;returning&amp;#160;a&amp;#160;tuple&amp;#160;and&amp;#160;using&amp;#160;Scala's&amp;#160;matching&amp;#160;to&amp;#160;expand&amp;#160;the&amp;#160;tuple&amp;#160;during&amp;#160;assignment.&amp;#160;&amp;#160;See&amp;#160;previous&amp;#160;topics&amp;#160;on&amp;#160;assignment&amp;#160;for&amp;#160;details&amp;#160;&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="comment"&gt;*/&lt;/span&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;(tmp,count)&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;file&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(&lt;span class="string"&gt;"tmp"&lt;/span&gt;);&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(!file.exists())&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;file.mkdirs();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;tmp&amp;#160;=&amp;#160;file.getAbsolutePath();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;count&amp;#160;=&amp;#160;file.listFiles.length;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;(tmp,&amp;#160;count)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;mvn_repo&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;home&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(System.getProperty(&lt;span class="string"&gt;"user.home"&lt;/span&gt;));&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;File(home,&amp;#160;&lt;span class="string"&gt;".m2"&lt;/span&gt;).getPath();&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;}&lt;/li&gt;&lt;/ol&gt;&lt;/div&gt;&lt;/code&gt;&lt;br /&gt;In some ways the Scala port is cleaner in that it splits the constructor up and decouples the dependencies between fields.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/5089773352404981635-860279868301735642?l=daily-scala.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://daily-scala.blogspot.com/feeds/860279868301735642/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://daily-scala.blogspot.com/2010/02/temporary-variables-during-object.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/860279868301735642'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/5089773352404981635/posts/default/860279868301735642'/><link rel='alternate' type='text/html' href='http://daily-scala.blogspot.com/2010/02/temporary-variables-during-object.html' title='Temporary variables during object instantiation'/><author><name>Jesse  Eichar</name><uri>http://www.blogger.com/profile/07600430363435495915</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='29' src='http://4.bp.blogspot.com/_d6JySbV_m2w/SnrNFgotR5I/AAAAAAAAADw/7B481I2AJDs/S220/JesseIcon.jpeg'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-5089773352404981635.post-4579861466481104799</id><published>2010-01-29T03:05:00.000-08:00</published><updated>2010-01-29T03:08:29.082-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Scala'/><category scheme='http://www.blogger.com/atom/ns#' term='covariance'/><category scheme='http://www.blogger.com/atom/ns#' term='variance'/><category scheme='http://www.blogger.com/atom/ns#' term='Advanced'/><category scheme='http://www.blogger.com/atom/ns#' term='match'/><category scheme='http://www.blogger.com/atom/ns#' term='Enumeration'/><category scheme='http://www.blogger.com/atom/ns#' term='matching'/><category scheme='http://www.blogger.com/atom/ns#' term='manifest'/><category scheme='http://www.blogger.com/atom/ns#' term='contravariance'/><title type='text'>Overcoming Type Erasure in Matching 2 (Variance)</title><content type='html'>A commenter (Brian Howard) on the post &lt;a href="http://daily-scala.blogspot.com/2010/01/overcoming-type-erasure-in-matching-1.html"&gt;Overcoming Type Erasure in Matching 1&lt;/a&gt; made a very good point:&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;Is there a way to deal with some type arguments being contravariant? Try the following:&lt;br /&gt;&lt;br /&gt;class A&lt;br /&gt;&lt;br /&gt;class B extends A&lt;br /&gt;&lt;br /&gt;val AAFunction = new Def[Function1[A,A]]&lt;br /&gt;&lt;br /&gt;((a:A) =&gt; a) match {case AAFunction(f) =&gt; Some(f(new A)); case _ =&gt; None} // this is OK&lt;br /&gt;&lt;br /&gt;((a:A) =&gt; new B) match {case AAFunction(f) =&gt; Some(f(new A)); case _ =&gt; None} // this is OK&lt;br /&gt;&lt;br /&gt;((b:B) =&gt; b) match {case AAFunction(f) =&gt; Some(f(new A)); case _ =&gt; None} // gives a ClassCastException, since new A is not a B&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;There is a way to do this, however the information is not captured in the Manifest.  A manifest is not designed to do full reflection it is by design very light and has little impact on performance.  So to provide the functionality requested by Brian one needs to add that information to the Extractor Definition.  Have have a possible solution below.&lt;br /&gt;&lt;code&gt;&lt;div class="codelist"&gt;&lt;ol class="codelist"&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;A&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;A&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;B&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;A&lt;/li&gt;&lt;li class="codelist alt"&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;B&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;object&lt;/span&gt;&amp;#160;Variance&amp;#160;&lt;span class="key"&gt;extends&lt;/span&gt;&amp;#160;Enumeration&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;Co,&amp;#160;Contra,&amp;#160;No&amp;#160;=&amp;#160;Value&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;module&amp;#160;Variance&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;Variance._&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="key"&gt;import&lt;/span&gt;&amp;#160;Variance._&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Def&lt;span class="type-param"&gt;[C]&lt;/span&gt;(variance:Variance.Value*)(implicit&amp;#160;desired&amp;#160;:&amp;#160;Manifest&lt;span class="type-param"&gt;[C]&lt;/span&gt;)&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;&lt;span class="magic"&gt;unapply&lt;/span&gt;&lt;span class="type-param"&gt;[X]&lt;/span&gt;(c&amp;#160;:&amp;#160;X)(implicit&amp;#160;m&amp;#160;:&amp;#160;Manifest&lt;span class="type-param"&gt;[X]&lt;/span&gt;)&amp;#160;:&amp;#160;Option&lt;span class="type-param"&gt;[C]&lt;/span&gt;&amp;#160;=&amp;#160;{&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;typeArgsTriplet&amp;#160;=&amp;#160;desired.typeArguments.zip(m.typeArguments).&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;zipWithIndex&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;sameArgs&amp;#160;=&amp;#160;typeArgsTriplet&amp;#160;forall&amp;#160;{&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;((desired,actual),index)&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(getVariance(index)&amp;#160;==&amp;#160;Contra)&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;desired&amp;#160;&amp;lt;:&amp;lt;&amp;#160;actual&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;((desired,actual),index)&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(getVariance(index)&amp;#160;==&amp;#160;No)&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;desired&amp;#160;==&amp;#160;actual&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;((desired,actual),index)&amp;#160;=&gt;&amp;#160;&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;desired&amp;#160;&gt;:&gt;&amp;#160;actual&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;isAssignable&amp;#160;=&amp;#160;desired.erasure.isAssignableFrom(m.erasure)&amp;#160;||&amp;#160;(desired&amp;#160;&gt;:&gt;&amp;#160;m)&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;&amp;#160;(isAssignable&amp;#160;&amp;amp;&amp;amp;&amp;#160;sameArgs)&amp;#160;Some(c.asInstanceOf&lt;span class="type-param"&gt;[C]&lt;/span&gt;)&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;None&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&lt;span class="key"&gt;def&lt;/span&gt;&amp;#160;getVariance(i:&lt;span class="basicType"&gt;Int&lt;/span&gt;)&amp;#160;=&amp;#160;&lt;span class="key"&gt;if&lt;/span&gt;(variance.length&amp;#160;&gt;&amp;#160;i)&amp;#160;variance(i)&amp;#160;&lt;span class="key"&gt;else&lt;/span&gt;&amp;#160;No&lt;/li&gt;&lt;li class="codelist alt"&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;|&amp;#160;}&lt;/li&gt;&lt;li class="codelist "&gt;defined&amp;#160;&lt;span class="key"&gt;class&lt;/span&gt;&amp;#160;Def&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;&lt;span class="key"&gt;val&lt;/span&gt;&amp;#160;AAFunction&amp;#160;=&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;Def&lt;span class="type-param"&gt;[Function1&lt;/span&gt;&lt;span class="type-param"&gt;[A,A]&lt;/span&gt;]&lt;/li&gt;&lt;li class="codelist alt"&gt;AAFunction:&amp;#160;Def&lt;span class="type-param"&gt;[(A)&amp;#160;=&amp;gt;&amp;#160;A]&lt;/span&gt;&amp;#160;=&amp;#160;Def&lt;span class="annotation"&gt;@&lt;/span&gt;64a65760&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;((a:A)&amp;#160;=&gt;&amp;#160;a)&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;AAFunction(f)&amp;#160;=&gt;&amp;#160;Some(f(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;A));&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;None}&lt;/li&gt;&lt;li class="codelist "&gt;res0:&amp;#160;Option&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;=&amp;#160;Some(A&lt;span class="annotation"&gt;@&lt;/span&gt;1bd4f279)&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;/li&gt;&lt;li class="codelist "&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;((a:A)&amp;#160;=&gt;&amp;#160;&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;B)&amp;#160;&lt;span class="key"&gt;match&lt;/span&gt;&amp;#160;{&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;AAFunction(f)&amp;#160;=&gt;&amp;#160;Some(f(&lt;span class="key"&gt;new&lt;/span&gt;&amp;#160;A));&amp;#160;&lt;span class="key"&gt;case&lt;/span&gt;&amp;#160;_&amp;#160;=&gt;&amp;#160;None}&lt;/li&gt;&lt;li class="codelist alt"&gt;res1:&amp;#160;Option&lt;span class="type-param"&gt;[A]&lt;/span&gt;&amp;#160;=&amp;#160;None&lt;/li&gt;&lt;li class="codelist "&gt;&lt;/li&gt;&lt;li class="codelist alt"&gt;&lt;span class="repl"&gt;scala&gt;&lt;/span&gt;&amp;#160;((b:B)&amp;#160;=&gt;&amp;#160;b)&amp;#160;&lt;s
