Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for...

60
Architecture of So-ware Systems Func5onal Programming Jan Michelfeit 2017

Transcript of Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for...

Page 1: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

ArchitectureofSo-wareSystemsFunc5onalProgramming

JanMichelfeit

2017

Page 2: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalProgramming

•  WhyshouldIcare?•  Whatisit?•  Prac5calfunc5onalprogramming

•  Func5onalprinciplesinso-warearchitecture

•  Advancedtopics•  Takeaways

Page 3: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

WHYFUNCTIONALPROGRAMMING?

Page 4: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

What’swrongwiththesesnippets?DateFormatformat=newSimpleDateFormat("yyyy-MM-dd");ExecutorServicethreadPool=Executors.newFixedThreadPool(5);List<Future<Date>>results=newArrayList<>();for(inti=0;i<10;i++){results.add(threadPool.submit(()->format.parse("2017-10-22")));}for(Future<Date>result:results){System.out.println(result.get());}

classPerson{privateStringname;//…@Overridepublicbooleanequals(Objecto){…}@OverridepublicinthashCode(){…}}Set<Person>set=newHashSet<>();Personp=newPerson();set.add(p);p.setName("Daniel");

voidprintItems(Iterator<String>items){intitemsCount=Iterators.size(items);for(inti=0;i<itemsCount;i++){System.out.println(items.next());}}

Page 5: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

What’swrongwiththesesnippets?DateFormatformat=newSimpleDateFormat("yyyy-MM-dd");ExecutorServicethreadPool=Executors.newFixedThreadPool(5);List<Future<Date>>results=newArrayList<>();for(inti=0;i<10;i++){results.add(threadPool.submit(()->format.parse("2017-10-22")));}for(Future<Date>result:results){System.out.println(result.get());}

classPerson{privateStringname;//…@Overridepublicbooleanequals(Objecto){…}@OverridepublicinthashCode(){…}}Set<Person>set=newHashSet<>();Personp=newPerson();set.add(p);p.setName("Daniel");

voidprintItems(Iterator<String>items){intitemsCount=Iterators.size(items);for(inti=0;i<itemsCount;i++){System.out.println(items.next());}}

Doesset.contains(p)returnstrue?

Doesthisprintanything?

Doesthisthrowanexcep5on?

Page 6: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

What’swrongwiththesesnippets?DateFormatformat=newSimpleDateFormat("yyyy-MM-dd");ExecutorServicethreadPool=Executors.newFixedThreadPool(5);List<Future<Date>>results=newArrayList<>();for(inti=0;i<10;i++){results.add(threadPool.submit(()->format.parse("2017-10-22")));}for(Future<Date>result:results){System.out.println(result.get());}

classPerson{privateStringname;//…@Overridepublicbooleanequals(Objecto){…}@OverridepublicinthashCode(){…}}Set<Person>set=newHashSet<>();Personp=newPerson();set.add(p);p.setName("Daniel");

voidprintItems(Iterator<String>items){intitemsCount=Iterators.size(items);for(inti=0;i<itemsCount;i++){System.out.println(items.next());}}

set.contains(p)returnsfalsebecauseofhashCode()behavior

NoSuchElementExcep5on(Iteratorreuse)

Works…orNumberFormatExcep5on:mul5plepoints…orNumberFormatExcep5on:Forinputstring:"101101.E101E22”…orArrayIndexOutOfBoundsExcep5on:-1(DateFormatisnotthread-safe)

Page 7: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

What’swrongwiththesesnippets?

•  Whatdidtheexampleshaveincommon?– Mutablestate

•  Doyoulikeglobalvariables?•  ShouldStringbemutable?

Mutablestatecanmakethingsreallyhardtoreasonabout,debug,…

Page 8: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalProgramming

•  Basicidea:– avoidmutablestateandside-effects– composeprogramsfromfuncDonsthatalwaysgivethesameresultforthesamearguments

•  Advantages–  leadstocodethatissafer,modular,composable– easiertoreasonabout,test,anddebug– wellsuitedforparallelizaDon

Page 9: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

WHATISFUNCTIONALPROGRAMMING?

Page 10: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

BasicTerminologyImmutability

–  Datastructure(object)isimmutableifit's(observable)statecannotbemodifiedaReritiscreated.

–  Examples(Java):String,ImmutableList(Guavalibrary),anyclasswithallfieldsfinal&immutable

ReferenDaltransparency–  Anexpressioneisreferen5allytransparentifforallprogramspeveryoccurrenceofeinpcanbereplacedwiththeresultofevaluaDnge,withoutaffec5ngtheobservableresultofp.

–  E.g.,replacealloccurrencesof“1+2”with“3”–  Allowscrea5onoflocalstate,aslongasit'snotobservable

Page 11: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

BasicTerminologyPurefuncDon

–  FuncDonfispureiftheexpressionf(x1,…,xn)isreferen5allytransparentforallreferen5allytransparentinputsx1,…,xn

–  Func5onoutputmaydependonlyonarguments,notonexternalmutablestate

–  Typically"noside-effects"-onlyobservableoutputshouldbethereturnvalue

–  Example:mathema5calfunc5ons(sin,max,+,...)

Sideeffect–  Modifiesstateoutsideofitsscope,orhasanobservableinterac5on

withitscallingfunc5onsortheoutsideworld–  examples

•  reassigningavariable,modifyingadatastructureinplace•  throwinganexcep5onorhal5ngwithanerror(dependsoncontext)•  userinterac5on•  reading/wri5ngafile

Page 12: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

ProgrammingParadigmsImperaDveProgramming

•  Program:sequenceofcommandschangingstate•  Commandsusuallydon'thavevalue=>dataexchangedthroughstate

•  “Func5ons”–subrou5nes(unitofmodularity)•  Func5oninvoca5oncangivedifferentresultsatdifferent5mes–  dependingonthestateoftheexecu5ngprogram

•  Closertohardware/tradi5onalprogrammerthinking

Page 13: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

ProgrammingParadigms(Pure)FuncDonalProgramming

•  Modelscomputa5onastheevaluaDonofexpressions,usingpurefuncDonsandimmutabledata

•  Avoidsmutablestateandside-effects

Page 14: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

ProgrammingParadigms(Pure)FuncDonalProgramming

•  BasedonLambdaCalculus–  Turing-completecomputa5onmodel

•  (Closertohumanthinking(unlessobfuscated))•  SpecialcaseofdeclaraDveprogramming–  expressesthelogicofacomputa5onwithoutdescribingitscontrolflow

–  describingwhattheprogrammustaccomplish,ratherthanhow

–  e.g.,HTML,Excel,mostpartsoffunc5onallanguages

Page 15: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

FuncDonsasfirst-classciDzens– canbepassedasargumentstootherfunc5onsorbereturnedasaresultofafunc5on

–  func5onsaccep5ngand/orreturningfunc5onsarehigher-orderfuncDons

List("list","of","words").map(word=>word.length)//List(4,2,5)

valf=(x:Int)=>-xvalg=f.compose((x:Int)=>x*x)g(3)//-9

TypicalFeaturesofFunc5onalLanguages

Func5on(String)=>Int

Page 16: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

TypicalFeaturesofFunc5onalLanguagesLazyevaluaDon– expressionevalua5ondelayedun5lthevalueisneeded

– evalua5onorderisirrelevantwithpurefunc5ons(noside-effectcaneverchangeexpressionvalue)--infinitedatastructurenumsFromn=n:numsFrom(n+1)take5(numsFrom0)--result:[0,1,2,3,4]

Source.fromFile("numbers.txt").map(line=>line.toInt).exists(n=>n<0)//fileisreadonlyuntilfirstnegativenumber

Page 17: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalProgrammingAdvantagesParallelwithstructuredvs.unstructuredprogramming:•  Structuredprogrammingforbids

–  goto–  mul5pleentriesorexitsfromablockofcode

=>seeminglylesspower?

But:–  encouragesmodulardesign=>simpler,smallermodules

•  easier,quickertocode•  easiertoreuse•  easiertotest

–  mathema5callymoretractable(easiertoanalyze,tooling)

Page 18: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalProgrammingAdvantagesIFPforbidsside-effectsinfunc5ons,mutablevariables•  seeminglylesspower?

But:•  Lackofsideeffectseliminatesamajorsourceofbugs•  Evalua5onorderirrelevant

–  parallelizaDonfriendly–  enablesprac5callazyevaluaDon

•  Higherorderfunc5ons&lazyevalua5onareanew"glue"forcomposiDonofmodules

Page 19: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalProgrammingAdvantagesIIFPforbidsside-effectsinfunc5ons,mutablevariables•  seeminglylesspower?

But:•  encouragesevenbeXermodularizaDon,composability•  easiertesDng(inputvaluesdetermineoutput,avoidssetupofstate)•  declaraDve(capturesinten5on),usuallymoreconsciousand

understandable(unlessobfuscated)•  immutabledatastructures-thread-safe,cacheable•  mathema5callymoretractable•  easierdebugging,...

Page 20: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

PRACTICALFUNCTIONALPROGRAMMING

Page 21: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Sum-Impera5vely

•  Whyisthisnotfunc7onal?•  Mutablevariablesresult,i(butnoexternallyvisiblestate)

privateintsum(List<Integer>list){intresult=0;for(inti=0;i<list.size();i++){result+=list.get(i);}returnresult;}

Page 22: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Sum-func5onally

defsum(list:List[Int]):Int={if(list.empty)0elselist.head+sum(list.tail)}

privateintsum(List<Integer>list){intresult=0;for(inti=0;i<list.size();i++){result+=list.get(i);}returnresult;}

Func5onalversion?(Hint:thinkofmathema7calinduc7on)

Page 23: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Count-func5onally

defcount(list:List[Int]):Int={if(list.empty)0else1+count(list.tail)}

Func5onalversionofcompu5nglistsize?

defsum(list:List[Int]):Int={if(list.empty)0elselist.head+sum(list.tail)}

Page 24: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Generalizing…

•  Whatwasspecificforsum()?– 0and+

defsum(list:List[Int]):Int={if(list.empty)0elselist.head+sum(list.tail)}

Page 25: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Fold

deffoldRight(list:List[Int],initial:Int,op:(Int,Int)=>Int):Int={if(list.isEmpty)initialelseop(list.head,foldRight(list.tail,initial,op))}

Page 26: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

UsingFold

defsum(list:List[Int])=foldRight(list,0,(a,b)=>a+b)defprod(list:List[Int])=foldRight(list,1,(a,b)=>a*b)defcount(list:List[Int])=foldRight(list,0,(a,b)=>1+b)defexists(list:List[Int],condi5on:Int=>Boolean)=foldRight(list,false,(n,b)=>condiDon(n)||b)defcopy(list:List[Int])=foldRight(list,List(),(n,list)=>n+:list)

Page 27: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Fold-Observa5ons

•  foldRight()isahigher-levelfunc5on•  sum(),count(),…arecomposedfromsmallerreusablebuildingblocks

•  IsthispossibleinJava?– yes,butfunc5onallanguagemadethemodulariza5oneasierandmoreobvious

–  funcDonalthinkingismoreimportantthanapar5cularlanguage

•  No5cethesimilaritywithalgebra(monoid)

Page 28: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

TypicalOpera5onsonCollec5onsImperaDveprogramming:add(),get(),set()/put()FuncDonalProgramming(examplesforTraversable[T]inScala–e.g.,List[T];simplified)•  map(f:A=>B):Traversable[B]•  flatMap(f:A=>Traversable[B]):Traversable[B]•  filter(f:A=>Boolean):Traversable[B]•  foldLeR(zero:B)(op:(B,A)=>B):B•  foldRight(),fold()•  head:A•  tail:Traversable[A]•  groupBy(f:A=>K):Map[K,Traversable[A]]•  ++(t:Traversable[A]):Traversable[A]•  ...manymore-take(),drop(),takeWhile(),slice(),zip(),grouped(),...•  Methodsdonotchangeinputs,butreturnnewcollecDonsasresult!•  ComputaDonmaybelazy

Page 29: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Collec5onsOpera5ons-Examples

defsum(list:List[Int])=list.foldRight(0)((a,b)=>a+b)defprod(list:List[Int])=list.foldRight(1)((a,b)=>a*b)defcount(list:List[Int])=list.foldRight(0)((a,b)=>1+b)defexists(list:List[Int],condi5on:Int=>Boolean)=list.foldRight(false)((n,b)=>condiDon(n)||b)defcopy(list:List[Int])=list.foldRight[List[Int]](List())((n,list)=>n+:list)

ProperScalasyntaxforsum(),prod(),…

Page 30: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Collec5onsOpera5ons-ExamplesPrintallmiddlenames(JavaScript)

varnames=["JamesPaulMcCartney","WilliamBradleyPin","LauraWitherspoon","HannahDakotaFanning"];names.map(func5on(name){returnname.split("");}).filter(func5on(parts){returnparts.length>=3;}).map(func5on(parts){returnparts[1];}).forEach(log)//forEachnotfunc5onal!!

Page 31: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Collec5onsOpera5ons-ExamplesGetlengthofthelongestword(Scala)

vallines=List("Scalacollections","havenicemethods")lines.flatMap(line=>line.split("").toList)//List(Scala,collections,have,nice,methods).map(word=>word.length)//List(5,11,4,4,7).fold(-1)(Math.max)//11

lines.map(line=>line.split("").toList)//List(List(Scala,collections),List(have,nice,methods)).map(x=>x.length)//List(2,3)

Page 32: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

FP-orientedLanguages•  Haskell•  Scala•  F#•  Erlang•  R•  …•  Somefeaturesintradi5onalOOlanguages–  Java8,LINQ,C++11

Page 33: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

GoingParallel-Impera5veHowtomakethisparallel?Generalapproach:1.  (Recursively)splittosubtasks2.  Executesubtasksinparallel3.  Re-combineresultsofsubtasks

privateintsum(List<Integer>list){intresult=0;for(inti=0;i<list.size();i++){result+=list.get(i);}returnresult;}

Page 34: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

GoingParallel-Impera5veDoesthiswork?No!Accesstomutablevariableresultisnotsynchronized

–  Resultswillbenon-determinis5c

privateintresult;publicintsum(List<Integer>list){result=0;for(Integern:list){threadPool.submit(()->result+=n);}//...waitfortasksfinished...returnresult;}

Page 35: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

GoingParallel-Func5onal

InScala:Internally:1.  Recursivelysplitslist2.  Foldseachpartinparallel3.  Appliesfoldopera5ontopar5alresults

list.par.sum

list.par.fold(0)((a,b)=>a+b)

Page 36: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

GoingParallel-Func5onal•  Combiningpar5alresultsmaybenon-determinis5c

–  E.g.List(1,2,3,4):(((0+1)+2)+3)+4or((0+1)+2)+((0+3)+4)

•  =>Foldopera5onmustbeassociaDve–  (a+b)+c=a+(b+c)–  remembermonoid

•  No5ceweusedfold()insteadoffoldRight() –  fold() expectsassocia5veopera5on

•  Exercise:tryparallelizingimpera5ve&func5onalQuickSort

Page 37: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

GoingParallel-Takeaways

•  Paralleliza5oncangetcomplex,frameworkshelp•  Sideeffects&parallelismmayleadtonon-determinism•  ParallelaccesstomutablestaterequiressynchronizaDon

–  e.g.AtomicInteger, ConcurrentHashMap,synchronized,…

–  synchroniza5oniscostly•  Non-associa5vere-combina5onofresultsmayleadtonon-determinism

–  (commuta5vityisnotrequired)

•  Paralleliza5onwithimmutabledataismucheasier&efficient–  avoidssynchroniza5on

Page 38: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

FUNCTIONALPRINCIPLESINSOFTWAREARCHITECTURE

Page 39: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalPrinciples

•  Statelessness•  Immutability&paralleliza5on•  Func5onalAPIs

Page 40: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

MapReduce

•  Frameworkforparallelprocessingofbigdata(mul5-terabyte)onlargeclustersofcommodityhardware

•  ExecutesMapReducejobs1.  Splitinputdata(onadistributedfilesystem)into

records2.  Processeachrecordwithamaptask

(consideringdatalocality)

3.  Mergeresultswithareducetask

Page 41: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

•  map:(K1,V1)=>List[(K2,V2)];•  reduce:(K2,List[V2])=>List[V3]

Page 42: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

MapReduce-Observa5ons

•  Distributedcomputa5on– nosharedmemory=>cannotsharestate

•  Mapandreducearehigher-levelfunc5ons– mappersandreducersarefirstclassci5zens,preferablyimmutable

•  Theprinciplecanbeappliedevenwhenprogrammingwiththreads– basicallyparallelmap()+fold()(orreduce())

Page 43: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

MapReduce–Example

•  Wordcount– Map:foreachwordemittuple(word,1)–  Reduce:Sum1sforeachword

•  Higherlevelframeworkso-enusedinprac5ce-e.g.Scalding

classWordCountJob(args:Args)extendsJob(args){TypedPipe.from(TextLine(args("input"))).flatMap{line=>line.toLowerCase.split("\\s+")}.groupBy{word=>word}//useeachwordforakey.size//ineachgroup,getthesize.write(TypedText.tsv[(String,Long)](args("output")))}

Page 44: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

StatelessComponents•  ServiceStatelessnessprinciple

–  “Guidelinesinfavorofmakingtheservicestatelessbyshi-ingawaythestatemanagementoverheadfromtheservicestosomeotherexternalarchitecturalcomponent”(wiki)

•  Statecanbeexternalizedtoadedicatedcomponent(database,distributedin-memorycache,...)

•  Why–  lowercomponentcomplexity–  makeshighavailabilityandhorizontalscalingeasier

•  E.g.,consideracustomer-facingwebserverands5ckysessions

•  Whynot–  canincreaseoverallsystemcomplexity–  affectsperformance,response5mes

Page 45: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalFrameworkAPIS

E.g.,D3.js

d3.selectAll("p").style("color","white");

varparagraphs=document.getElementsByTagName("p");for(vari=0;i<paragraphs.length;i++){varparagraph=paragraphs.item(i);paragraph.style.setProperty("color","white",null);}

d3.selectAll("p").style("color",function(d,i){returni%2?"#fff":"#eee";});

Page 46: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

ADVANCEDTOPICS

Page 47: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Side-effectsinPrac5ce

•  FPdiscouragesside-effects– Butwhatabouttheuser?Whatcantheprogramdo?

•  Somelanguagesallowside-effectsasprogrammer’sresponsibility

•  PureFPlanguages(e.g.,Haskell)allowonlyexplicitside-effectswrappedasmonads

Page 48: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Monad

•  RepresentsacomputaDonwithasequenDalstructureandpossibleside-effect– Defineswhatitmeanstochainopera5onstogether

•  Allowsrefactoringside-effectsoutoffunc5ons•  “Promise”toproduceavalueofacertaintype•  Allowssepara5ngcomputa5ondescrip5onandexecu5on

Page 49: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Monad

•  Formally:typeconstructor,bind&returnopera5ons,monadlaws[1],[2]

•  Informally:–  genericdatastructureM[A] – withconstructorof(): A => M[A] – Opera5on flatMap() : (A=>M[B]) => M[B]

•  E.g.,Optional<T>inJava:–  static <T> Optional<T> of(T value) –  Optional<U> flatMap( Function<T, Optional<U>> mapper)

Page 50: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Monad-Examples

•  I/OMonadinHaskell–wrapsallcomputa5onswithaglobaleffect–  getChar :: IO Char

•  purefunc5onthatreturnsaside-effec5ngcomputa5on•  doesnotnecessarilycauseanimmediateeffect•  =>canbeusedinanotherpurefuncDon

–  putChar :: Char -> IO () •  Scala–  Option[T], Future[T], Set[T], List[T]

•  LINQoperators-e.g.,M<T> SelectMany(this M<S> src, Func<S, M<T>> f)

Page 51: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Monad-ExamplesobjectOrderService{defloadOrder(username:String):Future[Order]=???}objectPurchaseService{defpurchase(order:Order):Future[PurchaseResult]=???deflogPurchase(result:PurchaseResult):Future[LogResult]=???}vallogResult=OrderService.loadOrder("customerUsername").flatMap(order=>PurchasingService.purchase(order)).flatMap(result=>PurchaseService.logPurchase(result))

Page 52: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

ReplacingImpera5veLoops

publicintfactorial(intn){intresult=1;while(n>0){result*=n--;}returnresult;}

Howtoreplacemutablevariables?deffactorial(n:Int)={if(n==1)1elsen*factorial(n-1)}

Page 53: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Recursion

•  Evalua5on:–  factorial(4)–  4 * factorial(3)–  4 * (3 * factorial(2))–  4 * (3 * (2 * factorial(1)))–  4 * (3 * (2 * 1))–  4 * (3 * (2))–  4 * (6)–  24

•  Stacksizedependentoninputargument

deffactorial(n:Int)={if(n==1)1elsen*factorial(n-1)}

Page 54: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

TailRecursion•  TailrecursivefuncDon-recursiveac5onasthelastac5on

–  variablesonthestackwillnolongerbeused•  =>Compilercanreplacerecursionwithaloop•  Howtopassintermediateresults?

–  “Accumulator”argument

•  Evalua5on:–  factorial(4,1)->factorial(3,4)->factorial(2,12)->factorial(1,24)->24

deffactorial(n:Int,accumulator:Int=1)={if(n==1)accumulatorelsefactorial(n–1,accumulator*n)}

Page 55: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

CONCLUSION&TAKEAWAYS

Page 56: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Func5onalProgramming-Comparison

ImperaDve FuncDonalBasicunit Command ExpressionComputa5on Commandexecu5on Expressionevalua5onMutability Mutabledata ImmutabledataSide-effects Allowed ExternalizedviaMonadsFunc5on Unitofmodularity;

candependonexternalstate

Purefunc5on;cannotdependonexternalstate

Programdescribes

Howtoaccomplishatask

Whattoaccomplish

Page 57: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

Cons&Pixalls•  Func5onallanguagemaybemoredistanttoatradi7onalprogrammer's

thinking–  Func5onalcodecanbeobfuscatedbytheprogrammer(bewareof“write-only”code)

•  Possiblestackoverflowsifrecursionusedwrong–  Usetailrecursionifthelanguagesupportsit

•  Nega5veimpactonperformanceifusedwrong–  Non-tailrecursionhasacost–  Memoryalloca5ons&garbagecollec5onofmanyimmutableobjects(but:short-lived

immutableobjectsmaybebenerforGCthanlong-livedmutableobjects)–  hnp://flyingfrogblog.blogspot.cz/2016/05/disadvantages-of-purely-func5onal.html

•  Somealgorithmshardtowriteefficiently–  SomeproblemssolvableinO(n)5mewithstatemuta5oncanrequireΩ(nlogn)5mein

pure,non-lazyfunc5onallanguage

•  Difficulttopredictthe5meandspacecostsofevalua5ngalazyfunc5onalprogram•  Butremember:prematureopDmizaDonistherootofallevil[1],[2]

Page 58: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

WhyFunc5onalProgramming

•  Features– Avoidsmutablestateandside-effects– New"glue"forcomposi5on:func5onsasfirst-classci5zens,lazyevalua5on

– Declara5ve•  Paralleliza5onfriendly•  Thread-safe,cacheabledatastructures•  Purefunc5onsaresafer,modular,composable•  Easiertoreasonabout,test,anddebug

Page 59: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

FurtherReading•  Func5onalProgramminginScala(Chiusano&Bjarnason)

(book)•  Seriesofar5clesbyLiborŠkarvada•  WhyFunc5onalProgrammingManers(Hughes)(paper)•  Func5onalprogramminginJavaScriptinEloquentJavaScript(book

chapter)•  Haskelldocumenta5on•  ComparisonofFunc5onal,Declara5veandImpera5ve

programmingonStackOverflow•  ProgramminginScala(2008,bookavailableonline)•  Scalacheatsheets:one,another

Page 60: Jan Michelfeit - cvut.cz · • Higher order func5ons & lazy evaluaon are a new "glue" for composion of modules Func5onal Programming Advantages II ... (JavaScript) var names = [

TheEnd…