diff --git a/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-10-MLN-Csharp.ipynb b/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-10-MLN-Csharp.ipynb index 75d59ae784..9f7f17b6e1 100644 --- a/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-10-MLN-Csharp.ipynb +++ b/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-10-MLN-Csharp.ipynb @@ -3,7 +3,16 @@ { "cell_type": "markdown", "id": "4b764a33", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.003018, + "end_time": "2026-09-29T17:35:42.742315+00:00", + "exception": false, + "start_time": "2026-09-29T17:35:42.739297+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "# Tweety-10 — Markov Logic Networks (MLN) en .NET (C# / IKVM)\n", "**Navigation** : [← Tweety-9-Préférences](Tweety-09-Preferences-Python.ipynb) | [Index](./README.md) | [Tweety-11-Causal →](Tweety-11-Causal.ipynb)\n", @@ -28,34 +37,148 @@ "id": "4f5ecc42", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:16.774404Z", - "iopub.status.busy": "2026-07-03T14:28:16.765895Z", - "iopub.status.idle": "2026-07-03T14:28:18.263571Z", - "shell.execute_reply": "2026-07-03T14:28:18.252024Z" - } + "iopub.execute_input": "2026-09-29T17:35:42.763864Z", + "iopub.status.busy": "2026-09-29T17:35:42.754621Z", + "iopub.status.idle": "2026-09-29T17:36:18.999840Z", + "shell.execute_reply": "2026-09-29T17:36:18.996474Z" + }, + "papermill": { + "duration": 36.254882, + "end_time": "2026-09-29T17:36:19.000016+00:00", + "exception": false, + "start_time": "2026-09-29T17:35:42.745134+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "display_data", + "data": { + "text/html": [ + "\r\n", + "
\r\n", + " \r\n", + " \r\n", + "
" + ] + }, "metadata": {}, + "output_type": "display_data" + }, + { "data": { "text/html": [ - "
Installing Packages
" + "
Installed Packages
" ] - } + }, + "metadata": {}, + "output_type": "display_data" }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "IKVM home=OK (basename=ikvm-home-8.14.0-win-x64)\r\n" + "IKVM home=OK (basename=ikvm-home-8.14.0-linux-x64)\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "DLL MLN reference chargee (chemin masque pour portabilite).\r\n" + "DLL MLN reference chargee (chemin masque pour portabilite).\n" ] } ], @@ -65,7 +188,8 @@ "#r \"org.tweetyproject.tweety-mln.dll\"\n", "// IKVM.Home DOIT etre connu du static initializer (JVM.Properties) AVANT tout appel Java.\n", "using System.IO;\n", - "string ikvmVer = \"8.14.0\", ikvmRid = \"win-x64\";\n", + "// RID de la machine courante (win-x64, linux-x64, osx-arm64...) : IKVM.Image tire l'image native de chaque plateforme.\n", + "string ikvmVer = \"8.14.0\", ikvmRid = (OperatingSystem.IsWindows() ? \"win\" : OperatingSystem.IsMacOS() ? \"osx\" : \"linux\") + \"-\" + System.Runtime.InteropServices.RuntimeInformation.ProcessArchitecture.ToString().ToLowerInvariant();\n", "string nugetRoot = Environment.GetEnvironmentVariable(\"NUGET_PACKAGES\")\n", " ?? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), \".nuget\", \"packages\");\n", "string ikvmBaseAny = Path.Combine(nugetRoot, \"ikvm.image\", ikvmVer, \"ikvm\", \"any\", \"any\");\n", @@ -93,14 +217,22 @@ "AppContext.SetData(\"ikvm.home\", ikvmHome);\n", "System.Console.WriteLine(\"IKVM home=\" + (File.Exists(Path.Combine(ikvmHome, \"lib\", \"tzdb.dat\")) ? \"OK (basename=\" + Path.GetFileName(ikvmHome) + \")\" : \"MISSING\"));\n", "System.Console.WriteLine($\"DLL MLN reference chargee (chemin masque pour portabilite).\");\n", - "\n", - "" + "\n" ] }, { "cell_type": "markdown", "id": "d0c6d2d9", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.004205, + "end_time": "2026-09-29T17:36:19.009304+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:19.005099+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "### Interprétation de l'initialisation\n", "**Succès** : la DLL `org.tweetyproject.tweety-mln.dll` (≈14 MB) est chargée dans le runtime .NET via IKVM. Elle contient l'intégralité du module `logics-mln` de Tweety 1.30 (Markov Logic Networks) + ses dépendances transitives `logics-fol` (First-Order Logic) et `logics-pcl` (Probabilistic Conditional Logic), compilées depuis le JAR `tweety-mln-full-1.30.jar` (12.9 MB).\n", @@ -111,7 +243,16 @@ { "cell_type": "markdown", "id": "feb426e7", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.004292, + "end_time": "2026-09-29T17:36:19.018206+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:19.013914+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Partie 1\n", " : De la logique du premier ordre à la logique pondérée### 1.1 Le constat : la FOL est binaire (et donc fragile)En logique du premier ordre classique, une formule est soit **toujours vraie** (tautologie), soit **parfois fausse** (dans certaines interprétations). Une règle comme « les oiseaux volent » s'écrit `∀x. Bird(x) ⇒ Flies(x)`. **Mais alors, que fait-on du pingouin ?** En FOL, soit on abandonne la règle (on perd la généralisation), soit on l'accepte (on classifie mal les pingouins).### 1.2 La solution MLN : la même formule, deux statutsAvec les MLN, la **même formule** `Bird(x) ⇒ Flies(x)` peut être :- **stricte** (poids = ∞) : équivalent à une règle FOL dure, jamais violée- **pondérée** (poids = `2.5` par exemple) : la règle est *presque* toujours vraie, mais peut être violée si d'autres règles (strictes) l'exigent (ex. `Penguin(x) ⇒ ¬Flies(x)`)### 1.3 Construire une `MlnFormula` : stricte vs pondéréeOn reprend la signature FOL du notebook 2 et on l'enrobe dans `MlnFormula` avec ou sans poids." @@ -123,18 +264,26 @@ "id": "7453cc17", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:18.266438Z", - "iopub.status.busy": "2026-07-03T14:28:18.266001Z", - "iopub.status.idle": "2026-07-03T14:28:19.211343Z", - "shell.execute_reply": "2026-07-03T14:28:19.211091Z" - } + "iopub.execute_input": "2026-09-29T17:36:19.028671Z", + "iopub.status.busy": "2026-09-29T17:36:19.028347Z", + "iopub.status.idle": "2026-09-29T17:36:20.812896Z", + "shell.execute_reply": "2026-09-29T17:36:20.812675Z" + }, + "papermill": { + "duration": 1.790677, + "end_time": "2026-09-29T17:36:20.812994+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:19.022317+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "MLN avec 2 formules ponderees : { <(Smokes(X)=>Cancer(X)), 2.0>, <(Friends(X,Y)&&Smokes(X)=>Smokes(Y)), 0.5> }\r\n" + "MLN avec 2 formules ponderees : { <(Friends(X,Y)&&Smokes(X)=>Smokes(Y)), 0.5>, <(Smokes(X)=>Cancer(X)), 2.0> }\n" ] } ], @@ -181,7 +330,16 @@ { "cell_type": "markdown", "id": "07f0300f", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.002968, + "end_time": "2026-09-29T17:36:20.819521+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:20.816553+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "### Interprétation : deux statuts pour une même formule\n", "**Sortie typique** :\n", @@ -198,7 +356,16 @@ { "cell_type": "markdown", "id": "b8b992ce", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.002808, + "end_time": "2026-09-29T17:36:20.825125+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:20.822317+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Diagnostic IKVM — corrigé : le reasoner MLN est invocable\n", "\n", @@ -214,7 +381,16 @@ { "cell_type": "markdown", "id": "2b86a3c0", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.002659, + "end_time": "2026-09-29T17:36:20.830540+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:20.827881+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Partie 2\n", " : L'exemple canonique — friends / smokers / cancerL'exemple de référence de **Richardson & Domingos (2006)** met en scène un petit réseau social : 3 personnes, des liens d'amitié, le fait de fumer, et la probabilité de cancer. Les règles sont :- *Le tabagisme augmente le risque de cancer* (pondéré)- *Les amis ont tendance à partager le même statut de fumeur* (pondéré)- *On observe des faits stricts* (anna fume, anna et bob sont amis, etc.)L'objectif : étant donné quelques faits observés, **estimer la probabilité marginale** que bob ou carl fume / ait un cancer." @@ -226,95 +402,103 @@ "id": "061aa5d3", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.213058Z", - "iopub.status.busy": "2026-07-03T14:28:19.212745Z", - "iopub.status.idle": "2026-07-03T14:28:19.259958Z", - "shell.execute_reply": "2026-07-03T14:28:19.259640Z" - } + "iopub.execute_input": "2026-09-29T17:36:20.837613Z", + "iopub.status.busy": "2026-09-29T17:36:20.837323Z", + "iopub.status.idle": "2026-09-29T17:36:51.724006Z", + "shell.execute_reply": "2026-09-29T17:36:51.723668Z" + }, + "papermill": { + "duration": 30.890904, + "end_time": "2026-09-29T17:36:51.724108+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:20.833204+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "MLN reseau social (3 personnes) : 5 formules\r\n" + "MLN reseau social (3 personnes) : 5 formules\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "{ <(Smokes(X)=>Cancer(X)), 3.0>, <(Friends(X,Y)&&Smokes(X)=>Smokes(Y)), 2.0>, , , }\r\n" + "{ , <(Friends(X,Y)&&Smokes(X)=>Smokes(Y)), 2.0>, <(Smokes(X)=>Cancer(X)), 3.0>, , }\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "Marginales a posteriori (reasoner exact, meme moteur Java que le jumeau Python) :\r\n" + "Marginales a posteriori (reasoner exact, meme moteur Java que le jumeau Python) :\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Atome | P(atome)\r\n" + " Atome | P(atome)\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " ------------------|---------\r\n" + " ------------------|---------\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Smokes(anna) | 1.0000\r\n" + " Smokes(anna) | 1.0000\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Smokes(bob) | 0.7294\r\n" + " Smokes(bob) | 0.7294\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Smokes(carl) | 0.7294\r\n" + " Smokes(carl) | 0.7294\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Cancer(anna) | 0.9526\r\n" + " Cancer(anna) | 0.9526\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Cancer(bob) | 0.8301\r\n" + " Cancer(bob) | 0.8301\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Cancer(carl) | 0.8301\r\n" + " Cancer(carl) | 0.8301\n" ] } ], @@ -385,7 +569,16 @@ { "cell_type": "markdown", "id": "0c5e37ba", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.003234, + "end_time": "2026-09-29T17:36:51.730953+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:51.727719+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "### Interprétation : marginales a posteriori du réseau social\n", "\n", @@ -406,7 +599,16 @@ { "cell_type": "markdown", "id": "91ebc523", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.003012, + "end_time": "2026-09-29T17:36:51.737074+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:51.734062+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Partie 3 : Comment les poids modèlent la croyance\n", "\n", @@ -430,130 +632,138 @@ "id": "c0116066", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.261923Z", - "iopub.status.busy": "2026-07-03T14:28:19.261594Z", - "iopub.status.idle": "2026-07-03T14:28:19.330208Z", - "shell.execute_reply": "2026-07-03T14:28:19.329931Z" - } + "iopub.execute_input": "2026-09-29T17:36:51.745161Z", + "iopub.status.busy": "2026-09-29T17:36:51.744926Z", + "iopub.status.idle": "2026-09-29T17:37:17.978456Z", + "shell.execute_reply": "2026-09-29T17:37:17.978194Z" + }, + "papermill": { + "duration": 26.238459, + "end_time": "2026-09-29T17:37:17.978560+00:00", + "exception": false, + "start_time": "2026-09-29T17:36:51.740101+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "A. Spectre 1-atome (forme fermee sigma(w)) :\r\n" + "A. Spectre 1-atome (forme fermee sigma(w)) :\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 0.0 -> P(a) = 0.5000 (MLN { })\r\n" + " w = 0.0 -> P(a) = 0.5000 (MLN { })\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 0.5 -> P(a) = 0.6225 (MLN { })\r\n" + " w = 0.5 -> P(a) = 0.6225 (MLN { })\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 1.0 -> P(a) = 0.7311 (MLN { })\r\n" + " w = 1.0 -> P(a) = 0.7311 (MLN { })\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 3.0 -> P(a) = 0.9526 (MLN { })\r\n" + " w = 3.0 -> P(a) = 0.9526 (MLN { })\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 5.0 -> P(a) = 0.9933 (MLN { })\r\n" + " w = 5.0 -> P(a) = 0.9933 (MLN { })\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "B. Sweep du poids w de 'Smokes=>Cancer' sur P(Cancer(bob)) (reasoner exact) :\r\n" + "B. Sweep du poids w de 'Smokes=>Cancer' sur P(Cancer(bob)) (reasoner exact) :\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 0.0 -> P(Cancer(bob)) = 0.5000\r\n" + " w = 0.0 -> P(Cancer(bob)) = 0.5000\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 0.5 -> P(Cancer(bob)) = 0.6024\r\n" + " w = 0.5 -> P(Cancer(bob)) = 0.6024\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 1.0 -> P(Cancer(bob)) = 0.6850\r\n" + " w = 1.0 -> P(Cancer(bob)) = 0.6850\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 2.0 -> P(Cancer(bob)) = 0.7865\r\n" + " w = 2.0 -> P(Cancer(bob)) = 0.7865\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 3.0 -> P(Cancer(bob)) = 0.8301\r\n" + " w = 3.0 -> P(Cancer(bob)) = 0.8301\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " w = 5.0 -> P(Cancer(bob)) = 0.8535\r\n" + " w = 5.0 -> P(Cancer(bob)) = 0.8535\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "Courbe de saturation : w=0 -> 0.5 (aucune contrainte) ; w croissant -> P -> 1\r\n" + "Courbe de saturation : w=0 -> 0.5 (aucune contrainte) ; w croissant -> P -> 1\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "(asymptote quasi-logique JAMAIS atteinte : une MLN reste probabiliste).\r\n" + "(asymptote quasi-logique JAMAIS atteinte : une MLN reste probabiliste).\n" ] } ], @@ -628,7 +838,16 @@ { "cell_type": "markdown", "id": "eccbcf7e", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.003552, + "end_time": "2026-09-29T17:37:17.986866+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:17.983314+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "### Interprétation : le spectre logique ↔ statistique\n", "\n", @@ -648,7 +867,16 @@ { "cell_type": "markdown", "id": "3acd4e28", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.003989, + "end_time": "2026-09-29T17:37:17.994491+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:17.990502+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Partie 4\n", " : Le paradoxe des exceptions — le pingouin qui ne vole pasVoici le cas où les MLN brillent et où la FOL classique échoue : la **généralisation avec exception**.- **tweety** est un pingouin (et un oiseau)- **robin** est un oiseau (ordinaire)- *Règle stricte* : les pingouins ne volent pas- *Règle pondérée* : la plupart des oiseaux volent (poids 2.0)Comment le MLN gère-t-il ce paradoxe ? La règle stricte `Penguin(X) => !Flies(X)` doit dominer pour tweety, mais pas pour robin." @@ -660,95 +888,103 @@ "id": "38183d9d", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.332287Z", - "iopub.status.busy": "2026-07-03T14:28:19.331864Z", - "iopub.status.idle": "2026-07-03T14:28:19.399531Z", - "shell.execute_reply": "2026-07-03T14:28:19.399222Z" - } + "iopub.execute_input": "2026-09-29T17:37:18.003436Z", + "iopub.status.busy": "2026-09-29T17:37:18.002895Z", + "iopub.status.idle": "2026-09-29T17:37:18.059976Z", + "shell.execute_reply": "2026-09-29T17:37:18.059808Z" + }, + "papermill": { + "duration": 0.062025, + "end_time": "2026-09-29T17:37:18.060055+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:17.998030+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "MLN paradoxe du pingouin : 5 formules\r\n" + "MLN paradoxe du pingouin : 5 formules\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "{ , <(Bird(X)=>Flies(X)), 2.0>, , <(Penguin(X)=>!Flies(X)), null>, }\r\n" + "{ , , <(Bird(X)=>Flies(X)), 2.0>, <(Penguin(X)=>!Flies(X)), null>, }\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " tweety : Bird + Penguin | robin : Bird seulement\r\n" + " tweety : Bird + Penguin | robin : Bird seulement\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " strict Penguin=>!Flies | pondere Bird=>Flies [w=2]\r\n" + " strict Penguin=>!Flies | pondere Bird=>Flies [w=2]\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " P(Flies(tweety)) = 0.0000\r\n" + " P(Flies(tweety)) = 0.0000\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " P(Flies(robin)) = 0.7870\r\n" + " P(Flies(robin)) = 0.7870\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "=> tweety (pingouin) ne vole pas : 0.0 -- l'exception STRICTE domine (tout monde\r\n" + "=> tweety (pingouin) ne vole pas : 0.0 -- l'exception STRICTE domine (tout monde\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " ou un pingouin vole a une probabilite nulle).\r\n" + " ou un pingouin vole a une probabilite nulle).\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "=> robin (oiseau ordinaire) vole probablement : ~0.79 (regle ponderee seule).\r\n" + "=> robin (oiseau ordinaire) vole probablement : ~0.79 (regle ponderee seule).\n" ] } ], @@ -815,7 +1051,16 @@ { "cell_type": "markdown", "id": "5c1c0fb3", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.003889, + "end_time": "2026-09-29T17:37:18.068211+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:18.064322+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "### Interprétation : la logique pondérée gère les exceptions nativement\n", "\n", @@ -842,7 +1087,16 @@ { "cell_type": "markdown", "id": "d0968923", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.004118, + "end_time": "2026-09-29T17:37:18.076548+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:18.072430+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Partie 5 : Trois familles de raisonneurs MLN\n", "\n", @@ -863,67 +1117,75 @@ "id": "01f10d37", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.401905Z", - "iopub.status.busy": "2026-07-03T14:28:19.401472Z", - "iopub.status.idle": "2026-07-03T14:28:19.470254Z", - "shell.execute_reply": "2026-07-03T14:28:19.469863Z" - } + "iopub.execute_input": "2026-09-29T17:37:18.085811Z", + "iopub.status.busy": "2026-09-29T17:37:18.085610Z", + "iopub.status.idle": "2026-09-29T17:37:27.883884Z", + "shell.execute_reply": "2026-09-29T17:37:27.883730Z" + }, + "papermill": { + "duration": 9.803676, + "end_time": "2026-09-29T17:37:27.884033+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:18.080357+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "Atome requete : P(Cancer(carl))\r\n" + "Atome requete : P(Cancer(carl))\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " ApproximateNaive (exact) : 0.8301 en 1.56s\r\n" + " ApproximateNaive (exact) : 0.8301 en 9.15s\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " SimpleSampling (approx): 0.8874 en 0.10s\r\n" + " SimpleSampling (approx): 0.8633 en 0.60s\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Ecart absolu : 0.0572\r\n" + " Ecart absolu : 0.0331\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "\r\n" + "\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "=> Le sampling est plus rapide mais legerement imprecis (et fluctue d'un run a l'autre).\r\n" + "=> Le sampling est plus rapide mais legerement imprecis (et fluctue d'un run a l'autre).\n" ] }, { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - " Pour un domaine petit, l'exact (enumeration) reste preferable.\r\n" + " Pour un domaine petit, l'exact (enumeration) reste preferable.\n" ] } ], @@ -990,21 +1252,24 @@ { "cell_type": "markdown", "id": "556a2203", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.004458, + "end_time": "2026-09-29T17:37:27.894101+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:27.889643+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "### Interprétation : exact vs approximatif\n", "\n", - "**Sortie réelle** (mesurée au Stopwatch, domaine ~15 atomes ground) :\n", - "\n", - "```\n", - " ApproximateNaive (exact) : 0.8301 en 1.56s\n", - " SimpleSampling (approx): 0.8874 en 0.10s\n", - " Ecart absolu : 0.0572\n", - "```\n", + "**Sortie réelle** : la cellule précédente, mesurée au Stopwatch sur un domaine d'environ 15 atomes ground. Les durées absolues dépendent de la machine ; la valeur exacte, elle, n'en dépend pas.\n", "\n", "**Lecture** :\n", - "- Le reasoner **exact** (`ApproximateNaiveMlnReasoner`) énumère les interprétations de Herbrand et calcule la marginale rigoureuse — ici `P(Cancer(carl)) = 0.8301`, la même valeur que la cell[8] (même modèle). Coût exponentiel en théorie (`2^n` mondes), mais immédiat sur un petit domaine.\n", - "- Le reasoner **par sampling** (`SimpleSamplingMlnReasoner(0.01, 1000)`) estime la marginale par tirage Monte-Carlo : ~15× plus rapide (0.10s vs 1.56s), mais **approximatif** — et sa valeur **fluctue d'une exécution à l'autre** (variance d'échantillonnage, non seedé). Le jumeau Python a obtenu 0.7722 sur la même requête (écart 0.058 de l'autre côté) ; ce run-ci donne 0.8874 (écart 0.057) : deux tirages légitimes du même estimateur autour de la vraie valeur 0.8301.\n", + "- Le reasoner **exact** (`ApproximateNaiveMlnReasoner`) énumère les interprétations de Herbrand et calcule la marginale rigoureuse — ici `P(Cancer(carl)) = 0.8301`, la même valeur que la cell[8] (même modèle). Coût exponentiel en théorie (`2^n` mondes), mais praticable sur un petit domaine.\n", + "- Le reasoner **par sampling** (`SimpleSamplingMlnReasoner(0.01, 1000)`) estime la marginale par tirage Monte-Carlo : environ 15× plus rapide que l'énumération (rapport mesuré sur deux machines différentes, dont les durées absolues diffèrent), mais **approximatif** — et sa valeur **fluctue d'une exécution à l'autre** (variance d'échantillonnage, non seedé). Le jumeau Python a obtenu 0.7722 sur la même requête (écart 0.058 sous la vraie valeur) ; ce run-ci donne 0.8633 (écart 0.0331 au-dessus), et une autre exécution de ce notebook donnera une autre valeur : autant de tirages légitimes du même estimateur autour de la vraie valeur 0.8301.\n", "- **Quand utiliser quoi** : énumération pour le debug, la validation et les petits graphes ; sampling pour les grands domaines où l'énumération explose — en acceptant la variance.\n", "\n", "> Comme au notebook 2 (Sat4j portable vs CaDiCaL natif), le choix du reasoner est une **décision d'ingénierie** pilotée par la taille du domaine : exactitude quand elle est atteignable, approximation contrôlée quand elle ne l'est pas.\n" @@ -1013,7 +1278,16 @@ { "cell_type": "markdown", "id": "14efc9df", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.004068, + "end_time": "2026-09-29T17:37:27.902347+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:27.898279+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Exercices (#2161 — 3 exos conformes)Les exercices suivent la convention `.claude/rules/three-exercises-per-notebook.md` : ils sont **stubbés** (sans `raise NotImplementedError`, cf règle C.1) et **répartis** dans le notebook, chacun précédé d'un contexte et d'objectifs.### Exercice 1\n", " : Étendre le réseau social**Contexte** : Le réseau de la partie 2 contient 3 personnes (anna, bob, carl). On veut y ajouter un 4ᵉ individu **dave** et observer la propagation de l'influence.**Objectif** :- Ajouter `dave` à la signature (sort `Person`)- Ajouter le fait que `Friends(carl, dave)` (pondéré ou strict ?)- Requérir `P(Smokes(dave))` et `P(Cancer(dave))` après la propagation**Indice** : il faut propager le tabagisme le long de la chaîne `anna → bob → carl → dave` via la règle d'amitié pondérée.### Exercice 2 : Un MLN de diagnostic médical**Contexte** : On veut modéliser un raisonnement de diagnostic : certaines maladies causent des symptômes, et des tests médicaux confirment/infirment les maladies.**Objectif** :- Créer un MLN avec : `Grippe(X) => Fievre(X)` (poids 2.0), `Covid(X) => Fievre(X)` (poids 2.5), `Fievre(X) => TestPositif(X)` (poids 1.5)- Ajouter le fait : `Fievre(marie)` (observé)- Requérir `P(Grippe(marie))` et `P(Covid(marie))` — quelle maladie est la plus probable ?**Indice** : les deux maladies expliquent la fièvre, mais la Covid a un poids légèrement plus élevé pour `Fievre`. Le MLN doit gérer cette **ambiguïté** correctement.### Exercice 3 : Trouver le seuil où une règle devient « quasi-stricte »**Contexte** : Dans la partie 3, on a vu que `P(Cancer(bob))` augmente avec le poids de la règle `Smokes(X) => Cancer(X)`. On veut déterminer **à partir de quel poids** la règle est *effectivement stricte* (probabilité de violation < 0.01).**Objectif** :- Boucler sur les poids `[3, 5, 7, 10, 15, 20]` et observer `P(¬Cancer(bob))` (i.e. `1 - P(Cancer(bob))`)- Identifier le poids à partir duquel la probabilité de violation passe sous 0.01 (i.e. la règle est quasi-stricte)**Indice** : plus le poids est grand, plus la violation coûte `exp(-w)`. Pour un domaine de 3 personnes, le seuil est autour de `w = 5-7` (cf partie 3)." @@ -1025,18 +1299,26 @@ "id": "d6d059ee", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.472476Z", - "iopub.status.busy": "2026-07-03T14:28:19.472103Z", - "iopub.status.idle": "2026-07-03T14:28:19.527283Z", - "shell.execute_reply": "2026-07-03T14:28:19.526941Z" - } + "iopub.execute_input": "2026-09-29T17:37:27.912659Z", + "iopub.status.busy": "2026-09-29T17:37:27.912399Z", + "iopub.status.idle": "2026-09-29T17:37:27.933237Z", + "shell.execute_reply": "2026-09-29T17:37:27.933375Z" + }, + "papermill": { + "duration": 0.026902, + "end_time": "2026-09-29T17:37:27.933481+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:27.906579+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "// --- Exercice 1 : étendre le réseau social à un 4ᵉ individu --- = Exercice a completer\r\n" + "// --- Exercice 1 : étendre le réseau social à un 4ᵉ individu --- = Exercice a completer\n" ] } ], @@ -1062,18 +1344,26 @@ "id": "d6b456d3", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.529356Z", - "iopub.status.busy": "2026-07-03T14:28:19.528940Z", - "iopub.status.idle": "2026-07-03T14:28:19.616539Z", - "shell.execute_reply": "2026-07-03T14:28:19.616313Z" - } + "iopub.execute_input": "2026-09-29T17:37:27.952607Z", + "iopub.status.busy": "2026-09-29T17:37:27.952399Z", + "iopub.status.idle": "2026-09-29T17:37:27.987132Z", + "shell.execute_reply": "2026-09-29T17:37:27.986930Z" + }, + "papermill": { + "duration": 0.041952, + "end_time": "2026-09-29T17:37:27.987226+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:27.945274+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "// --- Exercice 2 : MLN de diagnostic médical --- = Exercice a completer\r\n" + "// --- Exercice 2 : MLN de diagnostic médical --- = Exercice a completer\n" ] } ], @@ -1099,18 +1389,26 @@ "id": "44567848", "metadata": { "execution": { - "iopub.execute_input": "2026-07-03T14:28:19.618435Z", - "iopub.status.busy": "2026-07-03T14:28:19.618041Z", - "iopub.status.idle": "2026-07-03T14:28:19.669410Z", - "shell.execute_reply": "2026-07-03T14:28:19.669168Z" - } + "iopub.execute_input": "2026-09-29T17:37:27.998441Z", + "iopub.status.busy": "2026-09-29T17:37:27.998132Z", + "iopub.status.idle": "2026-09-29T17:37:28.015239Z", + "shell.execute_reply": "2026-09-29T17:37:28.014868Z" + }, + "papermill": { + "duration": 0.023256, + "end_time": "2026-09-29T17:37:28.015373+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:27.992117+00:00", + "status": "completed" + }, + "tags": [] }, "outputs": [ { - "output_type": "stream", "name": "stdout", + "output_type": "stream", "text": [ - "// --- Exercice 3 : seuil où une règle pondérée devient quasi-stricte --- = Exercice a completer\r\n" + "// --- Exercice 3 : seuil où une règle pondérée devient quasi-stricte --- = Exercice a completer\n" ] } ], @@ -1133,7 +1431,16 @@ { "cell_type": "markdown", "id": "b5cf8af4", - "metadata": {}, + "metadata": { + "papermill": { + "duration": 0.008625, + "end_time": "2026-09-29T17:37:28.032008+00:00", + "exception": false, + "start_time": "2026-09-29T17:37:28.023383+00:00", + "status": "completed" + }, + "tags": [] + }, "source": [ "## Résumé\n", "Ce notebook a couvert :\n", @@ -1172,8 +1479,20 @@ "pygments_lexer": "csharp", "version": "13.0" }, + "papermill": { + "default_parameters": {}, + "duration": 107.731163, + "end_time": "2026-09-29T17:37:28.157693+00:00", + "environment_variables": {}, + "exception": null, + "input_path": "Tweety-10-MLN-Csharp.ipynb", + "output_path": "Tweety-10-MLN-Csharp.ipynb", + "parameters": {}, + "start_time": "2026-09-29T17:35:40.426530+00:00", + "version": "2.7.0" + }, "title": "Tweety-10 — Markov Logic Networks (MLN) en .NET (C# / IKVM)" }, "nbformat": 4, "nbformat_minor": 5 -} +} \ No newline at end of file diff --git a/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-11-Causal-Csharp.ipynb b/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-11-Causal-Csharp.ipynb index c431cd2f65..5979952502 100644 --- a/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-11-Causal-Csharp.ipynb +++ b/MyIA.AI.Notebooks/SymbolicAI/Tweety/Tweety-11-Causal-Csharp.ipynb @@ -5,10 +5,10 @@ "id": "22185c95", "metadata": { "papermill": { - "duration": 0.026801, - "end_time": "2026-08-12T05:14:40.245936+00:00", + "duration": 0.003527, + "end_time": "2026-09-29T17:37:33.915250+00:00", "exception": false, - "start_time": "2026-08-12T05:14:40.219135+00:00", + "start_time": "2026-09-29T17:37:33.911723+00:00", "status": "completed" }, "tags": [] @@ -33,10 +33,10 @@ "id": "613cd651", "metadata": { "papermill": { - "duration": 0.019326, - "end_time": "2026-08-12T05:14:40.284164+00:00", + "duration": 0.003272, + "end_time": "2026-09-29T17:37:33.921806+00:00", "exception": false, - "start_time": "2026-08-12T05:14:40.264838+00:00", + "start_time": "2026-09-29T17:37:33.918534+00:00", "status": "completed" }, "tags": [] @@ -58,16 +58,16 @@ "id": "27e6a6d2", "metadata": { "execution": { - "iopub.execute_input": "2026-08-12T05:14:40.329520Z", - "iopub.status.busy": "2026-08-12T05:14:40.318874Z", - "iopub.status.idle": "2026-08-12T05:14:41.398086Z", - "shell.execute_reply": "2026-08-12T05:14:41.395983Z" + "iopub.execute_input": "2026-09-29T17:37:33.941107Z", + "iopub.status.busy": "2026-09-29T17:37:33.933635Z", + "iopub.status.idle": "2026-09-29T17:37:35.569214Z", + "shell.execute_reply": "2026-09-29T17:37:35.563343Z" }, "papermill": { - "duration": 1.10404, - "end_time": "2026-08-12T05:14:41.398407+00:00", + "duration": 1.644738, + "end_time": "2026-09-29T17:37:35.569461+00:00", "exception": false, - "start_time": "2026-08-12T05:14:40.294367+00:00", + "start_time": "2026-09-29T17:37:33.924723+00:00", "status": "completed" }, "tags": [] @@ -78,10 +78,11 @@ "text/html": [ "\r\n", "
\r\n", - "