Partage
  • Partager sur Facebook
  • Partager sur Twitter

Périmètre d'une Map - gérer les bords

Sujet résolu
    12 février 2022 à 19:34:38

    Bonjour à tous,

    je me suis attaqué à un problème d'apprentissage : on me donne en entrée une grille mettons de 10x15 cases, remplies de 0 ou de 1 : les 1 matérialisent un terrain dont je dois calculer le périmètre. Ce terrain est plein (continuité de 1 dans tout le terrain).

    Pour calculer le périmètre, j'ai voulu construire un code itératif : 

    (1) Je commence par trouver une 1ère case du périmètre en parcourant les cases ligne à ligne, colonne par colonne jusqu'à rencontrer un 1.

    (2) Puis à chaque pas de l'algorithme (schéma ci-dessous, les 1 sont symbolisés par la couleur jaune) :

    • j'ai les infos de case courante (C), de case précédente (P) et la valeur courante du périmètre
    • je cherche la case suivante (F) en faisant le tour anti-horaire des cases voisines de ma case courante
    • quand j'ai trouvé la case suivante, je fais l'ajout de périmètre que ma case courante apporte, je fais le transfert courant --> précédent, et j'itère

    En bref, dans le référentiel défini par le couple (P,C) je réalise toujours le même parcours de recherche :

    En considérant 3 possibles positions (P) par rapport à (C), je peux affirmer que la case à gauche de (C) est vide, et je recherche circulairement la case future.

    Maintenant mon problème !

    J'ai voulu construire un algorithme qui applique cette logique, via plusieurs "if" simplement pour prendre en compte les différentes orientations du couple (P;C) : P au dessus de C, à sa gauche, en dessous etc. et du coup adapter le chemin de recherche de la case suivante.

    Mon soucis : comment Java va réagir aux cas particuliers où mes cases se trouvent à un bord de la grille, et si cela crée des erreurs comment je peux les gérer sans me retrouver à faire une usine à gaz de conditions "if" pour gérer chaque cas particulier ??

    Pour mon code ci-dessous :

    • int[i][j] carte = la grille des cases 0 ou 1
    • ci, cj = les coordonnées de la case courante
    • prev_case la position de la case précédente par rapport à la case courante, de 0 à 7 dans le sens anti-horaire avec 0 quand prev est au dessus de la case courante
    • perimetre = calcul incrémental du périmètre
    while(ci != pi && cj != pj) {
            	// PREV CASE U ou UL
            	if(prev_case == 0 || prev_case == 1) {									
            		if(carte[ci + 1][cj - 1] == 1) {
            			perimetre ++;
            			prev_case = 7;
            			ci ++;
            			cj --;
            		} else if(carte[ci + 1][cj] == 1) {
            			perimetre ++;
            			prev_case = 0;
            			ci ++;
            		} else if(carte[ci + 1][cj + 1] == 1) {
            			perimetre += 2;
            			prev_case = 1;
            			ci ++;
            			cj ++;
            		} else if(carte[ci][cj + 1] == 1) {
            			perimetre += 2;
            			prev_case = 2;
            			cj ++;
            		} else if(carte[ci - 1][cj + 1] == 1) {
            			perimetre += 3;
            			prev_case = 3;
            			ci --;
            			cj ++;
            		} else {
            			perimetre += 3;
            			prev_case = 4;
            			ci --;
            		}
            	}
            }

    Merci à toute personne étant arrivé jusqu'ici, et pour toute aide !

    [EDIT] J'oubliais ! J'ai tout de même cherché un moment, et je n'ai trouvé que les outils "try/catch" mais cela ne me satisfait pas, je ne veux pas mettre chacun de mes tests "if" dans un "try" ...

    Ou alors je n'ai pas compris comment les utiliser !

    -
    Edité par Mobydikk 12 février 2022 à 19:57:06

    • Partager sur Facebook
    • Partager sur Twitter
      12 février 2022 à 20:49:45

      Bonjour,

      Pour chercher le périmètre, c'est simple. Pour chaque case, tu regardes si elle fait partie du terrain.

      Si  oui, on regarde si elle touche le bord gauche ou si la case à gauche est hors terrain.

      On fait de même avec les trois autres directions.

      • Partager sur Facebook
      • Partager sur Twitter
        12 février 2022 à 23:56:38

        Bonsoir,

        je te remercie de l'idée ! 

        Pour tout dire, j'ai simplifié mon sujet d'étude pour rendre l'explication facile. Mon algorithme doit en fait être résistant à des maps pour lesquelles il existe des zones de "0" internes (étangs au milieu du jardin).

        Quoi qu'il en soit, j'ai trouvé une solution de mon côté : construire une map à partir de celle de départ, en augmentant les bords de une case '0'. Du coup, plus de problèmes ! 

        • Partager sur Facebook
        • Partager sur Twitter

        Périmètre d'une Map - gérer les bords

        × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
        × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
        • Editeur
        • Markdown