Labyrinthe, par Clems, pour le SDZ

Introduction

Bonjour et bienvenue dans ma documentation :-)
Je vais tenter d'expliquer au mieux le fonctionnement général du script (pour tous les détails, il faut voir les sources php, que j'ai soigneusement commentées). J'ai essayer de faire le script le plus propre que j'ai pu. Certaines portions cependant sont moins propres que d'autres (je pense notamment à la fonction Chrono_aff (l. 216) qui m'a un peu pris la tête ^^). J'ai opté pour la POO, vu l'envergure du script. Pour l'occasion, j'ai créer un petit système de log, ce que j'appellerais ensuite "le journal", et un petit système de chronomètre. Ces deux éléments auraient pu être mis à part, dans une autre classe "monitoring" par exemple, mais je ne l'ai pas fait ^^.

Architecture

Architecture des fichiers

Architecture du script (labyrinthe.class.php)

Fonctionnement

Numérotation des cases et des murs

Le début des deux méthodes consiste à numéroter les cases et les murs de façons logique, histoire de savoir sur quoi on travaille. La numérotation des cases du labyrinthe se fait de gauche à droite, du haut vers le bas. La case en haut à gauche est la case 1 (et non 0). Pour les murs, je suis le meme ordre que pour les cases.
Exemple : labyrinthe de 3*4 :

11233547
2468
59611713815
10121416
917101911211223
18202224

Je crée ensuite un array $this->murs_enlevables contenant les murs supprimables (ceux qui ne sont pas sur les bords), dupliqué dans $this->murs_restants au début du script, pour pouvoir travailler sur le tableau en gardant les informations de départ).

Méthode "Fusion"

Pour la génération par Fusion, je commence par attribuer à chaque case un numéro de groupe. Au début, la case N appartient au groupe N. Je tire ensuite au hasard un murs dans $this->murs_restants (fonction Enleve_Mur(), l.430) : à chaque fois qu'un mur est choisi, deux possibilités :

Je continue ainsi à choisir des murs au hasard parmis les murs restants non-visités, jusqu'à ce qu'il n'y ai plus qu'un seul groupe de case.
Le labyrinthe est généré !

Méthode "Exploration"

Je commence pas créer le tableau $this->cases_voisines, associant chaque case (clés) à ses voisines (valeurs). Ensuite, à partir de la case de départ, je choisis au hasard une voisine, qui devient la case courante. Cette case courante est retirée des voisines possible de ses cases voisines, afin de ne pas pouvoir revenir dessus. Tout ceci est géré par la fonction Choix_case(), l.407. Si on arrive sur une case qui n'a plus de voisine non-visitée, on revient en arrière grâce à $this->pile. Ainsi de suite, j'avance de case en case, jusqu'à ce que $this->cases_visitees contienne autant d'éléments que le labyrinthe de cases.
Le labyrinthe est généré !

Résolution

Fonction Resolution(), l.514.
La méthode de résolution du labyrinthe est sensiblement la même que celle de la génération par "exploration", à ceci prêt que pour la résolution, j'utilise l'heuristique (Wikipédia ) suivante :

Mon script est en mesure de gérer une case de départ autre que l'angle haut-gauche et une case d'arrivée en bas à droite, mais il aurait alors fallu intégrer un petit bout de code déterminant quelle était la meilleur "direction" en cas de choix; je ne pense pas que ce soit bien difficile à faire, c'est juste que je n'ai pas le temps de m'y mettre maintenant (il est 23h35 ^^). Donc, tant que la case courante n'est pas la case d'arrivée, j'avance de cases voisines en cases voisines (en privilégiant le bas et la droite), les possibilités étant déterminées par la fonction Cases_possibles(), l.547. Si je me retrouve bloqué (aucune voisine possible), c'est que le chemin n'est pas le bon. Je l'efface jusqu'au dernier choix que j'ai eu à faire, et je prends une autre direction.

Affichage

Le dossier "palette" contient tout le nécessaire à la sélection d'une couleur et à l'auto-completion des champs du formulaire. Ce n'est pas très développé car ça fait partie des "petits plus" sur lesquels je n'ai pas passez trop de temps.

La fonction Affichage(), l.514 vérifie les paramêtre nécessaire à l'affichage, tandis que la fonction Affichage_go(), l.661 appellent les fonctions travaillant avec GD. Au niveau de l'affichage à proprement parlé, j'utilise la librairie GD, qui permet des possibilités bien supérieures à l'affichage html. Je gère deux types d'affichage :

Performances

Fusion

/!\L'algorythme "fusion" n'est pas du tout optimisé /!\
Je pense qu'il n'est pas pertinent de mettre ses performances ici, étant donné que je ne me suis pas interressé à son optimisation. J'ai hésité à le laisser dans la class, mais étant donné que je le l'ai quand même codé, ça aurait été dommage...

Exploration

Sur mon ordinateur : AMD 3200+ à 2.7Ghz et 1go de RAM Corsair Value, j'arrive à générer (avec l'aglorythme "exploration") :

Bug connu

soucis de récurence dans l'affichage du chrono
l'affichage ne passe bien que sur Firefox
Par contre, la source est niquelle ^^

Bugs inconnus

Je les ai pas encore trouvés ^^