/*************************************************************************************************************************************/
/*                                                                                                                                   */
/*        C O N S T R U C T I O N   D E   L ' E P O N G E   D E   M E N G E R  :                                                     */
/*                                                                                                                                   */
/*                                                                                                                                   */
/*        Author of '$xrf/EpongeDeMenger.01$I' :                                                                                     */
/*                                                                                                                                   */
/*                    Jean-Francois COLONNA (LACTAMME, 20140909133215).                                                              */
/*                                                                                                                                   */
/*************************************************************************************************************************************/

/*===================================================================================================================================*/
/*************************************************************************************************************************************/
/*                                                                                                                                   */
/*        G E N E R A T I O N   R E C U R S I V E   D E   L ' E P O N G E   D E   M E N G E R  :                                     */
/*                                                                                                                                   */
/*************************************************************************************************************************************/
DEFV(Local,DEFV(Logical,INIT(compatibilite_20240617,COMPATIBILITE_20240617)));
                                        /* Permet de proceder a des calculs compatibles a ceux qui furent effectues anterieurement   */
                                        /* au 20240617093456.                                                                        */
                                        /*                                                                                           */
                                        /* Le 20240618075356, a cause des images du type 'v $xiirf/SIER.61.2' ou les bords sont      */
                                        /* marques, je suis passe par defaut au mode compatibilite...                                */

DEFV(Local,DEFV(Logical,INIT(compatibilite_20240917,COMPATIBILITE_20240917)));
                                        /* Permet de proceder a des calculs compatibles a ceux qui furent effectues anterieurement   */
                                        /* au 20240917095113.                                                                        */

#define   Translation_Optionnelle_MaximumDoIn                                                                                           \
                    COND(IL_FAUT(compatibilite_20240617),ZERO,UN)

#define   Cube_cDENORMALISE_OX(coordonneeX)                                                                                             \
                    OPC1(IL_FAUT(utiliser_la_super_echelle)                                                                             \
                        ,SUPER_cDENORMALISE_OX                                                                                          \
                        ,_cDENORMALISE_OX                                                                                               \
                        ,coordonneeX                                                                                                    \
                         )
#define   XCubeMinimum                                                                                                                  \
                    Cube_cDENORMALISE_OX(NEUT(ASI1(origine_du_cube,x)))
#define   XCubeMaximum                                                                                                                  \
                    Cube_cDENORMALISE_OX(ADD2(ASI1(origine_du_cube,x),ASI1(cote_du_cube,dx)))
#define   XCubeMinimumDoIn                                                                                                              \
                    XCubeMinimum
#define   XCubeMaximumDoIn                                                                                                              \
                    nPREX(XCubeMaximum,Translation_Optionnelle_MaximumDoIn)

#define   Cube_cDENORMALISE_OY(coordonneeY)                                                                                             \
                    OPC1(IL_FAUT(utiliser_la_super_echelle)                                                                             \
                        ,SUPER_cDENORMALISE_OY                                                                                          \
                        ,_cDENORMALISE_OY                                                                                               \
                        ,coordonneeY                                                                                                    \
                         )
#define   YCubeMinimum                                                                                                                  \
                    Cube_cDENORMALISE_OY(NEUT(ASI1(origine_du_cube,y)))
#define   YCubeMaximum                                                                                                                  \
                    Cube_cDENORMALISE_OY(ADD2(ASI1(origine_du_cube,y),ASI1(cote_du_cube,dy)))
#define   YCubeMinimumDoIn                                                                                                              \
                    YCubeMinimum
#define   YCubeMaximumDoIn                                                                                                              \
                    nPREY(YCubeMaximum,Translation_Optionnelle_MaximumDoIn)

#define   Cube_cDENORMALISE_OZ(coordonneeZ)                                                                                             \
                    OPC1(IL_FAUT(utiliser_la_super_echelle)                                                                             \
                        ,SUPER_cDENORMALISE_OZ                                                                                          \
                        ,_cDENORMALISE_OZ                                                                                               \
                        ,coordonneeZ                                                                                                    \
                         )
#define   ZCubeMinimum                                                                                                                  \
                    Cube_cDENORMALISE_OZ(NEUT(ASI1(origine_du_cube,z)))
#define   ZCubeMaximum                                                                                                                  \
                    Cube_cDENORMALISE_OZ(ADD2(ASI1(origine_du_cube,z),ASI1(cote_du_cube,dz)))
#define   ZCubeMinimumDoIn                                                                                                              \
                    ZCubeMinimum
#define   ZCubeMaximumDoIn                                                                                                              \
                    COND(IFEQ(ZCubeMinimum,ZCubeMaximum)                                                                                \
                        ,ZCubeMaximum                                                                                                   \
                        ,nPREZ(ZCubeMaximum,Translation_Optionnelle_MaximumDoIn)                                                        \
                         )
                                        /* Definition du "cube" courant dont les cotes, apres denormalisations, ne sont pas          */
                                        /* necessairement egaux (et ce a cause des definitions des axes 'OX', 'OY' et 'OZ' qui sont  */
                                        /* a priori et en toute generalite differentes). Ceci a ete introduit le 20140923160150.     */
                                        /*                                                                                           */
                                        /* Le 20240617093723 je note (suite a la modification du 20240617080311 qui permet de        */
                                        /* colorier differemment les carres et les cubes...) qu'il y a un recouvrement sur les       */
                                        /* cotes correspondant aux maxima...                                                         */
                                        /*                                                                                           */
                                        /* La definition particuliere de 'ZCubeMaximumDoIn' est due au fait que l'on genere aussi    */
                                        /* des tapis de Sierpinski qui n'ont donc pas d'epaisseur 'Z'...                             */

#define   TRACER(compteur,tabulation,sequence)                                                                                          \
                    Bblock                                                                                                              \
                    Test(IL_FAUT(tracer_les_differentes_operations))                                                                    \
                         Bblock                                                                                                         \
                         CAL3(Prme4("NumeroTrace=%04d%*s fonction=%s"                                                                   \
                                   ,compteur                                                                                            \
                                   ,COND(IFEQ(tabulation,UNDEF),GRO10(profondeur_courante),tabulation)                                  \
                                   ,C_VIDE                                                                                              \
                                   ,NomDeLaFonctionCourante                                                                             \
                                    )                                                                                                   \
                              );                                                                                                        \
                                                                                                                                        \
                         BLOC(sequence);                                                                                                \
                                                                                                                                        \
                         INCR(compteur,I);                                                                                              \
                         Eblock                                                                                                         \
                    ATes                                                                                                                \
                         Bblock                                                                                                         \
                         Eblock                                                                                                         \
                    ETes                                                                                                                \
                    Eblock                                                                                                              \
                                        /* Procedure introduite le 20240618150653...                                                 */

DEFV(Local,DEFV(Float,INIT(increment_courant_de__niveau_de_marquage_de_l_eponge,ZERO)));
DEFV(Local,DEFV(Float,INIT(increment_de__increment_courant_de__niveau_de_marquage_de_l_eponge,ZERO)));
                                        /* Afin de pouvoir faire varier 'niveau_de_marquage_de_l_eponge' au cours du temps. Ceci     */
                                        /* fut introduit le 20240617080311...                                                        */
                                        /*                                                                                           */
                                        /* Le 20240621093645 il y a eu passage de 'Int' a 'Float' afin de permettre de gerer de      */
                                        /* tres longues sequences d'incrementation sans problemes de "debordement"...                */

BFonctionI

DEFV(LoF,DEFV(FonctionI,GenerationDunCube(ARGUMENT_POINTERs(origine_du_cube)
                                         ,ARGUMENT_POINTERs(cote_du_cube)
                                         ,album_d_imagesR
                                         ,niveau_de_marquage_de_l_eponge
                                         ,marquer_le_bord_X_de_l_eponge
                                         ,marquer_le_bord_Y_de_l_eponge
                                         ,marquer_le_bord_Z_de_l_eponge
                                         ,niveau_de_marquage_du_bord_de_l_eponge
                                         ,ARGUMENT_POINTERs(rapport_d_homothetie_cumule)
                                         ,profondeur_courante
                                          )
              )
     )
                                        /* La mise de cette fonction dans un '$I' est due aux operateurs 'OPC1(...)' qu'elle         */
                                        /* utilise un peu plus loin. Cette fonction a ete introduite le 20140916105025...            */
DEFV(Argument,DEFV(pointF_3D,POINTERs(origine_du_cube)));
DEFV(Argument,DEFV(deltaF_3D,POINTERs(cote_du_cube)));
                                        /* Definition du cube Argument.                                                              */
DEFV(Argument,DEFV(album,album_d_imagesR));
DEFV(Argument,DEFV(genere_p,niveau_de_marquage_de_l_eponge));
DEFV(Argument,DEFV(Logical,marquer_le_bord_X_de_l_eponge));
DEFV(Argument,DEFV(Logical,marquer_le_bord_Y_de_l_eponge));
DEFV(Argument,DEFV(Logical,marquer_le_bord_Z_de_l_eponge));
DEFV(Argument,DEFV(genere_p,niveau_de_marquage_du_bord_de_l_eponge));
                                        /* La possibilite de marquer le bord differemment a ete introduite le 20150326151832...      */
DEFV(Argument,DEFV(coeffI_3D,POINTERs(rapport_d_homothetie_cumule)));
                                        /* Introduit le 20171117174022...                                                            */
DEFV(Argument,DEFV(Int,profondeur_courante));
                                        /* Definition du niveau de recursivite (ne sert que pour 'TRACER(...)').                     */
/*-----------------------------------------------------------------------------------------------------------------------------------*/
     Bblock
     INIT_ERROR;
     /*..............................................................................................................................*/
     TRACER(compteur_de_trace_1
           ,UNDEF
           ,BLOC(
                 Bblock
                 CAL3(Prme6(".......... : OrigineCube={%04d,%04d,%04d} ExtremiteCube={%04d,%04d,%04d}\n"
                           ,Cube_cDENORMALISE_OX(NEUT(ASI1(origine_du_cube,x)))
                           ,Cube_cDENORMALISE_OY(NEUT(ASI1(origine_du_cube,y)))
                           ,Cube_cDENORMALISE_OZ(NEUT(ASI1(origine_du_cube,z)))
                           ,Cube_cDENORMALISE_OX(ADD2(ASI1(origine_du_cube,x),ASI1(cote_du_cube,dx)))
                           ,Cube_cDENORMALISE_OY(ADD2(ASI1(origine_du_cube,y),ASI1(cote_du_cube,dy)))
                           ,Cube_cDENORMALISE_OZ(ADD2(ASI1(origine_du_cube,z),ASI1(cote_du_cube,dz)))
                            )
                      );
                 Eblock
                 )
            );

     begin_albumQ(DoIn,ZCubeMinimumDoIn,ZCubeMaximumDoIn,PasZ
                 ,DoIn,YCubeMinimumDoIn,YCubeMaximumDoIn,PasY
                 ,DoIn,XCubeMinimumDoIn,XCubeMaximumDoIn,PasX
                  )
          Bblock
          DEFV(Logical,INIT(marquer_le_point_courant,VRAI));

          DEFV(genere_p,INIT(niveau_de_marquage
                            ,COND(I3OU(IFET(IL_FAUT(marquer_le_bord_X_de_l_eponge)
                                           ,IFOU(IFEQ(X,XCubeMinimum),IFEQ(X,XCubeMaximumDoIn))
                                            )
                                      ,IFET(IL_FAUT(marquer_le_bord_Y_de_l_eponge)
                                           ,IFOU(IFEQ(Y,YCubeMinimum),IFEQ(Y,YCubeMaximumDoIn))
                                            )
                                      ,IFET(IL_FAUT(marquer_le_bord_Z_de_l_eponge)
                                           ,IFOU(IFEQ(Z,ZCubeMinimum),IFEQ(Z,XCubeMaximumDoIn))
                                            )
                                       )
                                 ,niveau_de_marquage_du_bord_de_l_eponge
                                 ,ADD2(niveau_de_marquage_de_l_eponge,INTE(increment_courant_de__niveau_de_marquage_de_l_eponge))
                                  )
                             )
               );

          Test(IL_FAUT(generaliser_les_cubes))
               Bblock
               DEFV(Float,INIT(XCubeCentre,ADD2(ASI1(origine_du_cube,x),MOIT(ASI1(cote_du_cube,dx)))));
               DEFV(Float,INIT(YCubeCentre,ADD2(ASI1(origine_du_cube,y),MOIT(ASI1(cote_du_cube,dy)))));
               DEFV(Float,INIT(ZCubeCentre,ADD2(ASI1(origine_du_cube,z),MOIT(ASI1(cote_du_cube,dz)))));
                                        /* Introduits le 20171117160410...                                                           */

               DEFV(Float,INIT(XCubeCourant,FLOT__UNDEF));
               DEFV(Float,INIT(YCubeCourant,FLOT__UNDEF));
               DEFV(Float,INIT(ZCubeCourant,FLOT__UNDEF));

               DEFV(Float,INIT(equation_locale,FLOT__UNDEF));

               EGAL(XCubeCourant
                   ,MUL2(ASI1(rapport_d_homothetie_cumule,cx)
                        ,SOUS(Cube_cDENORMALISE_OX(X),XCubeCentre)
                         )
                    );
               EGAL(YCubeCourant
                   ,MUL2(ASI1(rapport_d_homothetie_cumule,cy)
                        ,SOUS(Cube_cDENORMALISE_OY(Y),YCubeCentre)
                         )
                    );
               EGAL(ZCubeCourant
                   ,MUL2(ASI1(rapport_d_homothetie_cumule,cz)
                        ,SOUS(Cube_cDENORMALISE_OZ(Z),ZCubeCentre)
                         )
                    );

               EGAL(equation_locale,HORNER_3_03__COUPE_QUELCONQUE_ALBUM(XCubeCourant,YCubeCourant,ZCubeCourant));
                                        /* Calcul d'un polynome au point {X,Y,Z}, l'origine des coordonnees etant le centre du cube. */
                                        /*                                                                                           */
                                        /* On rappelle les correspondances suivantes :                                               */
                                        /*                                                                                           */
                                        /*                  a001      -->       x                                                    */
                                        /*                  a010      -->       y                                                    */
                                        /*                  a100      -->       z                                                    */
                                        /*                  (...)                                                                    */
                                        /*                                                                                           */
                                        /* Ainsi, par exemple, pour calculer :                                                       */
                                        /*                                                                                           */
                                        /*                  x-y                                                                      */
                                        /*                                                                                           */
                                        /* on fera :                                                                                 */
                                        /*                                                                                           */
                                        /*                  a???=0                                                                   */
                                        /*                                                                                           */
                                        /*                  a001=+1             +1.x                                                 */
                                        /*                  a010=-1                  -1.y                                            */
                                        /*                  a100=0                        +0.z                                       */
                                        /*                  a000=0                             +0                                    */
                                        /*                                                                                           */

               Test(OPC1(IL_FAUT(generaliser_les_cubes_____faire_un_IZLE)
                        ,IZLE
                        ,IZGT
                        ,equation_locale
                         )
                    )
                    Bblock
                                        /* Cas :                                                                                     */
                                        /*                                                                                           */
                                        /*                  HORNER_3_03(X,Y,Z) <= 0                                                  */
                                        /*                                                                                           */
                                        /* (test par defaut...).                                                                     */
                    Eblock
               ATes
                    Bblock
                    EGAL(marquer_le_point_courant,FAUX);
                                        /* Cas :                                                                                     */
                                        /*                                                                                           */
                                        /*                  HORNER_3_03(X,Y,Z) > 0                                                   */
                                        /*                                                                                           */
                    Eblock
               ETes
               Eblock
          ATes
               Bblock
               Eblock
          ETes

          Test(IL_FAUT(marquer_le_point_courant))
               Bblock
               Astore_point_valide(niveau_de_marquage
                                  ,album_d_imagesR
                                  ,X,Y,Z
                                   );
                                        /* On utilise 'Astore_point_valide(...)' (et non pas 'Astore_point(...)' car, en effet, les  */
                                        /* denormalisations peuvent induire des debordements...                                      */
                                        /*                                                                                           */
                                        /* Le 20240617080311 a ete introduite une eventuelle dynamique de 'niveau_de_marquage'...    */
               Eblock
          ATes
               Bblock
               Eblock
          ETes
          Eblock
     end_albumQ(EDoI,EDoI,EDoI)

     Test(IL_FAUT(compatibilite_20240917))
          Bblock
          Eblock
     ATes
          Bblock
          INCR(increment_courant_de__niveau_de_marquage_de_l_eponge
              ,increment_de__increment_courant_de__niveau_de_marquage_de_l_eponge
               );
                                        /* Introduit le 20240917095113. En effet, il est assez logique que l'on puisse modifier      */
                                        /* le niveau de marquage qu'il y ait ou pas un processus aleatoire...                        */
          Eblock
     ETes

     RETU_ERROR;
     Eblock

EFonctionI

/*===================================================================================================================================*/
/*************************************************************************************************************************************/
/*                                                                                                                                   */
/*        G E N E R A T E U R   A L E A T O I R E  :                                                                                 */
/*                                                                                                                                   */
/*************************************************************************************************************************************/
#include  xrv/ARITHMET.1d.I"
#include  xrv/ARITHMET.21.I"
#include  xrv/champs_5.41.I"

DEFV(Static,DEFV(Positive,INIT(nombre_de_tirages_aleatoires,ZERO)));
                                        /* Introduit le 20240619093414 et utile surtout dans le cas ou sera utilise un generateur    */
                                        /* pre-calcule ('IL_FAUT(utiliser_un_generateur_aleatoire_pre_calcule)')...                  */

DEFV(Static,DEFV(Int,INIT(nombre_d_elements,NOMBRE_D_ELEMENTS)));
                                        /* On notera que l'on ne peut pas utiliser ici :                                             */
                                        /*                                                                                           */
                                        /*                  #include  xrv/ARITHMET.22$I"                                             */
                                        /*                                                                                           */
                                        /* pour definir 'nombre_d_elements' (obligatoire a cause de 'DERNIER_ELEMENT_D_UN_FICHIER'   */
                                        /* qui suit...) a cause de l'absence du 'DEFV(Static,' dans cet include...                   */

#define   VALEURS_ALEATOIRES_PRE_CALCULEES_IMPLICITE                                                                                    \
                    FLOT__BLANC

DEFV(Local,DEFV(Int,INIT(index_des_valeurs_aleatoires_pre_calculees,PREMIER_ELEMENT_D_UN_FICHIER)));
gGENERATION_D_UN_FICHIER(fichier_LISTE_VALEURS_ALEATOIRES_PRE_CALCULEES,liste_initiale_des_VALEURS_ALEATOIRES_PRE_CALCULEES);

#define   ELEMENT_DU_FICHIER_LISTE_VALEURS_ALEATOIRES_PRE_CALCULEES(index)                                                              \
                    gELEMENT_DU_FICHIER(liste_initiale_des_VALEURS_ALEATOIRES_PRE_CALCULEES,index)
                                        /* Acces a un element courant des fichiers de coordonnees et de niveaux.                     */

#define   PSEUDO_CODE_ALEATOIRE                                                                                                         \
                    NEUF                                                                                                                \
                                        /* Introduit le 20240920095025 afin de designer une valeur qui devra etre aleatoire          */ \
                                        /* dans 'ELEMENT_DU_FICHIER_LISTE_VALEURS_ALEATOIRES_PRE_CALCULEES(...)'...                  */


#define   GENERATION_D_UNE_VALEUR_ALEATOIRE(valeur_aleatoire_flottante)                                                                 \
                    Bblock                                                                                                              \
                    Test(IL_NE_FAUT_PAS(utiliser_le_generateur_a_periodicite_parametrable))                                             \
                         Bblock                                                                                                         \
                         EGAL(valeur_aleatoire_flottante                                                                                \
                             ,COND(IL_NE_FAUT_PAS(utiliser_un_espace_de_parametrage_tridimensionnel)                                    \
                                  ,rdnI2D(ADRESSE(point_courant_de_l_espace_de_parametrage_2D)                                          \
                                         ,graine                                                                                        \
                                         ,RDN_INIT_AND_GENERE                                                                           \
                                         ,FLOT(FAUX),FLOT(VRAI)                                                                         \
                                          )                                                                                             \
                                  ,rdnI3D(ADRESSE(point_courant_de_l_espace_de_parametrage_3D)                                          \
                                         ,graine                                                                                        \
                                         ,RDN_INIT_AND_GENERE                                                                           \
                                         ,FLOT(FAUX),FLOT(VRAI)                                                                         \
                                          )                                                                                             \
                                   )                                                                                                    \
                              );                                                                                                        \
                                        /* Generation d'une valeur aleatoire dans [FAUX,VRAI] et parametree par le point courant     */ \
                                        /* de l'espace de parametrage :                                                              */ \
                                                                                                                                        \
                         SPIRALE_INITIALISATION;                                                                                        \
                                        /* Initialisation dynamique de 'spirale_nombre_de_points_a_traiter'.                         */ \
                         SPIRALE_DEPLACEMENT(ASD1(point_courant_de_l_espace_de_parametrage_2D,x)                                        \
                                            ,ASD1(point_courant_de_l_espace_de_parametrage_2D,y)                                        \
                                             );                                                                                         \
                         SPIRALE_DEPLACEMENT(ASD1(point_courant_de_l_espace_de_parametrage_3D,x)                                        \
                                            ,ASD1(point_courant_de_l_espace_de_parametrage_3D,y)                                        \
                                             );                                                                                         \
                                        /* Deplacement du point courant de la spirale de l'espace de parametrage, et ce en restant   */ \
                                        /* dans un plan Z=constante (Zmin)...                                                        */ \
                         SPIRALE_PARCOURS;                                                                                              \
                                        /* Parcours de la spirale avec rotation eventuelle de PI/2 du bras courant...                */ \
                         Eblock                                                                                                         \
                    ATes                                                                                                                \
                         Bblock                                                                                                         \
                         EGAL(valeur_aleatoire_flottante                                                                                \
                             ,rdn_iteratif_cercle()                                                                                     \
                              );                                                                                                        \
                         EGAL(valeur_aleatoire_flottante                                                                                \
                             ,DENO(valeur_aleatoire_flottante,FLOT(FAUX),FLOT(VRAI))                                                    \
                              );                                                                                                        \
                                        /* Generation d'une valeur aleatoire dans [FAUX,VRAI] non parametree par le point courant    */ \
                                        /* de l'espace de parametrage.                                                               */ \
                                        /*                                                                                           */ \
                                        /* ATTENTION : on notera que cela est tres different de l'usage de la regle "A" dans         */ \
                                        /* la liste 'liste_des_cubes_a_subdiviser_avec_d_eventuels_espaces'. En effet, cette         */ \
                                        /* liste n'est utilisee qu'une seule fois a l'initialisation du processus de generation      */ \
                                        /* de la structure, alors que 'utiliser_un_generateur_aleatoire_pre_calcule' est appele pour */ \
                                        /* chaque cube. Et ainisi, deux cubes differents n'auront pas a priori le meme decoupage...  */ \
                         Eblock                                                                                                         \
                    ETes                                                                                                                \
                    Eblock                                                                                                              \
                                        /* Introduit le 20240920095025 afin de pouvoir etre utilise meme dans le cas ou c'est        */ \
                                        /* 'ELEMENT_DU_FICHIER_LISTE_VALEURS_ALEATOIRES_PRE_CALCULEES(...)' qui l'est...             */

#define   FIN_DE_L_INDECISION(valeur_aleatoire_logique)                                                                                 \
                    Bblock                                                                                                              \
                    DEFV(Float,INIT(valeur_aleatoire_flottante,FLOT__UNDEF));                                                           \
                                                                                                                                        \
                    Test(IL_NE_FAUT_PAS(utiliser_un_generateur_aleatoire_pre_calcule))                                                  \
                                        /* Test introduit le 20240617131119...                                                       */ \
                         Bblock                                                                                                         \
                         GENERATION_D_UNE_VALEUR_ALEATOIRE(valeur_aleatoire_flottante);                                                 \
                         Eblock                                                                                                         \
                    ATes                                                                                                                \
                         Bblock                                                                                                         \
                         EGAL(valeur_aleatoire_flottante                                                                                \
                             ,ELEMENT_DU_FICHIER_LISTE_VALEURS_ALEATOIRES_PRE_CALCULEES(index_des_valeurs_aleatoires_pre_calculees)     \
                              );                                                                                                        \
                                                                                                                                        \
                         Test(IFEQ(valeur_aleatoire_flottante,PSEUDO_CODE_ALEATOIRE))                                                   \
                              Bblock                                                                                                    \
                              GENERATION_D_UNE_VALEUR_ALEATOIRE(valeur_aleatoire_flottante);                                            \
                                        /* Generation aleatoire introduite le 20240920095025...                                      */ \
                              Eblock                                                                                                    \
                         ATes                                                                                                           \
                              Bblock                                                                                                    \
                              Eblock                                                                                                    \
                         ETes                                                                                                           \
                                                                                                                                        \
                         EGAL(valeur_aleatoire_flottante,TRON(valeur_aleatoire_flottante,PROBABILITE_NULLE,PROBABILITE_UNITE));         \
                                        /* Generation d'une valeur aleatoire dans [FAUX,VRAI] non parametree par le point courant    */ \
                                        /* de l'espace de parametrage.                                                               */ \
                                                                                                                                        \
                         INCR(index_des_valeurs_aleatoires_pre_calculees,I);                                                            \
                                                                                                                                        \
                         Test(IFGT(index_des_valeurs_aleatoires_pre_calculees,DERNIER_ELEMENT_D_UN_FICHIER));                           \
                              Bblock                                                                                                    \
                              EGAL(index_des_valeurs_aleatoires_pre_calculees,PREMIER_ELEMENT_D_UN_FICHIER);                            \
                              Eblock                                                                                                    \
                         ATes                                                                                                           \
                              Bblock                                                                                                    \
                              Eblock                                                                                                    \
                         ETes                                                                                                           \
                                                                                                                                        \
                         Test(IL_FAUT(compatibilite_20240917))                                                                          \
                              Bblock                                                                                                    \
                              INCR(increment_courant_de__niveau_de_marquage_de_l_eponge                                                 \
                                  ,increment_de__increment_courant_de__niveau_de_marquage_de_l_eponge                                   \
                                   );                                                                                                   \
                                        /* Introduit le 20240617080311 et mis ici le 20240622084330 (et non plus apres le            */ \
                                        /* 'end_albumQ(...)') afin que le niveau de marquage puisse evoluer apres le marquage        */ \
                                        /* de chaque point...                                                                        */ \
                              Eblock                                                                                                    \
                         ATes                                                                                                           \
                              Bblock                                                                                                    \
                              Eblock                                                                                                    \
                         ETes                                                                                                           \
                         Eblock                                                                                                         \
                    ETes                                                                                                                \
                                                                                                                                        \
                    EGAL(valeur_aleatoire_logique                                                                                       \
                        ,COND(IFLE(valeur_aleatoire_flottante                                                                           \
                                  ,HORNER_1_01(DIVI(FLOT(profondeur_courante),FLOT(nombre_d_iterations))                                \
                                              ,A_seuil_d_indecision_entre_FAUX_et_VRAI                                                  \
                                              ,B_seuil_d_indecision_entre_FAUX_et_VRAI                                                  \
                                               )                                                                                        \
                                   )                                                                                                    \
                             ,FAUX                                                                                                      \
                             ,VRAI                                                                                                      \
                              )                                                                                                         \
                         );                                                                                                             \
                                        /* On notera le choix 'IFLE(...)' comme dans 'v $xiii/aleat.1$FON Test.IFLE.rdnI2D'...       */ \
                                        /*                                                                                           */ \
                                        /* Le 20240926165103, le seuil d'indecision est devenu un polynome du premier degre          */ \
                                        /* fonction de 'profondeur_courante' renormalisee (P) :                                      */ \
                                        /*                                                                                           */ \
                                        /*                             1      0                                                      */ \
                                        /*                  seuil = A.P  + B.P                      P E [0,1]                        */ \
                                        /*                                                                                           */ \
                                        /* tel que par defaut (A>=0) au debut du processus (les grands cubes), le seuil est faible   */ \
                                        /* et donc on elimine peu de cubes. Alors qu'a la fin (les petits cubes), le seuil est       */ \
                                        /* eleve et on elimine donc plus de cubes. En choisissant 'A' negatif, ce fonctionnement     */ \
                                        /* est inverse...                                                                            */ \
                                        /*                                                                                           */ \
                                        /* On notera le 20240927100709 que :                                                         */ \
                                        /*                                                                                           */ \
                                        /*                  A=0                 (valeur par defaut)                                  */ \
                                        /*                  B<0                 (par exemple -0.1)                                   */ \
                                        /*                                                                                           */ \
                                        /* provoque l'absence de toute subdivision...                                                */ \
                                        /*                                                                                           */ \
                                        /* Le 20240927111123, en utilisant par exemple :                                             */ \
                                        /*                                                                                           */ \
                                        /*                  A=-1.001                                                                 */ \
                                        /*                  B=+1.000                                                                 */ \
                                        /*                                                                                           */ \
                                        /* tous les gros cubes seront conserves et les petits cubes tres subdivises. On notera       */ \
                                        /* les valeurs suivantes :                                                                   */ \
                                        /*                                                                                           */ \
                                        /*                  pc   ni   P=pc/ni             seuil               nombre d'occurences    */ \
                                        /*                                                                                           */ \
                                        /*                  5    5    1.000000            -0.001000           27                     */ \
                                        /*                  4    5    0.800000            +0.199200           729                    */ \
                                        /*                  3    5    0.600000            +0.399400           15714                  */ \
                                        /*                  2    5    0.400000            +0.599600           251046                 */ \
                                        /*                  1    5    0.200000            +0.799800           2693628                */ \
                                        /*                                                                                           */ \
                                        /* 'pc' et 'ni' designant respectivement 'profondeur_courante' et 'nombre_d_iterations'.     */ \
                                                                                                                                        \
                    INCR(nombre_de_tirages_aleatoires,I);                                                                               \
                                        /* Comptage introduit le 20240619093414...                                                   */ \
                                                                                                                                        \
                    Test(IL_FAUT(editer_les_nombres_aleatoires))                                                                        \
                                        /* Test introduit le 20240706100146...                                                       */ \
                         Bblock                                                                                                         \
                         CAL3(Prme3("ValeurAleatoire(%d)=%+.^^^ --> %s\n"                                                               \
                                   ,nombre_de_tirages_aleatoires                                                                        \
                                   ,valeur_aleatoire_flottante                                                                          \
                                   ,ETAT_LOGIQUE(valeur_aleatoire_logique)                                                              \
                                    )                                                                                                   \
                              );                                                                                                        \
                         Eblock                                                                                                         \
                    ATes                                                                                                                \
                         Bblock                                                                                                         \
                         Eblock                                                                                                         \
                    ETes                                                                                                                \
                    Eblock

/*===================================================================================================================================*/
/*************************************************************************************************************************************/
/*                                                                                                                                   */
/*        G E N E R A T I O N   R E C U R S I V E   D E   L ' E P O N G E   D E   M E N G E R  :                                     */
/*                                                                                                                                   */
/*************************************************************************************************************************************/

#define   OPTIMISER(borne_optimisee,borne_non_optimisee)                                                                                \
                    COND(IL_FAUT(parcours_optimise_de_la_hierarchie_des_cubes),borne_optimisee,borne_non_optimisee)                     \
                                        /* Introduit le 20180101085704...                                                            */

#define   PREMIERE_ITERATION_                                                                                                           \
                    UN
#define   DERNIERE_ITERATION_                                                                                                           \
                    nombre_d_iterations
#define   NOMBRE_EFFECTIF_D_ITERATIONS                                                                                                  \
                    MAX2(UN,NBRE(PREMIERE_ITERATION_,DERNIERE_ITERATION_))
                                        /* Le 'MAX2(UN,...)' a ete introduit le 20191204134246 afin de permettre de faire un         */
                                        /* nombre d'iterations nul ce qui permet d'avoir les ensembles entiers (sans trous...).      */

#define   PREMIER_CUBE_REDUIT_X                                                                                                         \
                    UN
#define   DERNIER_CUBE_REDUIT_X                                                                                                         \
                    ASD1(rapport_d_homothetie,cx)

#define   PREMIER_CUBE_REDUIT_Y                                                                                                         \
                    UN
#define   DERNIER_CUBE_REDUIT_Y                                                                                                         \
                    ASD1(rapport_d_homothetie,cy)

#define   PREMIER_CUBE_REDUIT_Z                                                                                                         \
                    UN
#define   DERNIER_CUBE_REDUIT_Z                                                                                                         \
                    ASD1(rapport_d_homothetie,cz)

#define   CUBE_REDUIT_CENTRAL_X                                                                                                         \
                    MOYE(PREMIER_CUBE_REDUIT_X,DERNIER_CUBE_REDUIT_X)
#define   CUBE_REDUIT_CENTRAL_Y                                                                                                         \
                    MOYE(PREMIER_CUBE_REDUIT_Y,DERNIER_CUBE_REDUIT_Y)
#define   CUBE_REDUIT_CENTRAL_Z                                                                                                         \
                    MOYE(PREMIER_CUBE_REDUIT_Z,DERNIER_CUBE_REDUIT_Z)

#define   NOMBRE_LINEAIRE_DE_CUBES_X                                                                                                    \
                    NBRE(PREMIER_CUBE_REDUIT_X,DERNIER_CUBE_REDUIT_X)
#define   NOMBRE_LINEAIRE_DE_CUBES_Y                                                                                                    \
                    NBRE(PREMIER_CUBE_REDUIT_Y,DERNIER_CUBE_REDUIT_Y)
#define   NOMBRE_LINEAIRE_DE_CUBES_Z                                                                                                    \
                    NBRE(PREMIER_CUBE_REDUIT_Z,DERNIER_CUBE_REDUIT_Z)

#define   NOMBRE_VOLUMIQUE_DE_CUBES                                                                                                     \
                    MUL3(NOMBRE_LINEAIRE_DE_CUBES_X,NOMBRE_LINEAIRE_DE_CUBES_Y,NOMBRE_LINEAIRE_DE_CUBES_Z)

BFonctionI

#define   index_X_des_cubes_reduits                                                                                                     \
                    X
#define   index_Y_des_cubes_reduits                                                                                                     \
                    Y
#define   index_Z_des_cubes_reduits                                                                                                     \
                    Z
                                        /* Index des 3x3x3=27 cubes reduits (27 par defaut) introduit le 20171215143439 sous cette   */
                                        /* forme afin d'utiliser 'begin_albumQ(...)' ci -apres...                                    */

#define   SUBDIVISER_UN_CUBE(index_X_des_cubes_reduits,index_Y_des_cubes_reduits,index_Z_des_cubes_reduits,profondeur_courante)         \
                    IdTb4(selecteur_des_cubes_a_subdiviser                                                                              \
                         ,INDX(profondeur_courante,PREMIERE_ITERATION_),NOMBRE_EFFECTIF_D_ITERATIONS                                    \
                         ,INDX(index_X_des_cubes_reduits,PREMIER_CUBE_REDUIT_X),NOMBRE_LINEAIRE_DE_CUBES_X                              \
                         ,INDX(index_Y_des_cubes_reduits,PREMIER_CUBE_REDUIT_Y),NOMBRE_LINEAIRE_DE_CUBES_Y                              \
                         ,INDX(index_Z_des_cubes_reduits,PREMIER_CUBE_REDUIT_Z),NOMBRE_LINEAIRE_DE_CUBES_Z                              \
                          )

DEFV(Local,DEFV(Int,DdTb4(POINTERi
                         ,selecteur_des_cubes_a_subdiviser
                         ,NOMBRE_EFFECTIF_D_ITERATIONS
                         ,NOMBRE_LINEAIRE_DE_CUBES_Z
                         ,NOMBRE_LINEAIRE_DE_CUBES_Y
                         ,NOMBRE_LINEAIRE_DE_CUBES_X
                         ,ADRESSE_NON_ENCORE_DEFINIE
                          )
                )
     );
                                        /* On notera que 'NOMBRE_LINEAIRE_DE_CUBES' depend de 'rapport_d_homothetie' et que          */
                                        /* celui-ci peut etre redefini via 'v $xrf/EpongeDeMenger.01$K .rh...rapport_d_homothetie'.  */
                                        /* Mais cela n'est pas grave car, en effte, 'NOMBRE_LINEAIRE_DE_CUBES' n'est pas exploite    */
                                        /* par 'DdTb3(...)'.                                                                         */
                                        /*                                                                                           */
                                        /* Le 20180110093215 le type de 'selecteur_des_cubes_a_subdiviser' est passe de 'Logical'    */
                                        /* a 'Int' depuis que des valeurs autres que 'FAUX' et 'VRAI' (en particulier 'INDECIS')     */
                                        /* ont ete introduites le 20180107174041...                                                  */

#define   REDUCTION_D_UN_CUBE                                                                                                           \
                    DEFV(pointF_3D,origine_du_cube_reduit);                                                                             \
                    DEFV(coeffI_3D,prochain_rapport_d_homothetie_cumule);                                                               \
                                                                                                                                        \
                    INITIALISATION_POINT_3D(origine_du_cube_reduit                                                                      \
                                           ,ADD2(ASI1(origine_du_cube,x)                                                                \
                                                ,MUL2(SOUS(index_X_des_cubes_reduits,PREMIER_CUBE_REDUIT_X)                             \
                                                     ,ASD1(cote_du_cube_reduit,dx)                                                      \
                                                      )                                                                                 \
                                                 )                                                                                      \
                                           ,ADD2(ASI1(origine_du_cube,y)                                                                \
                                                ,MUL2(SOUS(index_Y_des_cubes_reduits,PREMIER_CUBE_REDUIT_Y)                             \
                                                     ,ASD1(cote_du_cube_reduit,dy)                                                      \
                                                      )                                                                                 \
                                                 )                                                                                      \
                                           ,ADD2(ASI1(origine_du_cube,z)                                                                \
                                                ,MUL2(SOUS(index_Z_des_cubes_reduits,PREMIER_CUBE_REDUIT_Z)                             \
                                                     ,ASD1(cote_du_cube_reduit,dz)                                                      \
                                                      )                                                                                 \
                                                 )                                                                                      \
                                            );                                                                                          \
                                        /* Definition de l'un des vingt (par defaut) cubes reduits par homothetie de rapport 3       */ \
                                        /* (par defaut) du cube Argument.                                                            */ \
                                                                                                                                        \
                    INITIALISATION_COEFFICIENT_3D(prochain_rapport_d_homothetie_cumule                                                  \
                                                 ,MUL2(ASD1(rapport_d_homothetie,cx),ASI1(rapport_d_homothetie_cumule,cx))              \
                                                 ,MUL2(ASD1(rapport_d_homothetie,cy),ASI1(rapport_d_homothetie_cumule,cy))              \
                                                 ,MUL2(ASD1(rapport_d_homothetie,cz),ASI1(rapport_d_homothetie_cumule,cz))              \
                                                  );                                                                                    \
                                        /* Introduit le 20180116101706 pour la nouvelle option 'STOPPER_LA_SUBDIVISION_D_UN_CUBE'... */ \
                                        /*                                                                                           */ \
                                        /* ATTENTION, il ne faut pas de :                                                            */ \
                                        /*                                                                                           */ \
                                        /*                  Bblock                                                                   */ \
                                        /*                  (...)                                                                    */ \
                                        /*                  Eblock                                                                   */ \
                                        /*                                                                                           */ \
                                        /* dans cette definition, etant donne qu'on y definit differentes donnees utilisees par      */ \
                                        /* la suite...                                                                               */

#define   GENERATION_DUN_CUBE(origine_du_cube,cote_du_cube,rapport_d_homothetie_cumule)                                                 \
                    Bblock                                                                                                              \
                    CALS(GenerationDunCube(origine_du_cube                                                                              \
                                          ,cote_du_cube                                                                                 \
                                          ,album_d_imagesR                                                                              \
                                          ,niveau_de_marquage_de_l_eponge                                                               \
                                          ,marquer_le_bord_X_de_l_eponge                                                                \
                                          ,marquer_le_bord_Y_de_l_eponge                                                                \
                                          ,marquer_le_bord_Z_de_l_eponge                                                                \
                                          ,niveau_de_marquage_du_bord_de_l_eponge                                                       \
                                          ,rapport_d_homothetie_cumule                                                                  \
                                          ,profondeur_courante                                                                          \
                                           )                                                                                            \
                         );                                                                                                             \
                    Eblock                                                                                                              \
                                        /* Introduit le 20180116101706 pour la nouvelle option 'STOPPER_LA_SUBDIVISION_D_UN_CUBE'... */

DEFV(Local,DEFV(Logical,INIT(tabuler_apres_une_C_PD,FAUX)));
DEFV(Local,DEFV(Logical,INIT(eliminer_les_K_LF_redondants,VRAI)));
                                        /* L'elimination des 'K_LF's pourrait etre inhibee si besoin etait...                        */

DEFV(Local,DEFV(CHAR,INIT(caractere_precedent,K_LF)));

#define   EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(caractere)                                                             \
                    Bblock                                                                                                              \
                    DEFV(CHAR,INIT(caractere_courant,caractere));                                                                       \
                    Test(IFET(IL_FAUT(eliminer_les_K_LF_redondants)                                                                     \
                             ,IFET(IFEQ(caractere_courant,K_LF),IFEQ(caractere_precedent,K_LF))                                         \
                              )                                                                                                         \
                         )                                                                                                              \
                         Bblock                                                                                                         \
                         Eblock                                                                                                         \
                    ATes                                                                                                                \
                         Bblock                                                                                                         \
                         CAL3(Prme1("%c"                                                                                                \
                                   ,caractere_courant                                                                                   \
                                    )                                                                                                   \
                              );                                                                                                        \
                         Eblock                                                                                                         \
                    ETes                                                                                                                \
                                                                                                                                        \
                    EGAL(caractere_precedent,caractere_courant);                                                                        \
                                        /* Dispositif introduit le 20240918182033 afin d'eviter des lignes vides en emettant         */ \
                                        /* plusieurs 'K_LF' a la suite...                                                            */ \
                    Eblock

#define   FACTEUR_DE_TABULATION_DES_REGLES                                                                                              \
                    DIX
#define   TABULATION(amplitude)                                                                                                         \
                    Bblock                                                                                                              \
                    CAL3(Prme2("%*s"                                                                                                    \
                              ,MUL2(amplitude,FACTEUR_DE_TABULATION_DES_REGLES)                                                         \
                              ,C_VIDE                                                                                                   \
                               )                                                                                                        \
                         );                                                                                                             \
                    Eblock

#define   NUMERO_D_ITERATION_COURANTE                                                                                                   \
                    SOUS(nombre_d_iterations,profondeur_courante)
#define   NOMBRE_DE_CARACTERES_DU_NUMERO_D_ITERATION_COURANTE                                                                           \
                    DEUX

DEFV(Local,DEFV(FonctionI,GenerationDeLEpongeDeMenger(ARGUMENT_POINTERs(origine_du_cube)
                                                     ,ARGUMENT_POINTERs(cote_du_cube)
                                                     ,profondeur_courante
                                                     ,album_d_imagesR
                                                     ,niveau_de_marquage_de_l_eponge
                                                     ,marquer_le_bord_X_de_l_eponge
                                                     ,marquer_le_bord_Y_de_l_eponge
                                                     ,marquer_le_bord_Z_de_l_eponge
                                                     ,niveau_de_marquage_du_bord_de_l_eponge
                                                     ,c_est_le_premier_cube_de_la_profondeur_courante
                                                     ,ARGUMENT_POINTERs(rapport_d_homothetie_cumule)
                                                      )
                )
     )
                                        /* La mise de cette fonction dans un '$I' est due aux operateurs 'OPC1(...)' qu'elle         */
                                        /* utilise un peu plus loin...                                                               */
DEFV(Argument,DEFV(pointF_3D,POINTERs(origine_du_cube)));
DEFV(Argument,DEFV(deltaF_3D,POINTERs(cote_du_cube)));
                                        /* Definition du cube Argument.                                                              */
DEFV(Argument,DEFV(Int,profondeur_courante));
                                        /* Definition du niveau de recursivite.                                                      */
DEFV(Argument,DEFV(album,album_d_imagesR));
DEFV(Argument,DEFV(genere_p,niveau_de_marquage_de_l_eponge));
DEFV(Argument,DEFV(Logical,marquer_le_bord_X_de_l_eponge));
DEFV(Argument,DEFV(Logical,marquer_le_bord_Y_de_l_eponge));
DEFV(Argument,DEFV(Logical,marquer_le_bord_Z_de_l_eponge));
DEFV(Argument,DEFV(genere_p,niveau_de_marquage_du_bord_de_l_eponge));
                                        /* La possibilite de marquer le bord differement a ete introduite le 20150326151832...       */
DEFV(Argument,DEFV(Logical,c_est_le_premier_cube_de_la_profondeur_courante));
                                        /* Argument introduit le 20140922164132 dans le but de faire des verifications des           */
                                        /* differents cotes des cubes au cours du processus de reduction recursive...                */
DEFV(Argument,DEFV(coeffI_3D,POINTERs(rapport_d_homothetie_cumule)));
                                        /* Introduit le 20171117174022...                                                            */
/*-----------------------------------------------------------------------------------------------------------------------------------*/
     Bblock
     INIT_ERROR;
     /*..............................................................................................................................*/
     TRACER(compteur_de_trace_2
           ,UNDEF
           ,BLOC(
                 Bblock
                 CAL3(Prme6(" : OrigineCube={%04d,%04d,%04d} ExtremiteCube={%04d,%04d,%04d}\n"
                           ,Cube_cDENORMALISE_OX(NEUT(ASI1(origine_du_cube,x)))
                           ,Cube_cDENORMALISE_OY(NEUT(ASI1(origine_du_cube,y)))
                           ,Cube_cDENORMALISE_OZ(NEUT(ASI1(origine_du_cube,z)))
                           ,Cube_cDENORMALISE_OX(ADD2(ASI1(origine_du_cube,x),ASI1(cote_du_cube,dx)))
                           ,Cube_cDENORMALISE_OY(ADD2(ASI1(origine_du_cube,y),ASI1(cote_du_cube,dy)))
                           ,Cube_cDENORMALISE_OZ(ADD2(ASI1(origine_du_cube,z),ASI1(cote_du_cube,dz)))
                            )
                      );
                 Eblock
                 )
            );

     Test(EST_VRAI(c_est_le_premier_cube_de_la_profondeur_courante))
          Bblock
                                        /* Rien a faire a la date du 20140922165323 et d'ailleurs que faire pour bien verifier       */
                                        /* la divisibilite par 3 des trois cotes de base denormalises des cubes (qui ne sont pas     */
                                        /* necessairement egaux, puisque les trois dimensions en {X,Y,Z} ne sont pas forcement       */
                                        /* egales...) ? En attendant, le 20140923161553, j'introduis les editions suivantes...       */
          Test(IL_FAUT(editer_la_hierarchie_des_cubes))
                                        /* Test introduit le 20140923161553...                                                       */
               Bblock
               CAL3(Prme1("Cube(%d)=",NUMERO_D_ITERATION_COURANTE));
               CAL3(Prme2("%0*d",TRPU(NOMBRE_DE_CHIFFRES_DECIMAUX(dimX)),DIMENSION(XCubeMinimum,XCubeMaximum)));
               CALS(FPrme0("x"));
               CAL3(Prme2("%0*d",TRPU(NOMBRE_DE_CHIFFRES_DECIMAUX(dimY)),DIMENSION(YCubeMinimum,YCubeMaximum)));
               CALS(FPrme0("x"));
               CAL3(Prme2("%0*d",TRPU(NOMBRE_DE_CHIFFRES_DECIMAUX(dimZ)),DIMENSION(ZCubeMinimum,ZCubeMaximum)));
               CALS(FPrme0(" : "));
               CAL3(Prme1("%d",ASD1(rapport_d_homothetie,cx)));
               CALS(FPrme0("x"));
               CAL3(Prme1("%d",ASD1(rapport_d_homothetie,cy)));
               CALS(FPrme0("x"));
               CAL3(Prme1("%d",ASD1(rapport_d_homothetie,cz)));
               CALS(FPrme0("-Divisibilite="));
               CAL3(Prme1("%d",REST(DIMENSION(XCubeMinimum,XCubeMaximum),ASD1(rapport_d_homothetie,cx))));
               CALS(FPrme0("x"));
               CAL3(Prme1("%d",REST(DIMENSION(YCubeMinimum,YCubeMaximum),ASD1(rapport_d_homothetie,cy))));
               CALS(FPrme0("x"));
               CAL3(Prme1("%d",REST(DIMENSION(ZCubeMinimum,ZCubeMaximum),ASD1(rapport_d_homothetie,cz))));
               CALS(Fsauts_de_lignes(UN));
                                        /* On notera les 'TRPU(...)'s au cas ou une ou plusieurs dimensions du cube seraient un      */
                                        /* peu superieures a celles des axes 'OX', 'OY' et 'OZ' ('v $xiirf/.SIER.51.1.$U')...        */
                                        /*                                                                                           */
                                        /* Le 20140924111212, je note que ces editions peuvent faciliter le choix des                */
                                        /* dimensions des axes 'OX', 'OY' et 'OZ' dans le but d'obtenir des cubes qui aient          */
                                        /* tous des cotes multiples de 3. Ainsi, par exemple, soit :                                 */
                                        /*                                                                                           */
                                        /*                  nombre_d_iterations=4 (valeur par defaut) ----------------------------   */
                                        /*                                                                                        |  */
                                        /* Si l'on veut que le plus petit cube ait les cotes 9x9x9, il suffit de fixer :          |  */
                                        /*                                                   X Y Z                                |  */
                                        /*                                                   | | |                                |  */
                                        /*                  XYmaxNe   0 727 0 727            | | |                                |  */
                                        /*                  Zmin=0    Zmax=727               | | |                                |  */
                                        /*                                                   | | |                                |  */
                                        /* car, en effet :         ------------------------------                                 |  */
                                        /*                        |                                                               |  */
                                        /*                        |                                                               |  */
                                        /*                       \|/                                                              |  */
                                        /*                        .  4 <----------------------------------------------------------   */
                                        /*                  727 = 9x3 - 2                                                            */
                                        /*                          |                                                                */
                                        /*                          |                                                                */
                                        /*                           ---------> Rapport d'homothetie...                              */
                                        /*                                                                                           */
                                        /* On obtient alors les sorties suivantes :                                                  */
                                        /*                                                                                           */
                                        /*                  Cube(0)=0729x0729x0729 : 3-Divisibilite=0x0x0                            */
                                        /*                  Cube(1)=0243x0243x0243 : 3-Divisibilite=0x0x0                            */
                                        /*                  Cube(2)=0081x0081x0081 : 3-Divisibilite=0x0x0                            */
                                        /*                  Cube(3)=0027x0027x0027 : 3-Divisibilite=0x0x0                            */
                                        /*                  Cube(4)=0009x0009x0009 : 3-Divisibilite=0x0x0                            */
                                        /*                                                                                           */
                                        /* Le 20171215114928 je rappelle que '3' est la valeur par defaut de 'rapport_d_homothetie'. */
               Eblock
          ATes
               Bblock
               Eblock
          ETes
          Eblock
     ATes
          Bblock
          Eblock
     ETes

     Test(IZGT(profondeur_courante))
          Bblock
                                        /* Cas ou il faut iterer la subdivision :                                                    */
          DEFV(Logical,INIT(c_est_le_premier_cube_a_editer_1,VRAI));
          DEFV(Logical,INIT(c_est_le_premier_cube_a_editer_2,LUNDEF));
                                        /* Il va s'agir du premier cube de la subdivision courante...                                */

          DEFV(Int,INIT(nouvelle_profondeur,PRED(profondeur_courante)));
          DEFV(deltaF_3D,cote_du_cube_reduit);

          INITIALISATION_ACCROISSEMENT_3D(cote_du_cube_reduit
                                         ,DIVI(ASI1(cote_du_cube,dx),ASD1(rapport_d_homothetie,cx))
                                         ,DIVI(ASI1(cote_du_cube,dy),ASD1(rapport_d_homothetie,cy))
                                         ,DIVI(ASI1(cote_du_cube,dz),ASD1(rapport_d_homothetie,cz))
                                          );
                                        /* Par definition de l'eponge de Menger, on divise par 3 (par defaut)...                     */

          begin_hyper_albumQ(DoDe
                            ,OPTIMISER(profondeur_courante,PREMIERE_ITERATION_)
                            ,OPTIMISER(profondeur_courante,DERNIERE_ITERATION_)
                            ,I
                            ,DoIn,PREMIER_CUBE_REDUIT_Z,DERNIER_CUBE_REDUIT_Z,I
                            ,DoIn,PREMIER_CUBE_REDUIT_Y,DERNIER_CUBE_REDUIT_Y,I
                            ,DoIn,PREMIER_CUBE_REDUIT_X,DERNIER_CUBE_REDUIT_X,I
                             )
                                        /* Introduit le 20171215143439 sous cette forme...                                           */
                                        /*                                                                                           */
                                        /* ATTENTION : jusqu'au 20171231142417 il y avait par erreur ci-dessus :                     */
                                        /*                                                                                           */
                                        /*                  begin_hyper_albumQ(DoDe,PREMIERE_ITERATION_,DERNIERE_ITERATION_,I        */
                                        /*                                                                                           */
                                        /* ce qui avait pour effet d'allonger considerablement les calculs (l'arborescence etant     */
                                        /* reexploree en totalite a chaque niveau), mais en donnant evidemment des resultats         */
                                        /* corrects...                                                                               */
               Bblock
               DEFV(Logical,INIT(subdiviser_le_cube
                                ,SUBDIVISER_UN_CUBE(index_X_des_cubes_reduits
                                                   ,index_Y_des_cubes_reduits
                                                   ,index_Z_des_cubes_reduits
                                                   ,profondeur_courante
                                                    )
                                 )
                    );

               Test(EST_INDECIS(subdiviser_le_cube))
                    Bblock
                    FIN_DE_L_INDECISION(subdiviser_le_cube);
                                        /* Dans le cas d'une indecision, on fait un tirage aleatoire (introduit le 20180107183041).  */
                    Eblock
               ATes
                    Bblock
                    Eblock
               ETes

               Test(IL_FAUT(editer_les_choix_de_subdivision_suppression))
                                        /* Test introduit le 20240917115816 afin de le rendre l'edition des choix possible...        */
                    Bblock
                    INCR(compteur_de_trace_3,I);

                    Test(IL_FAUT(editer_les_choix_de_subdivision_suppression__version_simplifiee))
                                        /* Test introduit le 20240918170544...                                                       */
                         Bblock
                         EGAL(c_est_le_premier_cube_a_editer_2,c_est_le_premier_cube_a_editer_1);

                         Test(EST_VRAI(c_est_le_premier_cube_a_editer_1))
                              Bblock
                              EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_LF);

                              Test(IL_FAUT(editer_les_choix_de_subdivision_suppression__version_simplifiee_avec_parenthesage))
                                        /* Test introduit le 20240921103547...                                                       */
                                   Bblock
                                   TABULATION(NUMERO_D_ITERATION_COURANTE);
                                   EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_PG);
                                   CAL3(Prme2("[%0*d]"
                                             ,NOMBRE_DE_CARACTERES_DU_NUMERO_D_ITERATION_COURANTE
                                             ,NUMERO_D_ITERATION_COURANTE
                                              )
                                        );
                                        /* On notera le "%02d" qui permet de maintenir les tabulations quels que soient le numero    */
                                        /* d'iteration (inferieur a 100...).                                                         */
                                   EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_LF);
                                   TABULATION(NUMERO_D_ITERATION_COURANTE);
                                   Eblock
                              ATes
                                   Bblock
                                   Eblock
                              ETes

                              EGAL(c_est_le_premier_cube_a_editer_1,FAUX);
                              Eblock
                         ATes
                              Bblock
                              Eblock
                         ETes

                         Test(IL_FAUT(editer_les_choix_de_subdivision_suppression__version_simplifiee_avec_parenthesage))
                                        /* Test introduit le 20240921103547...                                                       */
                              Bblock
                              Test(IL_FAUT(tabuler_apres_une_C_PD))
                                   Bblock
                                   EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_LF);
                                   TABULATION(SUCC(NUMERO_D_ITERATION_COURANTE));

                                   EGAL(tabuler_apres_une_C_PD,FAUX);
                                   Eblock
                              ATes
                                   Bblock
                                   Eblock
                              ETes

                              TABULATION(COND(EST_VRAI(c_est_le_premier_cube_a_editer_2),UN,ZERO));
                              Eblock
                         ATes
                              Bblock
                              Eblock
                         ETes

                         EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(COND(EST_FAUX(subdiviser_le_cube)
                                                                                    ,K_0
                                                                                    ,COND(EST_VRAI(subdiviser_le_cube)
                                                                                         ,K_1
                                                                                         ,K_UNDEF
                                                                                          )
                                                                                     )
                                                                                );
                                        /* Le 20240918102326, pour information, je note les sorties suivantes (en rappelant les      */
                                        /* convention de codage 'FAUX=0' et 'VRAI=1') :                                              */
                                        /*                                                                                           */
                                        /* Eponge de Menger, iteration 1 :                                                           */
                                        /*                                                                                           */
                                        /*                  111 101 111         101 000 101         111 101 111                      */
                                        /*                                                                                           */
                                        /*                                                                                           */
                                        /* Eponge de Menger, iteration 2 :                                                           */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  0                                                                        */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  0                                                                        */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                  0                                                                        */
                                        /*                  0                                                                        */
                                        /*                  0                                                                        */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  0                                                                        */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  0                                                                        */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                  1         111 101 111        101 000 101        111 101 111              */
                                        /*                                                                                           */
                                        /*                                                                                           */
                                        /* Eponge de Menger, iteration 3 :                                                           */
                                        /*                                                                                           */
                                        /*                  $xrf/EpongeDeMenger.01.z      3                                          */
                                        /*                                                                                           */
                                        /*                                                                                           */
                                        /* Eponge de Menger, iteration 4 :                                                           */
                                        /*                                                                                           */
                                        /*                  $xrf/EpongeDeMenger.01.z      4                                          */
                                        /*                                                                                           */
                                        /*                                                                                           */
                                        /* etc...                                                                                    */
                                        /*                                                                                           */
                         Eblock
                    ATes
                         Bblock
                         CAL3(Prme2("Subdivision(%d)=%s\n",compteur_de_trace_3,ETAT_LOGIQUE(subdiviser_le_cube)));
                         Eblock
                    ETes
                    Eblock
               ATes
                    Bblock
                    Eblock
               ETes

               Test(IL_FAUT(subdiviser_le_cube))
                                        /* Test introduit le 20171215152010...                                                       */
                    Bblock
                    REDUCTION_D_UN_CUBE;
                                        /* Introduit le 20180116113103 sous cette forme...                                           */

                    CALS(GenerationDeLEpongeDeMenger(ADRESSE(origine_du_cube_reduit)
                                                    ,ADRESSE(cote_du_cube_reduit)
                                                    ,nouvelle_profondeur
                                                    ,album_d_imagesR
                                                    ,niveau_de_marquage_de_l_eponge
                                                    ,marquer_le_bord_X_de_l_eponge
                                                    ,marquer_le_bord_Y_de_l_eponge
                                                    ,marquer_le_bord_Z_de_l_eponge
                                                    ,niveau_de_marquage_du_bord_de_l_eponge
                                                    ,IFET(EST_VRAI(c_est_le_premier_cube_de_la_profondeur_courante)
                                                         ,I3ET(IFEQ(index_X_des_cubes_reduits,PREMIER_CUBE_REDUIT_X)
                                                              ,IFEQ(index_Y_des_cubes_reduits,PREMIER_CUBE_REDUIT_Y)
                                                              ,IFEQ(index_Z_des_cubes_reduits,PREMIER_CUBE_REDUIT_Z)
                                                               )
                                                          )
                                                    ,ADRESSE(prochain_rapport_d_homothetie_cumule)
                                                     )
                         );
                                        /* Les cubes reduits non centraux sont traites recursivement...                              */
                    Eblock
               ATes
                    Bblock
                    Test(IFEQ(subdiviser_le_cube,STOPPER_LA_SUBDIVISION_D_UN_CUBE))
                                        /* Test introduit le 20180116101706...                                                       */
                         Bblock
                         REDUCTION_D_UN_CUBE;
                         GENERATION_DUN_CUBE(ADRESSE(origine_du_cube_reduit)
                                            ,ADRESSE(cote_du_cube_reduit)
                                            ,ADRESSE(prochain_rapport_d_homothetie_cumule)
                                             );
                                        /* Generation d'un cube "non terminal" (introduit le 20180116101706...).                     */
                         Eblock
                    ATes
                         Bblock
                         Eblock
                    ETes
                    Eblock
               ETes
               Eblock
          end_hyper_albumQ(EDoD,EDoI,EDoI,EDoI)

          Test(IL_FAUT(editer_les_choix_de_subdivision_suppression))
                                        /* Test introduit le 20240918172007...                                                       */
               Bblock
               Test(IL_FAUT(editer_les_choix_de_subdivision_suppression__version_simplifiee))
                                        /* Test introduit le 20240918172007...                                                       */
                    Bblock
                    Test(IL_FAUT(editer_les_choix_de_subdivision_suppression__version_simplifiee_avec_parenthesage))
                                        /* Test introduit le 20240921103547...                                                       */
                         Bblock
                         EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_LF);
                         TABULATION(NUMERO_D_ITERATION_COURANTE);
                         EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_PD);

                         EGAL(tabuler_apres_une_C_PD,VRAI);
                         Eblock
                    ATes
                         Bblock
                         Eblock
                    ETes

                    EMETTRE_UN_CARACTERE_EN_SUPPRIMANT_LES_K_LF_REDONDANTS(K_LF);
                    Eblock
               ATes
                    Bblock
                    Eblock
               ETes
               Eblock
          ATes
               Bblock
               Eblock
          ETes
          Eblock
     ATes
          Bblock
                                        /* Cas ou la subdivision est terminee, il faut marquer les points des cubes de ce niveau...  */
          GENERATION_DUN_CUBE(origine_du_cube,cote_du_cube,rapport_d_homothetie_cumule);
                                        /* Generation du cube courant...                                                             */
          Eblock
     ETes

     RETU_ERROR;
     Eblock

EFonctionI

#undef    REDUCTION_D_UN_CUBE
#undef    GENERATION_DUN_CUBE

#undef    index_X_des_cubes_reduits
#undef    index_Y_des_cubes_reduits
#undef    index_Z_des_cubes_reduits

#undef    ZCubeMaximum
#undef    ZCubeMinimum
#undef    YCubeMaximum
#undef    YCubeMinimum
#undef    XCubeMaximum
#undef    XCubeMinimum



Copyright © Jean-François COLONNA, 2019-2024.
Copyright © CMAP (Centre de Mathématiques APpliquées) UMR CNRS 7641 / École polytechnique, Institut Polytechnique de Paris, 2019-2024.