+/* mnemon - A memory training library
+ *
+ * Copyright © 2006,2011 Carl Worth
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3, or (at your option)
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA."
+ */
+
+#ifndef MNEMON_H_INCLUDED
+#define MNEMON_H_INCLUDED
+
+typedef struct _bin bin_t;
+typedef struct _category category_t;
+
+typedef struct _mnemon {
+ char *dir_name;
+
+ int categories_size;
+ int num_categories;
+ category_t *categories;
+
+ int bins_size;
+ int num_bins;
+ bin_t *bins;
+
+ int to_introduce;
+ int to_master;
+ int unlearned;
+ int mastered;
+} mnemon_t;
+
+/* Initialize a new mnemon object. This function must be called before
+ * any other mnemon functions are used. */
+void
+mnemon_init (mnemon_t *mnemon);
+
+/* Inidicate the caller is finished with a mnemon object. Free all
+ * resources associated with this object. After this call, the given
+ * mnemon object should not be passed to any other menmon function,
+ * (except mnemon_init to start over). */
+void
+mnemon_fini (mnemon_t *mnemon);
+
+/* Load a specific category of mnemon challenges. The name should
+ * indicate the name of a file within the user's .mnemon directory. */
+void
+mnemon_load_category (mnemon_t *mnemon,
+ const char *name);
+
+/* Load all categories of mnemon challenges.
+ *
+ * This is equivalent to calling mnemon_load_category for all files
+ * found within the user's .mnemon directory. */
+void
+mnemon_load (mnemon_t *mnemon);
+
+/* Run a series of memory challenges acoording to the to_introduce and
+ * to_master counters as set on the given mnemon object.
+ *
+ * The challenge system is designed to rapidly reinforce items needing
+ * to be learned and provide exponentially less reinforcement for
+ * items as mastery is displayed. This is achieved by storing the
+ * items in a series of numberred bins.
+ *
+ * Items start in bin 0 indicating that they have never been presented
+ * to a user. When an item is presented to the user and answered
+ * correctly, it is moved into the bin of the next higher number.
+ *
+ * However, when an item is answered incorrectly, it is moved directly
+ * to bin -2 (if coming from a bin of a positive number), or the bin
+ * of the next lower integer (more negative) if coming from a bin of a
+ * negative number.
+ *
+ * When selecting a new item to challenge, first a bin is chosen
+ * (considering only the non-empty bins). The bin with the lowest
+ * number is the most likely to be chosen, while each succesively-
+ * higher-numbered bin has a probability one-half of that of the
+ * previous bin.
+ *
+ * A session of challenges consists of three phases, some of which may
+ * be entirely empty, as follows:
+ *
+ * 1. The introduction phase
+ *
+ * This phase is controlled by the to_introduce counter which is
+ * by default set to 10. It is decremented every time an item is
+ * introduced from the bin with score 0, or (if there is no bin
+ * with score 0), every time an item is introduced from the bin
+ * with the lowest non-negative score of any bin.
+ *
+ * 2. The mastering phase
+ *
+ * This phase is controlled by the to_master counter which is
+ * initially set to 10. It begins at the beginning of the session
+ * so can run concurrently with the introduction phase. The
+ * to_master counter is decremented every time an item with a
+ * positive (non-zero) score is answered correctly. It is also
+ * incremented every time an item with a positive (non-zero) score
+ * is answered incorrectly during the introduction phase. If
+ * perfect mastery is demonstrated, the mastering phase is likely
+ * to be complete simultaneous with the introduction stage. If the
+ * user is really struggling with mastery, the mastering phase
+ * will extend long after the introduction phase is over. But
+ * since we never incremeent to_master after the introduction
+ * phase is over, the user cannot build an infinite snowball of
+ * to_master items and have to give up in despair.
+ *
+ * 3. The solidifying phase
+ *
+ * This final phase continues after the mastering phase for as
+ * long as any items with a negative score remain. The idea here
+ * is that we want to quickly give the reinforcement from a missed
+ * item in the current session. Also, there's a bit of a challenge
+ * to the user to demonstrate good mastery of any non-negative
+ * items presented so that the phase actually terminates. It's
+ * possible for this phase to extend for an arbitrary amount of
+ * time, but not very likely, (since the negative items are chosen
+ * preferentially and the user will continue to see the correct
+ * answers to them over and over).
+ *
+ * This function returns after all three phases are complete.
+ *
+ * The user's progress (the movement of items to various new bins) is
+ * kept only in memory. In order to save this progress to disk, the
+ * caller must call mnemon_save.
+ */
+void
+mnemon_do_challenges (mnemon_t *mnemon);
+
+/* Save the user's progress by updating the category files in the
+ * users .mnemon directory. */
+void
+mnemon_save (mnemon_t *mnemon);
+
+/* Print a histogram showing the number of items in each bin.
+ *
+ * If category_name is not NULL, then only the items from the given
+ * category (matching a particular filename within the user's .mnemon
+ * directory) will be shown.
+ *
+ * If length is non zero, then only items with a challenge string of
+ * 'length' characters will be shown. (This is only useful for
+ * particular types of challenges, such as for showing anagram
+ * challenges of a given length).
+ *
+ * To see a histogram of all currently-loaded items, pass NULL for
+ * category and 0 for length.
+ *
+ * Note: Some bins may be removed entirely by (a misfeature side
+ * effect of) the mnemon_do_challenges function, (such as bin 0 being
+ * removed after the introduction phase is complete). An accurate
+ * histogram can be guaranteed by calling menmon_print_histogram
+ * immediately after calling mnemon_load.
+ */
+void
+mnemon_print_histogram (mnemon_t *mnemon,
+ const char *category_name,
+ int length);
+
+#endif