There are no standard metrics to agree on.
Sufficiently simple and minimal to be easily understandable.
mov $0x0C0C, %ax
mov $0x01, %bh
mov $0x0001, %cx
mov $0x0001, %dx
int $0x10
inc %cx
inc %dx
cmp $201, %dx
jz end
(λ x. x) t
(λ x. x) t
t
Programs written in the model must be quick and easy to understand.
λ b. (λ c. λ t. λ f. c t f) b (λ x. λ y. y) (λ x. λ y. x)
b => if (b) false else true
(b: Boolean) => !b
The program must run correctly irrespective of the computers it is deployed on, and their relationships.
class Ping extends Actor {
def receive = {
case "pong" => sender ! "ping"
}
}
class Ping extends Actor {
def receive = {
case "pong" => sender ! "ping"
}
}
class Ping extends Actor {
def receive = {
case "pong" => sender ! "ping"
}
}
class Pong extends Actor {
def receive = {
case "ping" => sender ! "pong"
}
}
Programs can be built from smaller independent programs.
class Server[T, S](f: T => S)
extends Actor {
def receive = {
case x: T => sender ! f(x)
}
}
class Client[T, S](
server: ActorRef,
req: T,
action: S => Unit
) extends Actor {
server ! req
def receive = {
case x: S => action(x)
}
}
val actors = Map[String, ActorRef]
val ns = actorOf(Server(actors))
val actors = Map[String, ActorRef]
val ns = actorOf(Server(actors))
actorOf(Client(ns, "p", println))
val actors = Map[String, ActorRef]
val ns = actorOf(Server(actors))
actorOf(Client(ns, "p", println))
val actors = Map[String, ActorRef]
val ns = actorOf(Server(actors))
actorOf(Client(ns, "p", println))
val actors = Map[String, ActorRef]
val ns = actorOf(Server(actors))
actorOf(Client(ns, "p", println))
class Cache(var c: ActorRef = null)
extends Client(ns, "p", r => c=r)
class Cache(var c: ActorRef = null)
extends Client(ns, "p", r => c=r)
class Cache(var c: ActorRef = null)
extends Client(ns, "p", r => c=r) {
def receive = super.receive orElse {
case "p" => sender ! c
}
}
class Cache(var c: ActorRef = null)
extends Client(ns, "p", r => c=r) {
def receive = super.receive orElse {
case "p" => sender ! c
case ns: ActorRef => ns ! "p"
}
}
class Cache
extends Reactor[String] {
var cached = _
}
val (events, ch) = open[String]
events.onEvent {
s => println(s)
}
ch ! ""
type Req[T, S] =
Channel[(T, Channel[S])]
def server[T, S](f: T => S): Req[T, S] = {
val (events, ch) = open[(T, Channel[S])]
events onMatch {
case (x, sender) => sender ! f(x)
}
ch
}
type Req[T, S] =
Channel[(T, Channel[S])]
def ?[T,S](r: Req[T, S], x: T): Events[S] ={
val (events, ch) = open[S]
r ! (x, ch)
events
}
def cache[T,S](s:Req[T,S], x:T): Req[T,S] = {
var cached: S = _
(s ? x) onEvent {
y => cached = y
}
server(y => cached)
}
type Server[T, S] =
Reactor[(T, Channel[S])]
class Cache
extends Server[String, Channel[_]] {
events.forward(cache(ns, "p"))
}
Broadcast
Communication pattern in which the sender sends the same message to multiple targets.
import broadcast.bestEffort
import broadcast.totalOrder
import replication.crdt