http://www.cs.usask.ca/faculty/mccrosky/carl/courses/cmpt421_814/index.html