Functional reactive programming
This article provides insufficient context for those unfamiliar with the subject.Learn how and when to remove this template message)(April 2015) (
Functional reactive programming (FRP) is a programming paradigm for reactive programming (asynchronous dataflow programming) using the building blocks of functional programming (e.g. map, reduce, filter). FRP has been used for programming graphical user interfaces (GUIs), robotics, games, and music, aiming to simplify these problems by explicitly modeling time.
Formulations of FRP
FRP has taken many forms since its introduction in 1997. One axis of diversity is discrete vs. continuous semantics. Another axis is how FRP systems can be changed dynamically.
The earliest formulation of FRP used continuous semantics, aiming to abstract over many operational details that are not important to the meaning of a program. The key properties of this formulation are:
- Modeling values that vary over continuous time, called "behaviors" and later "signals".
- Modeling "events" which have occurrences at discrete points in time.
- The system can be changed in response to events, generally termed "switching."
- The separation of evaluation details such as sampling rate from the reactive model.
This semantic model of FRP in side-effect free languages is typically in terms of continuous functions, and typically over time.
Formulations such as Event-Driven FRP and Elm before version 0.17 require that updates are discrete and event-driven. These formulations have pushed for practical FRP, focusing on semantics that have a simple API that can be implemented efficiently in a setting such as robotics or in a web-browser.
In these formulations, it is common that the ideas of behaviors and events are combined into signals that always have a current value, but change discretely.
It has been pointed out that the ordinary FRP model, from inputs to outputs, is poorly suited to interactive programs. Lacking the ability to "run" programs within a mapping from inputs to outputs may mean one of the following solutions has to be used:
- Create a data structure of actions which appear as the outputs. The actions must be run by an external interpreter or environment. This inherits all of the difficulties of the original stream I/O system of Haskell.
- Use Arrowized FRP and embed arrows which are capable of performing actions. The actions may also have identities, which allows them to maintain separate mutable stores for example. This is the approach taken by the Fudgets library and, more generally, Monadic Stream Functions.
- The novel approach is to allow actions to be run now (in the IO monad) but defer the receipt of their results until later. This makes use of an interaction between the Event and IO monads, and is compatible with a more expression-oriented FRP:
planNow :: Event (IO a) -> IO (Event a)
There are two types of FRP systems, push-based and pull-based. Push-based systems take events and push them through a signal network to achieve a result. Pull-based systems wait until the result is demanded, and work backwards through the network to retrieve the value demanded.
Some FRP systems such as Yampa use sampling, where samples are pulled by the signal network. This approach has a drawback: the network has to wait up to the duration of one computation step to find out about changes to the input. Sampling is an example of pull-based FRP.
The Reactive and Etage libraries on Hackage introduced an approach called push-pull FRP, which combines the best of push-based and pull-based FRP. In this approach, only when the next event on a purely defined stream (such as a list of fixed events with times) is demanded, that event is constructed. These purely defined streams act like lazy lists in Haskell. That is the pull-based half. The push-based half is used when events external to the system are brought in. The external events are pushed to consumers, so that they can find out about an event the instant it is issued.
- Yampa is an arrowized, efficient, pure Haskell implementation with SDL, SDL2, OpenGL and HTML DOM support.
- The programming language Elm used to support FRP  but has since replaced it with a different pattern 
- reflex is an efficient push/pull FRP implementation in Haskell with hosts for browser/DOM, SDL and Gloss.
- reactive-banana is a target agnostic push FRP implementation in Haskell.
- netwire and varying are arrowized, pull FRP implementations in Haskell.
- React is an OCaml module for functional reactive programming.
- Sodium is a push FRP implementation independent of a specific UI framework for several programming languages, such as Java, TypeScript and C#.
- Elliott, Conal; Hudak, Paul. "Functional Reactive Animation". Functional Reactive Animation. ICFP ’97. Retrieved 14 July 2018.
- Nilsson, Henrik; Courtney, Antony; Peterson, John (Feb 2011) , "Functional Reactive Programming, Continued", Haskell Workshop (PDF) (2).
- Elliott, Conal; Hudak, Paul (1997), "Functional Reactive Animation", ICFP.
- Courtney, Antony; Elliott, Conal (Feb 2011) , "Genuinely Functional User Interfaces" (PDF), Haskell Workshop, Yale.
- Taha, Walid; Wan, Zhanyong; Hudak, Paul (2002), "Event-Driven FRP", PADL (PDF), Yale.
- Czaplicki, Evan; Chong, Stephen (2013), "Asynchronous Functional Reactive Programming for GUIs", PLDI, Harvard.
- Wan, Zhanyong; Taha, Walid; Hudak, Paul (Feb 2011), "Real-Time FRP", ICFP (PDF) (1).
- Czaplicki, Evan (Apr 2012), Elm: Concurrent FRP for Functional GUIs (PDF) (thesis), Harvard.
- Czaplicki, Evan. "A Farewell to FRP". elm. Retrieved 14 July 2018.
- Haskell-related FRP research
- "Deprecating the Observer Pattern with Scala.React," – Scala.React, an FRP Scala implementation
- probability of living chart example - using ReactiveChart FRP glitch free implementation, see docu https://reactivechart.com/knowledge/reactive
- What is (functional) reactive programming? – Stack Overflow answers
- Functional Reactive Programming: Functional Program Design in Scala - A lecture from École Polytechnique Fédérale de Lausanne's Coursera course on "Functional Program Design in Scala", by Martin Odersky