{
  "nbformat": 4,
  "nbformat_minor": 5,
  "metadata": {
    "kernelspec": {
      "display_name": "Python 3",
      "language": "python",
      "name": "python3"
    },
    "language_info": {
      "name": "python",
      "version": "3.12.14"
    },
    "research_runtime": {
      "engine": "pyodide",
      "packages": [],
      "assets": [
        "experiment.py",
        "figure_generation.py"
      ],
      "generated_assets": [
        "results.json",
        "figure.svg"
      ],
      "display_assets": [
        "figure.svg"
      ],
      "filesystem_root": ".",
      "network_required": false,
      "validation_engine": "CPython standard-library execution"
    }
  },
  "cells": [
    {
      "cell_type": "markdown",
      "metadata": {},
      "source": [
        "# Why does an imitation learner struggle after its first mistake?\n\nDeterministic tabular dataset aggregation in an eight-step offset simulator; no neural training, driving deployment, or claim to reproduce the paper benchmarks.\n\nThis notebook runs the complete saved experiment, checks its assertions, and regenerates the SVG from the computed results. Python 3.10+ and standard-library modules only. Place experiment.py and figure_generation.py beside the notebook. The exact loaded assets are recorded in notebook metadata.\n"
      ],
      "id": "cell-1"
    },
    {
      "cell_type": "code",
      "metadata": {},
      "execution_count": 1,
      "outputs": [
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "iteration=0 error=3 trace=[0, 0, 0, 1, 1, 1, 0, 0, 0]\n",
            "  visited=[0, 1]\n",
            "iteration=1 error=4 trace=[0, 0, 0, 1, 0, 0, -1, -1, -1]\n",
            "  visited=[-1, 0, 1]\n",
            "iteration=2 error=2 trace=[0, 0, 0, 1, 0, 0, -1, 0, 0]\n",
            "  visited=[-1, 0, 1]\n",
            "Aggregated table: {-1: 1, 0: 0, 1: -1}\n",
            "Centered test error=2\n",
            "Unseen offset-2 test error=19\n",
            "table round=0, exhaustive centered mean error=6.9712, unknown-state decisions=60.4938%\n",
            "table round=1, exhaustive centered mean error=5.9300, unknown-state decisions=41.1523%\n",
            "table round=2, exhaustive centered mean error=4.0000, unknown-state decisions=0.0000%\n"
          ]
        }
      ],
      "source": [
        "import runpy\n_ = runpy.run_path('experiment.py', run_name='__main__')\n"
      ],
      "id": "cell-2"
    },
    {
      "cell_type": "code",
      "metadata": {},
      "execution_count": 2,
      "outputs": [
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "Regenerated figure.svg from results.json.\n"
          ]
        }
      ],
      "source": [
        "runpy.run_path('figure_generation.py', run_name='__main__')\n",
        "print('Regenerated figure.svg from results.json.')\n",
        "\n",
        "import base64\n",
        "print('__NOTEBOOK_IMAGE__svg+xml:' + base64.b64encode(open('figure.svg','rb').read()).decode())\n"
      ],
      "id": "cell-3"
    },
    {
      "cell_type": "markdown",
      "metadata": {},
      "source": [
        "## Inspect the saved result\n\nThe article's static figure is available before running code. The regenerated figure.svg uses results.json, and every plotted quantity comes from the experiment.\n\n![Computed figure](figure.svg)\n\nChange an input in experiment.py, rerun both code cells, then compare the saved result and figure.\n"
      ],
      "id": "cell-4"
    }
  ]
}
