Functional Programming - fcrimins/fcrimins.github.io GitHub Wiki
Goodbye, Object Oriented Programming (9/27/16)
Dependency Injection (formerly known as: Inversion of Control) (8/31/16)
Map, map, flatMap and filter in Scala (8/30/16)
- good short tutorial/description
Separating Mutation from Computation (7/28/16)
- "computation is very much like mathematical functions, there is no sense of time or change; just a relationship between input parameters and a returned value. mutation on the other hand captures time, change, and the order of events."
Structural Pattern Matching in Java (7/5/16)
- "structural pattern matching on algebraic data types. Once you’ve used this feature, you don’t ever want to program without it. You will find this in languages like Haskell and Scala."
Efficiency of Functional Programming (4/12/16)
OOP is embarrassing (3/7/16)
- 2:50 - Let data just be data
- Let actions just be actions (don't nounify verbs)
MapReduce is not functional programming (3/2/16)
- map is a trivial concept. It’s basically SELECT from SQL
- reduce in MapReduce is a GROUPBY operator: it groups the output of map by key and applies a second, different map on each (key, [stream of values]) pair
- I should also note that, though classical MapReduce consists of 3 stages (parallel apply, group-by a.k.a. shuffle, and another parallel apply), this is merely an arbitrary restriction of the original implementation. People quickly realized that you can assemble more complex networks of parallel applications and group-by’s, which you can see in the FlumeJava paper, Spark, Apache Crunch etc., and finally of course in Dataflow.
Awk, Unix, and functional programming (2/6/16)
OOP is bad (1/26/16)
- procedural programming is ideal
- good discussion of 4 types of programming at beginning of talk (imperative, functional, procedural, and ?)
- 18:08 - Why does OOP not work? A: encapsulation
- 23:00 - "half-assed encapsulation actually gets us something
- wrangling the object zoo
- sub-system hierarchies of objects -- the improper OOP way -- require introductiong "sub-god objects" [fwc - [sobjects"]
- 25:00 - the proper OOP way and the improper OOP way both suck
- 33:00 - Write methods only when the exclusive association with the data type is not in doubt -- main example of this: abstract data types (ADTs), e.g. lists and queues
- the minute you start hemming and hawing over whether a function has a primary association with a data type is the moment you say "screw it" and just make it a plain function
- because most things we tend do do in code are cross-cutting concerns-- they don't have special obvious relationships with particular data types
- principles
- when in doubt, parameterize (no globals, or shared implicit state)
- want data access in our programs to flow through the call graph
- bundle globals into structs/records/classes
- favor pure functions (easier when efficiency is not a priority)
- encapsulate (loosely) at the level of namespaces/packages/modules
- don't be afraid of long functions (do be afraid of needlessly shared state)
- of course if you want to execute code from multiple places you have to break things into functions
- but don't break things into functions merely for documentation purposes -- too much code floating around, too much API to search through
- plus its tough to name functions/variables well
- next best thing: make it private or nested function
- constrain scope of local variables in sub-scopes or nested anonymous funcs
- what we really want though (that doesn't exist in any language) is an anonymous function that doesn't see any of its enclosing scope (FWC - write a language! or just check out Groovy)
- but this requires variables from local scope to be passed into functions as params
- what we really want is a scope-limiter like "use x, y { ... }" that restricts scope to a few local variables without having to pass them in
- such blocks should return a value also
- makes it clear that this is a piece of code used only in this one place (and don't have to give it a name)
- 43:55 - books to not read
3 Reasons why You Shouldn’t Replace Your for-loops by Stream.forEach() (12/11/15)
From 2001: "I will eat a week's pay if OOP is still in vogue in 2015." (12/2/15)
Beware of Functional Programming in Java (11/13/15)
- The lambda style will encourage using higher-order functions in Java, all over the place. Which is generally good. But only when the higher-order function is a static method, whose resulting types will not enclose any state.
- So, be careful, and follow this rule: (“Pure”) Higher order functions MUST be static methods in Java!
Google Guava (Java library): Functional Explained (11/9/15)
Also see Java Notes for functional programming in Java.
Good Functional Programming Article
- https://github.com/fcrimins/fcrimins.github.io/wiki/Better-Java
- There is no
User
but it’s very likely there isSignupUser
. There is noOrder
but you definitely can deal withPlaceOrder
. And when you see classes ending withManager
--just run.
Functional Programming in Python
- "Q2. Can we do Functional Programming in Python? Ans. Yes, we can do FP in Python but its NOT a “Pure” functional language and still youcan program in functional style but be careful. The only reason to ever do so is for readability. If the algorithm is more elegantly expressed functionally than imperatively, and it doesn’t cause performance problems (it usually doesn’t), then go right ahead."
- The fate of reduce() in Python 3000
- "So now reduce(). This is actually the one I've always hated most, because, apart from a few examples involving + or *, almost every time I see a reduce() call with a non-trivial function argument, I need to grab pen and paper to diagram what's actually being fed into that function before I understand what the reduce() is supposed to do. So in my mind, the applicability of reduce() is pretty much limited to associative operators, and in all other cases it's better to write out the accumulation loop explicitly."
Functional Programming in Java
- Functional programming: A step backward
- "The better argument for functional programming is that, in modern applications involving highly concurrent computing on multicore machines, state is the problem. All imperative languages, including object-oriented languages, involve multiple threads changing the shared state of objects. This is where deadlocks, stack traces, and low-level processor cache misses all take place. If there is no state, there is no problem."
- "Unlike imperative code, functional code doesn't map to simple language constructs. Rather, it maps to mathematical constructs."
- "After decades of progress in making programming languages easier for humans to read and understand, functional programming syntax turns back the clock."
- This goes along with Josh's oft stated point about premature optimization.
- "premature optimization is the root of all evil" because it leads to less maintainable code
- For example, how maintainable does this look? http://sebastian-millies.blogspot.de/2015/09/cartesian-products-with-kleisli.html
jOOQ (Java 8 Streams and Functional Programming)
- Comparing Imperative and Functional Algorithms in Java 8
- How to Use Java 8 Streams to Swiftly Replace Elements in a List
- Common SQL Clauses and Their Equivalents in Java 8 Streams
- How to use Java 8 Functional Programming to Generate an Alphabetic Sequence
- "Recently, functional programming has risen in importance because it is well suited for concurrent and event-driven (or "reactive") programming."
- "You can supply a lambda expression whenever an object of an interface with a single abstract method is expected. Such an interface is called a functional interface."
- "In fact, conversion to a functional interface is the only thing that you can do with a lambda expression in Java."
- "The expression
System.out::println
is a method reference that is equivalent to the lambda expressionx -> System.out.println(x)
." - "A lambda expression has three ingredients:"
- "A block of code"
- "Parameters"
- "Values for the free variables; that is, the variables that are not parameters and not defined inside the code... We say that these values have been captured by the lambda expression."
- "interface methods with concrete implementations (called default methods). Those methods can be safely added to existing interfaces."
- https://docs.oracle.com/javase/tutorial/java/javaOO/lambdaexpressions.html