Seminar Javascript Pattern and Anti-Patterns

Functional Patterns & 

Functional Reactive Programming

David Dao

Technical University Munich

Refactored CODE

Refactored:

https://github.com/emepyc/tnt.tree (BioJS Tree Component)

https://github.com/pasierb/flickr-gallery (Flickr Gallery)

Some more components ...

FRP Created:

http://daviddao.github.io/functional-vis-example/src/table.html

AGENDA

Functional Patterns

- What is Functional Programming?

- Pure Functions / Functionals

- Function Compositions

- Currying

- Partials

 

 

Functional Reactive Programming

- Concept 

- Example Applications

 

Let's Say we have A, And we Want D.

How do we get there?

1. Option: Take A and Hammer it to

2. Option: TRANSFORM -> B, B -> C, C -> D 

Turing Machine Style
Lambda Calculus Style

TRANSFORM -> B, B -> C, C -> D 

Express the result in terms of the inputs, rather than starting from the input and crafting your way to the result

Express what the program should do,
not how

http://www.slideshare.net/ScottWlaschin/fp-patterns-buildstufflt

What is Functional Programming? 

Definition
Functional programming is a programming paradigm, that treats computation as the evaluation of mathematical functions and avoids changing-state and mutable data (Pure functions).

 

It is a declarative programming paradigm, which means programming is done with expressions.

Source: http://en.wikipedia.org/wiki/Functional_programming

are Functional Patterns Different from OO?

JavaScript 101 - Functions

Core Principle in FP #1

Pure Functions

Loops have bad SIgnal/NOISE RATIO

// Original method
var members = [];
for(var i = 0, len = nodes.length; i < len; i++) {
  // up until here all 'how'
  // the isMember bit is the only thing specific
  // everything else generic to all filters
  if(nodes.isMember) {
    members.push(node);
  }
}

Loops describes HOW not WHAT we have to do to get D.

Result: A lot of boilerplate code!

FILTERING WITH FUNCTIONalS

The better Loop

// Refactored
var isMember = function(u) { return u.isMember };
var members = nodes.filter(isMember);

Split the filtering code from the filter.

  • filter: [A], (A -> Boolean) -> [A]

Takes a data array and a function returning a boolean. Returns a transformed data array.

MAPPING With FUNCTIONALS

// extracting some data from each node
var nodes_names = nodes.map(function(node) { return node.name });

// a calculation for each node
var distanceFromMeanBranchLength = nodes.map(function(node) {
  return Math.abs(node.branchLength - meanBranchLength);
});

Have some As, want some Bs

Common tasks: access all els properties

Map: [A], (A -> B) -> [B] 

REDUCING With FUNCTIONALS

// simple arithmetic
var totalDistance = nodes.reduce(function(sum,node) {
  return sum + node.branchLength
},0);

// creating strings
var userList = users.reduce(function(html,user) {
  return html + "<li>" + user.name + "</li>"
},"");

Have a list of As, create a single B from them

Reduce: [A], (A -> B) -> B

Recursive, we return a B at every stage

fold: we're folding the list down to one thing

USAGE: ONE LINE LOOKUP FUNCTION

// Functional method
function index(obj,i) {return obj[i]}


'a.b.c'.split('.').reduce(index, {a: {b: {c: "hello!"}}}) // => "hello"

MORE FUNCTIONALS!

filter: [A], (A -> Boolean) -> [A]

map: [A], (A -> B) -> [B]

reduce: [A], (A -> B) -> B

some: [A], (A -> Boolean) -> Boolean

every: [A], (A -> Boolean) -> Boolean

forEach: [A], (A -> Any) -> undefined

Benefits of Pure Functions

FUNCTIONAL COMPOSITION

f (g(x))
f(g(x))f (g(x))

Core Principle in FP #2

Definition
Function composition is the pointwise application of one function to
the result of another to produce a third function.

FUNCTIONAL COMPOSITION

var compose = function(f,g) {
  return function(x) {
    return f(g(x));
  };
};

var toUpperCase = function(x) { return x.toUpperCase(); };
var exclaim = function(x) { return x + '!'; };
var shout = compose(exclaim, toUpperCase);

shout("functional composition rocks");
//=> "FUNCTIONAL COMPOSITION ROCKS!"
f (g(x))
f(g(x))f (g(x))

FUNCTIONAL COMPOSITION

f (g(x))
f(g(x))f (g(x))

Advantages

 More readable

 More reusable

 Separate logical tasks

 Like Lego blocks, rather than Jenga tower

CURRYING

Core Principle in FP #3

Call a function with fewer arguments than it expects. It returns a function that takes the remaining arguments.

CLOSURES

if(!someThingImportant) {
  var someThingImportant = {};
}
// this works due to hoisting and function scope

Scope is only affected by functions, not blocks.

Each function defines new scope and has access to parent's scope

Inside its closure, the function is stored with its initialising environment

(function() {
  var c = "now you see me";
  (function() {
    // can see c here
    console.log(c);
  })();
})();
// c not set here

CLOSURES

CLOSURES

function makeClosure(name) {
  return function () {
    return name;
  };
}
var description1 = makeClosure("Cloe the Closure");
var description2 = makeClosure("Albert the Awesome");
console.log(description1());
console.log(description2());

Quiz: CLOSURES

CURRYING

var add = function(a, b, c){ return a + b + c }
add(1, 2, 3) //= 6
add(1, 2, 3, 'IGNORE ME') //= 6
add(1) //= NaN
var curry_add = function(a){ 
    return function(b) {
        return function(c) {
            return a + b + c;
        }
    }
}
curry_add(1)(2)(3); //=6
var curry_add1 = curry_add(1); 
curry_add1(2)(3) //= 6

CURRYING

  • Little pieces can be configured and reused with ease
  • Logic clear and extracted
// Curried get method
var get = function(property, object){ 
    return function(property){     
        return object[property]
        }
    }

var obj = [{ id: 1 }, { id: 2 }, { id: 3 }];
obj.map(get('id')) //= [1,2,3]

// Even better with curried map method
var getIDs = map(get('id'));
getIDs(obj); //= [1,2,3]

Ok enough, show me REAL CODE!

https://github.com/pasierb/flickr-gallery

Great libraries with FP support: 

Underscore

Lodash

Ramda

MatheMAGIC

Core Principle in FP #4

Advantage : Steal some tricks from math to improve performance of your code (and show off)

Disadvantage: Sometimes confusing for non-math wiz

 

Partial Pattern

var unCube = Math.pow.partial(___,1/3);
 
unCube(27); //3
unCube(15); //2.46621207433047

var later = timeOut.partial(___,1000);
 
later(alert("here I am!"));//... ... "here I am!"

Returning a new function, where partial arguments are fixed. 

BIND - A PARTIAL PARTIAL

function add(a, b) {
    return a + b;
}

var addOne = add.bind(null, 1);

addOne(2) // => 3

[1, 2, 3].map(addOne) // => [2, 3, 4]

Function.prototype.bind is a pure JS Solution 

Takes a function, returns a new version with more context

Sets this context, and some arguments (left to right)

Can be used to flatten callback hells

 

USAGE: FLATTENING CALLBACK HELLS

// Original code
function updateData(req,res) {
  getUser(res.params.userId,function(err,user) {
    if(err) return res.send(404);
    getProfile(user,function(err,profile) {
      if(err) return res.send(500);
      updateProfile(user,profile,req.params.profile,function(err) {
        if(err) return res.send(500);
      });
    })
  })
}
// Pure JS Solution
function updateProfile(req,res) {
  getUser(res.params.userId,function(err,user) {
    // bind the user context, returning a fn that 
    // just needs err and profile
    getProfile(user,updateProfileWithUserAndProfile.bind(null,user));
  })
}
function updateProfileWithUserAndProfile(user,err,profile) {}

Functional Reactive Programming

Functional Reactive Programming (FRP)

Definition

Reactive programming is programming with asynchronous data streams (Observables)

https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

Functional

On top of that, you are given an amazing toolbox of functions to combine, create and filter any of those streams. 

CONNECTING STREAMS TO BUILD APPLICATION LOGIC AND AVOID spaghetti code

Event based

Stream based

Everything can be a stream

https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

Using FUnctionals to transform the stream

MULTI CLICK LOGIC in FRP

https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

MULTI CLICK LOGIC in FRP

https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

Functional Reactive Programming with Visualisations

Advantages

 Everything can be an event stream

 Plugin style coding - high abstraction

 Declarative style instead of control flow

 Functional programming as powerful modification tool to  produce clean code

 

Disadvantages

 Requires to think reactively

 Radically different from object oriented design

 Mathematical instead of understandable code

 

Thank YOU for your attention

Functional Patterns & Functional Reactive Programming

By David Dao

Functional Patterns & Functional Reactive Programming

  • 1,140