Quelques exemples d'algorithmes valides en Galg
"prémachés" pour une traduction automatique en
C, C++, Java, Pascal, Rexx, Perl.

Tous les algorithmes commencent par un commentaire avec un nom d'auteur.
Un algorithme s'arrête là où vous voyez une fine barre horizontale.

Sous l'algorithme, le listage des fichiers à inclure.

     gilles.hunault@univ-angers.fr

1. cfe.alg   pour traduction en Pascal
2. bonjour.alg   pour traduction en C
3. triFus.alg   pour traduction en C++
4. macNaughton.alg   pour traduction en Java
5. tabmult.alg   pour traduction en Perl
6. maxocc.alg   pour traduction en Rexx

 

   #################################################
   #                                               #
   #   cfe.alg  ;  conversion francs en euro       #
   #            -- auteur : gh                     #
   #                                               #
   #   algorithme pour traduction en pascal        #
   #                                               #
   #################################################

   #: Uses linux ;

   #> valeur.pas
   #> format.pas

   #: var mntF,mntE : real ;
   #:     mntA : integer ;

   #: BEGIN

   # 1. Saisie ou conversion du paramètre

   si _nbParametres()=0
      alors écrire_  " Quel est le montant en Francs ? "
            lire     mntF
      sinon affecter mntF <-- valeur( _parametre( 1 ) )
   fin_si # nbParametres()=0


   # 2. Conversion et affichage

   affecter mntE <-- mntF / 6.55957
   écrire   mntF , " Francs font " , mntE , " euros."
   affecter mntA <--  _partieEntiere( 0.5 + mntE )
   écrire   " et si on arrondit : " , format(mntA,4 ), " euros."




   ###############################################
   #
   # ceci est le contenu du fichier valeurs.pas
   # pour l'algorithme cfe.alg (traduction pascal)
   #
   ###############################################

   function valeur( chaine : string) : real ;

    var rc     : integer ;
        nombre : real ;

   begin

    val(chaine,nombre,rc) ;
    if rc=0 then valeur := nombre
            else valeur := -999.99 ;

   end ; (* function valeur() *)

   ###############################################
   #
   # ceci est le contenu du fichier format.pas
   # pour l'algorithme cfe.alg (traduction pascal)
   #
   ###############################################

   function format( nombre : integer ; longueur : integer ) : string ;

     var chaine : string ;

   begin

     str(nombre:longueur,chaine) ;
     format := chaine ;

   end ;



 

   ################################################################
   #                                                              #
   #                                                              #
   #  auteur : (gH)                                               #
   #  bonjour.alg : un algorithme de bonjour conséquent.          #
   #                                                              #
   #  algorithme pour traduction en  C                            #
   #                                                              #
   ################################################################
   #                                                              #
   #                                                              #
   #                                                              #
   #      cet algorithme comporte un dialogue où on demande à     #
   #      l'utilisateur de donner son nom ;                       #
   #      il affiche ensuite la date et l'heure puis dit au       #
   #      revoir à la personne après avoir le nom en majuscules.  #
   #                                                              #
   #                                                              #
   #                                                              #
   ################################################################

   #> maju.c
   #> date.c
   #> heure.c

   #: int main() {

   #: chaine id ;

      # la demande = une question + une réponse

      écrire   " Bonjour. Quel est ton nom ? "
      lire     id


      # ce qu'on fait répondre par la machine

      écrire   " Le ", date(), " à ", heure(), " au revoir " , maju(id)



   ###############################################
   #
   # ceci est le contenu du fichier maju.c
   # pour l'algorithme bonjour.alg (traduction C)
   #
   ###############################################

      char*  maju(chaine f_iden) {
       int idc = 0 ;
       while (idc<strlen(f_iden)) {
          f_iden[idc] = toupper(f_iden[idc]) ;
          idc++ ;
       } ; /* fin de pour # idc */
       return( f_iden ) ;
      } /* fin de maju */




   ###############################################
   #
   # ceci est le contenu du fichier date.c
   # pour l'algorithme bonjour.alg (traduction C)
   #
   ###############################################


      char* date(void) {
           time_t now   = time(NULL);
           struct tm *t = localtime(&now);
           char laDate[100] ;
           strftime(laDate, 100, "%d/%m/%Y", t) ;
           return(laDate) ;
      } /* fin de date */




   ###############################################
   #
   # ceci est le contenu du fichier heure.c
   # pour l'algorithme bonjour.alg (traduction C)
   #
   ###############################################

      char* heure(void) {
           time_t now   = time(NULL);
           struct tm *t = localtime(&now);
           char lHeure[100];
           strftime (lHeure, 100, "%H:%M.%S", t);
           return(lHeure) ;
      } /* fin de heure */



 

   ###############################################
   #
   # triFus.alg : trifusion de 2 fichiers déjà triés
   #              auteur -- gH
   #
   # algorithme pour traduction en C++
   #
   ###############################################

   #> triFusCpp.inc

   #: int main() {

   # nommage des variables pour noms de fichier

   appeler _affecterChaine( nomFic1 , "triFus.f1" )
   appeler _affecterChaine( nomFic2 , "triFus.f2" )
   appeler _affecterChaine( nomFic3 , "triFus.f3" )

   # initialisation des nombres de lignes lues et écrites

   affecter nbl1 <-- 0
   affecter nbl2 <-- 0
   affecter nbl3 <-- 0

   # ouverture des 3 fichiers

   ouvrir nomFic1 en_lecture  comme fic1
   ouvrir nomFic2 en_lecture  comme fic2
   ouvrir nomFic3 en_ecriture comme fic3

   # lecture du premier enregistrement sur fic1

   si non fin_de_fichier(fic1)
      alors # lecture possible
            lire ligne1 sur fic1
            affecter nbl1 <-- nbl1 + 1
   fin_si # lecture du fic1

   # lecture du premier enregistrement sur fic2

   si non fin_de_fichier(fic2)
      alors # lecture possible
            lire ligne2 sur fic2
            affecter nbl2 <-- nbl2 + 1
   fin_si # lecture du fic2

   # boucle de tri-fusion

   tant_que (non fin_de_fichier(fic1)) et (non fin_de_fichier(fic2))

     appeler _affecterChaine( mot1, mot(ligne1,2))
     appeler _affecterChaine( mot2, mot(ligne2,2))

     si strncmp(mot1,mot2,20)<0
        alors  # écriture de fic1 vers fic3
               si _longueur(ligne1)>0
                  alors
                        écrire " (fic1) " , ligne1 sur fic3
                        affecter nbl3 <-- nbl3 + 1
               fin_si # sur longueur
               si non fin_de_fichier(fic1)
                  alors # on a une ligne de plus
                        lire ligne1 sur fic1
               fin_si # lecture
               si _longueur(ligne1)>0
                  alors
                        affecter nbl1 <-- nbl1 + 1
                  sinon
                        appeler _affecterChaine( ligne1 , "" )
               fin_si # lecture du fic1
        sinon  # écriture de fic2 vers fic3
               si _longueur(ligne2)>0
                  alors
                  écrire " (fic2) " , ligne2 sur fic3
                  affecter nbl3 <-- nbl3 + 1
               fin_si # sur longueur
               si non fin_de_fichier(fic2)
                  alors # on a une ligne de plus
                        lire ligne2 sur fic2
               fin_si #
               si _longueur(ligne1)>0
                     alors
                        affecter nbl2 <-- nbl2 + 1
                  sinon
                        appeler _affecterChaine( ligne2 , "" )
               fin_si # lecture du fic2
     fin_si # comparaison ligne 1 et ligne 2
   fin_tant_que # lecture sur les deux fichiers

   # un des deux lignes n'a pas été recopiée, donc :

   si non fin_de_fichier(fic1) et _longueur(ligne1)>0
      alors  # écriture de fic1 vers fic3
                        écrire " (fic1) " , ligne1 sur fic3
                        affecter nbl3 <-- nbl3 + 1
   fin_si # on compare en fin de fichier

   si non fin_de_fichier(fic2) et _longueur(ligne2)>0
      alors  # écriture de fic2 vers fic3
                        écrire " (fic2) " , ligne2 sur fic3
                        affecter nbl3 <-- nbl3 + 1
   fin_si # on compare en fin de fichier

   # s'il reste des lignes dans f1, on recopie f1

   tant_que non fin_de_fichier(fic1)
               lire ligne1 sur fic1
               si _longueur(ligne1)>0
                  alors
                    affecter nbl1 <-- nbl1 + 1
                    écrire " [fic1] " , ligne1 sur fic3
                    affecter nbl3 <-- nbl3 + 1
               fin_si # sur longueur
   fin_tant_que # lecture sur f1

   # s'il reste des lignes dans f2, on recopie f2

   tant_que non fin_de_fichier(fic2)
               lire ligne2 sur fic2
               si _longueur(ligne2)>0
                  alors
                    affecter nbl2 <-- nbl2 + 1
                    écrire " [fic2] " , ligne2 sur fic3
                    affecter nbl3 <-- nbl3 + 1
               fin_si # sur longueur
   fin_tant_que # lecture sur f1

   # fermeture des fichiers

   fermer fic1
   fermer fic2
   fermer fic3

   # affichage du nombre de lignes lues et écrites :

   écrire "    "  , nbl1 , " lignes lues    sur "  ,  nomFic1
   écrire "    " , nbl2 , " lignes lues    sur "  ,  nomFic2
   écrire "    " , nbl3 , " lignes écrites sur "  ,  nomFic3

   quitter 0



   ###############################################
   #
   # ceci est le contenu du fichier triFusCpp.inc
   # pour l'algorithme triFus.alg (traduction C++)
   #
   ###############################################


   #include <iostream>
   #include <string>
   #include <fstream>

   typedef char chaine[250] ;

   chaine nomFic1,
          nomFic2,
          nomFic3,
          ligne1,
          ligne2,
          mot1,
          mot2
          ;

   int nbl1,
       nbl2,
       nbl3,
       rc
       ;

   // ###############################################################

   char* sousChaine(chaine ancienne, int debut, int longueur) {
   chaine nouvelle ;
   int ic ;
     strcpy(nouvelle,ancienne) ;
     if (debut<0) { debut = 0 ; } ;
     if (longueur>strlen(ancienne)) { longueur = strlen(ancienne) ; } ;
     nouvelle[longueur] = 0 ;
     for (ic=0;ic<strlen(nouvelle);ic++) {
       nouvelle[ic] = ancienne[debut+ic-1] ;
     } ; // fin pour
     return(nouvelle) ;
   } /* fin de sousChaine */

   // ###############################################################

   char* mot(chaine ancienne, int numero) {
   chaine PHR ;
   chaine lemot ;
   chaine motr ;
   chaine sep   ;
   int    nb,i,L,debut_mot,fin_mot,lng_mot ;
     strcpy(lemot,ancienne) ;
     strcpy(sep," ") ;
     strcpy(PHR,ancienne) ;
     strcat(PHR,sep) ;
     L    = strlen(PHR) ;
     i    = 0 ;
     nb   = 0 ;
     while ( (i < L) && (nb < (numero-1)) ) {
        if (PHR[i]==sep[0]) {
           nb = nb + 1 ;
           while ((i < L ) && (PHR[i]==sep[0])) { i = i + 1 ; } ;
        } ; /*  finsi PHR[i]=sep */
        i = i + 1 ;
     } ; /* fin while (i < L) and ... */
     /* le début est donc trouvé ; cherchons la fin */
     debut_mot = i ;
     while (i<L ) {
        if (PHR[i] != sep[0]) {  i = i + 1 ; }
                         else { fin_mot  = i ; i = L + 1 ; }
     } ; /* fin tant que i< L */
     lng_mot = fin_mot-debut_mot+1 ;
     strcpy(motr,ancienne) ;
     if (fin_mot > debut_mot) { strcpy(motr,sousChaine(PHR,debut_mot,lng_mot)) ; } ;
     if (fin_mot > debut_mot) { strcpy(lemot,motr) ; }
                         else { strcpy(lemot,"") ; } ;
     return(lemot) ;

   } /* fin de mot */


   // ###############################################################



 

   ##############################################################
   #                                                            #
   #   macNaughton.alg : affectation de taches selon            #
   #                     la méthode de mac Naughton             #
   #   auteur (gH)                                              #
   #                                                            #
   #   algorithme pour traduction java                          #
   #                                                            #
   ##############################################################
   #                                                            #
   #   références :  Cormen, Leiserson et Rivest                #
   #                 Introduction to algorithms, MIT Press      #
   #                                                            #
   ##############################################################
   #                                                            #
   #                                                            #
   # avec nbMachines qui doivent effectuer nbTaches et sachant  #
   # que la tache numéro i dure dureeTache[ i] comment répartir #
   # les taches ? la durée est en heure et les taches sont      #
   # morcelables heure par heure.                               #
   #                                                            #
   #                                                            #
   ##############################################################
   #
   #:     import java.io.* ;

   #> maxEntier.java
   #> partieEntiere.java
   #> format.java
   #> copies.java

   #: public static void main(String args[]) {
   #: // début de la méthode main()


   #:     int     nbMachines    = -1  ;
   #:     int     nbTaches      = -1  ;
   #:     int[]   dureeTache          ;
   #:     int     somDuree      =  0  ;
   #:     int     dureeCour     =  0  ;
   #:     int     dureeMax      =  0  ;
   #:     int     dureeMin      =  0  ;
   #:     int[]   nbTache             ;
   #:     int[][] machineTacheNumero  ;
   #:     int[][] machineTacheDuree   ;
   #:     int     tempsPris     =  0  ;
   #:     int     machineCour   =  0  ;
   #:     int     tacheCour     =  0  ;
   #:     int     resteTemps    =  0  ;
   #:     int     nbTacheCour   =  0  ;


   # 0.  Affectations arbitraires pour tester un
   #     exemple élémentaire
   #

   affecter nbMachines  <-- 3
   affecter nbTaches    <-- 6

   #:     dureeTache         = new int[ nbTaches + 1 ] ;
   #:     nbTache            = new int[ nbTaches + 1 ] ;
   #:     machineTacheNumero = new int[ nbTaches + 1 ][ nbMachines + 1 ] ;
   #:     machineTacheDuree  = new int[ nbTaches + 1 ][ nbMachines + 1 ] ;

   affecter dureeTache[ 1 ]  <--   5
   affecter dureeTache[ 2 ]  <--   3
   affecter dureeTache[ 3 ]  <--   4
   affecter dureeTache[ 4 ]  <--   5
   affecter dureeTache[ 5 ]  <--   2
   affecter dureeTache[ 6 ]  <--   5


   # 1. Calcul de la durée minimale

   affecter somDuree <-- 0
   pour indTache de1a nbTaches
        affecter dureeCour <-- dureeTache[ indTache ]
        affecter somDuree  <-- somDuree + dureeCour
        si indTache=1
           alors affecter dureeMax <-- dureeCour
           sinon
                 si dureeCour > dureeMax
                    alors affecter dureeMax <-- dureeCour
                 fin_si # dureeCour > dureeMAx
        fin_si # indTache=1
   fin_pour # indTache de1a nbTaches
   affecter dureeMin <-- maxEntier( partieEntiere( somDuree / nbMachines) , dureeMax)


   # 2. Affectation des taches aux machines


   # 2.1 Initialisation du tableau de répartititon

   pour indTache de1a nbTaches
        affecter nbTache[ indTache ] <-- 0
        pour indMachine de1a nbMachines
              affecter machineTacheNumero[ indTache , indMachine ] <-- 0
              affecter machineTacheDuree[  indTache , indMachine ]  <-- (-1)
        fin_pour # indMachine de1a nbMachines
   fin_pour # indTache de1a nbTaches

   # 2.2 Boucle d'affectation

   affecter tempsPris   <-- 0
   affecter machineCour <-- 1

   pour indTache de1a nbTaches
       affecter dureeCour <-- dureeTache[ indTache ]

       si tempsPris+dureeCour <=  dureeMin

          alors # on peut affecter toute la tache a la machine courante

                affecter tacheCour                                      <--  nbTache[ machineCour ] + 1
                affecter nbTache[ machineCour ]                         <--  tacheCour
                affecter machineTacheNumero[ machineCour , tacheCour ]  <--  indTache
                affecter machineTacheDuree[  machineCour , tacheCour ]  <--  dureeCour
                affecter tempsPris                                      <--  tempsPris + dureeCour
                si tempsPris = dureeMin
                   alors affecter machineCour <-- machineCour + 1
                         affecter tempsPris   <-- 0
                fin_si # tempsPris = dureeMin

          sinon # on n'a le droit d'affecter qu'une partie a la machine courante

                affecter tacheCour                                     <--  nbTache[ machineCour ] + 1
                affecter nbTache[ machineCour ]                        <--  tacheCour
                affecter machineTacheNumero[ machineCour , tacheCour ] <--  indTache
                affecter resteTemps                                    <--  dureeMin - tempsPris
                affecter machineTacheDuree[  machineCour , tacheCour ] <--  resteTemps

                # et on affecte ce qui reste a la machine suivante

                affecter machineCour                                   <--  machineCour + 1
                affecter tacheCour                                     <--  nbTache[ machineCour ] + 1
                affecter nbTache[ machineCour ]                        <--  tacheCour
                affecter machineTacheNumero[ machineCour , tacheCour ] <--  indTache
                affecter machineTacheDuree[  machineCour , tacheCour ] <--  dureeCour - resteTemps
                affecter tempsPris                                     <--  dureeCour - resteTemps

       fin_si # tempsPris+dureeTache[ tacheCour ] <=  dureeMin

   fin_pour # indTache de1a nbTaches


   # 3. Affichage des données et des répartitions

   écrire " Il y avait " , nbMachines , " machines et " , nbTaches ," taches à répartir."
   écrire " Voici la durée des taches : "
   écrire "   Tache    Durée (en heures)"
   pour indTache de1a nbTaches
        écrire  format(indTache,8) , format( dureeTache[ indTache ],8 )
   fin_pour # indTache de1a nbTaches


   écrire ""
   écrire " La durée minimale calculée est " , dureeMin ," heures."
   écrire ""


   pour indMachine de1a nbMachines
       écrire "  -- machine " , indMachine , " : "
       affecter nbTacheCour <-- nbTache[ indMachine ]
       si nbTacheCour > 0
          alors
                pour indTache de1à nbTacheCour
                     affecter dureeCour <-- machineTacheDuree[  indMachine , indTache ]
                     affecter tacheCour <-- machineTacheNumero[ indMachine , indTache ]
                     écrire   copies("  ",6) , " tache " , tacheCour , " durée " , dureeCour
                fin_pour # indTache de1à nbTacheCour
       fin_si # numMachine > 0
   fin_pour # indTache de1a nbTaches




   ###############################################
   #
   # ceci est le contenu du fichier maxEntier.java
   # pour l'algorithme macNaughton.alg (traduction java)
   #
   ###############################################

   public static int maxEntier( int un, int deux) {
     if (un>deux) { return un ; } else { return deux ; } ;
   } // fin de maxEntier

   


   ###############################################
   #
   # ceci est le contenu du fichier partieEntiere.java
   # pour l'algorithme macNaughton.alg (traduction java)
   #
   ###############################################

   static int partieEntiere(double nb_r) {
     return (int) nb_r ;
   } // fin de partieEntiere

   


   ###############################################
   #
   # ceci est le contenu du fichier format.java
   # pour l'algorithme macNaughton.alg (traduction java)
   #
   ###############################################

   public static String format(int nombre, int longueur) {

     String chen = Integer.toString(nombre) ;
     while (chen.length() < longueur) { chen = " " + chen ; } ;
     return chen ;

   } // fin de format

   


   ###############################################
   #
   # ceci est le contenu du fichier copies.java
   # pour l'algorithme macNaughton.alg (traduction java)
   #
   ###############################################


   public static String copies(String motif, int repet) {

     String chen = "" ;
     for (int ifois =1 ; ifois <= repet ; ifois++) {
         chen = motif + chen ;
     } ; // fin de pour

     return chen ;

   } // fin de copies



 

   #####################################################
   #                                                   #
   # tabmult.alg -- un exemple simple d'algorithme :   #
   #                la table de multiplication         #
   #                                                   #
   #  auteur : gh                                      #
   #                                                   #
   #  algorithme pour traduction en perl               #
   #                                                   #
   #####################################################
   #                                                   #
   #  on demande à l'utilisateur un nombre entier et   #
   #  on le relance tant que le nombre n'est pas       #
   #  entier.                                          #
   #                                                   #
   #  lorsque le nombre est entier, on afiche sa       #
   #  table avec cadrage des unités sous les unités,   #
   #  des dizaines sous les dizaines etc.              #
   #                                                   #
   #####################################################


   # demande initiale

   écrire  " Donner un entier "
   lire nbChoisi


   # relance éventuelle

   tant_que (non entier(nbChoisi))
       écrire " nombre incorrect. Redonner un nombre ENTIER "
       lire nbChoisi
   fin_tant_que # nombre invalide


   # boucle d'affichage

   écrire " Table de " , nbChoisi
   pour indb de1a 10
       affecter produit <-- nbChoisi*indb
       affecter find <-- format(indb,2)
       affecter fpro <-- format(produit,5)
       écrire find , " fois " , nbChoisi , " = " , fpro
   fin_pour # indb de1a 10

   #> entier.pl
   #> format.pl



   ###############################################
   #
   # ceci est le contenu du fichier entier.pl
   # pour l'algorithme tabmult.alg (traduction perl)
   #
   ###############################################

   sub  entier  {

     # renvoie "vrai" si le paramètre est un entier éventuellement signé

     my $parm_entier = $_[0] ;
     return $parm_entier =~ /^[+-]?\d+$/ ;

   } ; # fin sub entier




   ###############################################
   #
   # ceci est le contenu du fichier format.pl
   # pour l'algorithme tabmult.alg (traduction perl)
   #
   ###############################################

   sub  format  {
     return( sprintf("%$_[1]d",$_[0]) ) ;
   } ; # fin sub format



 

   ########################################################
   #                                                      #
   #  maxocc.alg : comptage des occurences du maximum     #
   #               d'un tableau en une seule boucle       #
   #                                                      #
   #  -- auteur  : gh                                     #
   #                                                      #
   # algorithme pour traduction en rexx                   #
   #                                                      #
   ########################################################


   #< maxocc_dr.rex

   # initialisation du tableau avec 15 éléments
   # entiers entre 10 et 100


   affecter nbElt <-- 15
   appeler init_Tab( monT , nbElt , 10 , 100 )

   # détermination du max et comptage du nb d'occurences
   # du max en une seule boucle

   # initialisation de la valeur du maximum (valMax)
   # et de son nombre d'occurences (nbMax)

   affecter valMax  <-- monT[ nbElt ]
   affecter nbMax   <-- 1

   # on parcourt alors le tableau
   # sans utiliser le dernier élément déja comptabilisé

   pour indb de1a nbElt-1
        affecter eltCourant <-- monT[ indb ]
        si eltCourant > valMax
           alors # nouveau maximum local
                 affecter valMax  <-- eltCourant
                 affecter nbMax   <-- 1
           sinon
                 si eltCourant = valMax
                    alors # une fois de plus le maximum
                          affecter nbMax <-- nbMax + 1
                 fin_si # nouvelle occurence du maximum
        fin_si # nouveau maximum
   fin_pour # indb de1a 10

   # affichage de fin

   écrire " Le maximum dans le tableau est : " , valMax
   écrire " et il apparait " , nbMax , " fois."
   écrire " Pour vérification, voici les éléments du tableau : "

   appeler affiche_Tab( monT , 1 , nbElt , 4)
   appeler quitter()

   #< maxocc_fr.rex



   ###############################################
   #
   # ceci est le contenu du fichier maxocc_dr.rex
   # pour l'algorithme maxocc.alg (traduction rexx)
   #
   ###############################################

     nomTab = "monT."




   ###############################################
   #
   # ceci est le contenu du fichier maxocc_fr.rex
   # pour l'algorithme maxocct.alg (traduction rexx)
   #
   ###############################################

   /* sous-programmes */

   init_Tab: procedure expose (nomTab)

     parse arg sonNom  nbe  vmin vmax
     say "   ===>  Vous demandez " nbe " éléments entre " vmin " et " vmax  " pour le tableau : " sonNom
     do i = 1 to nbe
        elt = random(vmin,vmax)
        lins =  nomTab||i||" = " elt
        interpret lins
     end /* fin pour i */

   return ""

   affiche_Tab: procedure expose (nomTab)

     parse arg sonNom  indMin  indMax largeurF
     say "   ===>  Affichage des éléments " indMin " à " indMax " en largeur " largeurF " du tableau " sonNom
     do i = indMin to indmax
        elt = value(nomTab||i)
        say "    Elément " format(i,3) " : " format(elt,largeurF)
     end /* fin pour i */

   return ""



    retour page principale de galg  Retour à la page principale de Galg