| When building a spaced repetition toy, the most satisfying algorithm I found was: * Model the forgetting curve as p = 2 ^ (−∆/h) (p = probability of recall, ∆ = time since last review, h = forgetting half-life for a particular card and user) (see https://research.duolingo.com/papers/settles.acl16.pdf) * Numerically fit this curve to the last ~10 recent reviews of the card by the user to give an estimate for h (the half-life but effectively the intrinsic "difficulty" of the card for that user) * Schedule the next review of the card at the time when a particular recall probability is reached. This probability should be configurable by the user: >90% for an "easy" session, <70% for a "hard" session. * Use the "due date" to queue up cards for review. If a user reviews a card _before_ the due date, ensure that the half-life is never reduced after a succesful review. Provide some feedback to the user to suggest they stop the session when there are no pending cards left ("10 more cards due today, 100 cards due tomorrow, 1000 cards due next week") * Don't schedule the same card twice in a row as this is annoying for the user. If it has just been reviewed and is due next, move it back to second place in the queue. I found this works well once there are 2 or more reviews of a particular card for a particular user. For scheduling the _second_ review of the card I had to invent a heuristic like: if first review failed, schedule again in 1 minute, if first review passed schedule again tomorrow. However in apps where many users are reviewing the same cards, you could probably build a good model of the difficulty of a card for a user before 2 reviews by considering the performance of other users on that card. |