Skip to content

Instantly share code, notes, and snippets.

@nkallen
Created October 22, 2010 22:11
Show Gist options
  • Save nkallen/641482 to your computer and use it in GitHub Desktop.
Save nkallen/641482 to your computer and use it in GitHub Desktop.
import java.util.concurrent.atomic.AtomicReference
class Serializer {
abstract case class State {
def +(other: Unit => Unit): State
}
case object Idle extends State {
def +(other: Unit => Unit) = Working(List(other))
}
case class Working(items: Seq[Unit => Unit]) extends State {
def first = items.first
def rest = Working(items.drop(1))
def isEmpty = items.isEmpty
def +(other: Unit => Unit) = Working(items ++ List(other))
}
private val stateRef = new AtomicReference[State](Idle)
def doIt(f: Unit => Unit) {
if (stateRef.compareAndSet(Idle, Working(List(f)))) {
var newState: Working = null
do {
var oldState: Working = null
var g: Unit => Unit = null
do {
oldState = stateRef.get.asInstanceOf[Working]
g = oldState.first
newState = oldState.rest
} while (!stateRef.compareAndSet(oldState, newState))
g()
} while (!newState.isEmpty || !stateRef.compareAndSet(newState, Idle))
} else {
var oldState: State = null
var newState: State = null
do {
oldState = stateRef.get
newState = oldState + f
} while (!stateRef.compareAndSet(oldState, newState))
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment