RubyConf Argentina 2014
Look ma’, I knowmy algorithms!
View Slide
Lucia Escanellasraviolicode
Attributionshttps://flic.kr/p/6DDvQP https://flic.kr/p/qv5Zphttps://flic.kr/p/6SaZsP https://flic.kr/p/edauSNhttps://flic.kr/p/4uNfK8 https://flic.kr/p/o9ggdkhttps://flic.kr/p/6kfuHzhttps://flic.kr/p/5kBtbS
SpeedSpeed
Zen EleganceElegance
Toolbox
TheoryTheory
This exampleNot so common
FROM >30HSTO 18 S
WHY USE ORDERS?ALGORITHMS ARE POWERFULAVOID TRAPS IN RUBY
WHY USING ORDERS?ALGORITHMS ARE POWERFULAVOID TRAPS IN RUBY
Let’s have a look at thePROBLEM
Ordered arrayHow many pairs (a,b) wherea ≠ b-100 <= a + b <= 100
Array: [-100, 1, 100]
Array: [-100, 1, 100](-100, 1), (-100, 100), (1, 100)
Array: [-100, 1, 100](-100, 1), (-100, 100), (1, 100)-100 + 1 = 99 YES
Array: [-100, 1, 100](-100, 1), (-100, 100), (1, 100)-100 + 100 = 0 YES
Array: [-100, 1, 100](-100, 1), (-100, 100), (1, 100)1 + 100 = 101 NO
Array: [-100, 1, 100](-100, 1), (-100, 100), (1, 100)Result: 2
First solutionCombinations of 2 elementsFilter by: -100 <= a + b <= 100
def count!combinations = @numbers.combination(2).to_a!!combinations!.map{ |a,b| a + b }!.select do |sum|!sum.abs <= THRESHOLD!end.size!end
10K takes10sBUT100M takes30hs
Time to buy aNEWLAPTOP!
Big O notationHow WELL an algorithmSCALESas theDATA involvedINCREASES
Calc Array size (length=N)Count elements one by one: O(N)
Calc Array size (length=N)Count elements one by one: O(N)Length stored in variable: O(1)
Graphical Math PropertiesOrderMathematicalProperties
Remember:f < g => O(f + g) = O(g)O(K . f) = O(f)O(1) < O(ln N) < O(N) < O(N2) < O(eN)
Ex: Binary SearchFind 7 in [1, 2, 3, 4, 5, 6, 7, 8]1. element in the middle is 52. 5 == 7 ? NO3. 5 < 7 ? YES => Find 7 in [6, 7, 8]Step 1
!Find 7 in [0, 1, 2, 3, 4, 5, 6, 7, 8]1. element in the middle is 72. 7 == 7 ? YES!FOUND IT!!Step 2
Ex: Binary SearchWorst case: ceil ( Log2 N ) 23 = 8ONLY 3 steps
Typical examplesAccess to a Hash O(1)Binary search O(log N)Sequential search O(N)Traverse a matrix NxN O(N2)
DON’T JUST BELIEVE MEfooplot.com
BUT raviolicode,I’m getting BORED
I WANT CONCURRENCYI WANT CONCURRENCY
wait… was itConcurrency? orParallelism?
GIL+CPU-boundNO I/O OPERATIONSconcurrency = OVERHEAD
NOT what Iwasexpecting
Parallelism...Parallelism
What do weREALLY get?O(N2/ cores) = O(N2)jRubyGoScala
NO SpoilersO(N2) O(N.log(N)) O(N)
THINKING algorithmsis as IMPORTANTas ANY OTHER technique
BYE.
Wait! It's still slow.Wait! It’s still SLOW
Given [1,2,3,4,5]Take 1, then print [5,4,3,2]Take 2, then print [5,4,3]and so on…
What’s the ORDER of this code?@nums.each_with_index do |a,i|!! puts @nums.slice(i+1,N).reverse!.inspect!end
What’s the ORDER of this code?@nums.each_with_index do |a,i|!! puts @nums.slice(i+1,N).reverse!.inspect!endLooks like O(N)
What’s the ORDER of this code?@nums.each_with_index do |a,i|!! puts @nums.slice(i+1,N).reverse!.inspect!end Behaves like O(N2)
Let’s Lookat the DOCSRuby-Doc.org!#reverse
O(N) hidden!O(N)!
What’s the ORDER of this code?@nums.each_with_index do |a,i|!! puts @nums.slice(i+1,N).reverse!.inspect!endO(N2)!
Leaky abstractionsLEAKY ABSTRACTIONS
All Non-trivialabstractionsare LEAKY to some degree
ABSTRACTIONSDO NOT reallySIMPLIFYas they were meant to
KnowingTHEALGORITHMSBehind everyday methodsPAYS OFF
Thanks :)Thanks :)