[TUTORIEL] Traduction textuelle d’un montant numérique
par
, 01/04/2021 à 10h45 (377 Affichages)
Travaux Pratiques d'algorithmique (Force 3/7)
Exercice corrigé et proposition de refactoring
Public :
- étudiants
- débutants
- et pourquoi pas, enseignants
Contenu :
- la boucle DO
- la structure itérative LCP
- la structure linéaire CORIG
- l’orthographe des nombres en lettres
TUTORIEL
Traduction textuelle d’un montant numérique
§ 1. Traduction textuelle d’un montant numérique■ ■ ■ SOMMAIRE DU BILLET ■ ■ ■
- Traduction textuelle d’un montant numérique
- Compréhension de la problématique
- Simulation
- Règles orthographiques des nombres en lettres
- Million et milliard
- Mille ou Milles ?
- Cent ou Cents ?
- Vingt ou Vingts ?
- Les nombres de 20 à 99
- L'Algorigramme
- L'Algorithme
- Exercice pratique de refactoring
- ANNEXES
- Divagations méthodologiques
- De l'instruction PRINT FILE
- Discussions similaires
Cet exercice a fait l’objet d’une discussion ouverte le 25/12/2021 sur le Forum Algorithmes et structures de données :
Dans une carrière de développeur, il n’est pas évident d’abstraire de ses développements des sujets d’algorithmique originaux et exploitables pédagogiquement.
La traduction textuelle d’un montant numérique n’est pas une fonctionnalité d’une grande complexité algorithmique mais demande quand même un peu de réflexion assujettie à un minimum d’orthographe. C’est surtout un prétexte pour ressusciter deux méthodologies des années 60-70, LCP et CORIG.
La Solution :
Anecdote :
Chacun de nous à un jour rongé son frein à la caisse d’un magasin ou d’un supermarché, le temps que le client devant soi remplisse consciencieusement son chèque.
Imaginez le pensum imposé par la TG (Trésorerie Générale) à un service administratif de formation continue qui doit libeller chaque montant d’un Certificat Administratif ou d’un État de Liquidation.
Un Certificat Administratif est une pièce comptable transmise à la TG, équivalente à une facture, pour s’acquitter de l’achat de matériel pédagogique.
Un État de Liquidation est une autre pièce comptable transmise à la TG, équivalente à un bulletin de paie, pour rémunérer les prestations des formateurs.
Jusqu’à présent, un État de Liquidation "hebdomadaire" globalisant les sommes de toutes les prestations à liquider est produit manuellement. Cet État de Liquidation "collectif" se présente sous forme d’un tableau avec une ligne par prestation formateur à indemniser et une ligne de totalisations avec le montant total brut, les sommes à déduire (la solidarité, la retenue RDS, la retenue CSG appliquée sur le montant total brut) et le montant total net qu’il reste ensuite à libeller.
Le procédé minimise certes l’écriture manuelle ou dactylographique des sommes en lettres, sauf que les déductions sur la ligne des totalisations se réfèrent au montant total brut pour ne pas perturber les contrôleurs de la TG. Ce faisant, elles ne peuvent jamais correspondre à la somme des déductions appliquées sur chaque montant d’une ligne du tableau. Ce petit détail a pour conséquence de devoir produire en fin d’année budgétaire, un document spécifique avec des écritures comptables d’ajustement pour justifier l’incohérence du bilan annuel auprès de la TG.
Assainir la procédure de liquidation et libérer les gestionnaires de leurs contraintes implique la possibilité d’imprimer des États de Liquidation "individuels" avec la traduction textuelle des montants numériques. L’occasionnel Certificat Administratif, profitera opportunément de la fonctionnalité déjà programmée.
« Pour la petite histoire, réaliser cette fonctionnalité et l’optimiser pour ne pas vexer la susceptibilité du compilateur - "Programme trop complexe" disait-il - n’a pas été le plus compliqué. L’État de Liquidation programmé d’abord classiquement, avec des caractères semi-graphiques pour tracer le tableau, a néanmoins fini par pousser le pauvre compilateur à la faute. Correct à la compilation, il suffisait d’une instruction de trop, même inopérante, pour que le programme donne des résultats complètement fantaisistes. Trop conséquent et sans doute saturé d’instructions conditionnelles, la situation paraissait désespérée jusqu’à ce qu’un de mes neurones se souvienne d’une petite instruction insolite, toute simple, à laquelle je ne m’étais jamais intéressé : PRINT FILE chemin_du_formulaire. Vraisemblablement crée pour moi uniquement, cette instruction va simplifier miraculeusement le programme et me permettre désormais de concevoir autrement mes éditions. »
Cette digression mise à part, ce petit exercice d’algorithmique et de français vous inspire-t-il ?
§ 2. Compréhension de la problématique
§ 2.1. Simulation
Compte-tenu de l’objectif des programmes, on peut convenir sans risque que la fonctionnalité ne doit traduire textuellement que des montants inférieurs au million d’Euros. Le montant chiffré maximum à traduire est donc : 999.999,99 Euros.
Soit :
NEUF-CENT-QUATRE-VINGT-DIX-NEUF-MILLE-NEUF-CENT-QUATRE-VINGT-DIX-NEUF EUROS QUATRE-VINGT-DIX-NEUF CENTIMES.
On observe alors que pour les Euros, la traduction textuelle est la même, appliquée aux milliers d’Euros et aux Euros compris entre 1 et 999 ; il s’agit de traduire les centaines, les dizaines et les unités... s’il y en a bien sûr.
Pour les centimes, la traduction textuelle ne concerne que les dizaines et les unités... s’il y en a.
La fonctionnalité ainsi exprimée, l’algorigramme est pratiquement fait ! L’observation concernant les Euros suggère une boucle exécutée deux fois plutôt qu’un traitement linéaire dupliqué.
§ 2.2. Règles orthographiques des nombres en lettres
Une petite révision ne fait pas de mal. Vous pouvez tester votre orthographe en cliquant sur les liens d’où sont extraits les questionnaires dont je vous propose les corrigés ci-dessous.
- Million et milliard
Million et milliard sont des noms (et non des adjectifs numéraux). Ils s'accordent donc en nombre et, placés après vingt ou cent, ils n'empêchent pas l'accord de ceux-ci : quatre-vingts millions d'habitants ; cinq cents milliards de kilomètres.
- Mille ou Milles ?
"MILLE" est un adjectif numéral toujours invariable. Historiquement, mille était le pluriel de mil, ce qui explique pourquoi mille est invariable.
Placé après CENT, il empêche l'accord de celui-ci ; on écrit TROIS-CENT MILLE.
Exemples :
- J'ai gagné vingt mille euros.
- J'aimerais partir à dix mille kilomètres d'ici.
- Je vais répéter la même chose mille fois. Mille millions de mille sabords ! (Capitaine Haddock)
- CENT ou CENTS ?
"CENT" est un numéral qui prend la marque du pluriel -S seulement s'il est multiplié (par un nombre) sans être suivi d'un déterminant numéral (autrement dit s'il termine le numéral). Nous devons par exemple écrire : TROIS CENTS, mais TROIS CENT CINQUANTE.
Dans tous les autres cas, "CENT" reste invariable : CINQ MILLE CENT, page TROIS CENT.
Exemples :
- C'est un très gros livre. Il y a environ cinq cents pages.
- Ce poulet doit bien peser quatre cent cinquante grammes.
- Le lot gagnant porte le numéro trois cent.
- Il me reste les cent dernières pages à lire.
- Ce poulet doit bien peser dans les quatre cents grammes.
- Cette maison fut construite en mille neuf cent.
- Le budget de la ville s'élève à huit cents millions d'euro(s)
- Ce poulet pèse probablement plus de cinq cents grammes.
- Dès les premiers jours, ce livre s'est vendu à près de trois cent mille exemplaires !
- La réponse à votre question se trouve à la page deux cent.
- VINGT ou VINGTS ?
"VINGT" ne prend normalement pas la marque du pluriel, sauf dans "QUATRE-VINGTS" s'il n'est pas un ordinal (un ordinal est par exemple un numéro de page, un millésime, une année, un numéro d'ordre, etc.) et s'il n'est pas suivi d'un autre cardinal numéral (QUATRE-VINGTS, TROIS CENT QUATRE-VINGTS, mais QUATRE-VINGT-SIX, DEUX CENT QUATRE-VINGT-DEUX…).
Exemples :
- Il me reste encore deux cent vingt pages à lire pour achever la lecture de ce livre.
Invariable, règle générale.- Ma voisine va organiser une fête pour ses vingt ans.
Invariable, règle générale.- Ma grand-mère a au moins quatre-vingts ans.
Pluriel (exception) car 80 n'est suivi d'aucun cardinal numéral et n'est pas un ordinal.- Mon grand-père va fêter ses quatre-vingt-dix ans.
Invariable, car 80 est suivi d'un cardinal numéral.- Ce poulet pèse probablement plus de six cent quatre-vingts grammes.
Pluriel (exception) car 80 n'est suivi d'aucun autre cardinal numéral et n'est pas un ordinal.- Ce film a rapporté près de quatre-vingts millions d'euros.
Pluriel (exception) car 80 n'est suivi d'aucun cardinal numéral (million n'est pas un cardinal numéral : c'est un nom).- Cette pétition a obtenu plus de quatre-vingt mille signatures.
Invariable, car 80 est suivi d'un cardinal numéral (mille est un cardinal numéral, contrairement à million qui est un nom).- Nous devons faire l'exercice de la page quatre-vingt pour demain.
Invariable, car 80 est ici un ordinal (un numéro de page).- Nous l'attendons depuis vingt-quatre heures.
Invariable, règle générale.- Cette chanson date des années quatre-vingt.
Invariable, car 80 est ici un ordinal.- Les nombres de 20 à 99
Les nombres composés jusqu'à cent prennent un trait d'union sauf lorsqu'il y a "et".
Mais depuis la réforme de 1990, on peut mettre des traits d'union partout.
Le rapport de 1990 sur les rectifications orthographiques propose de nouvelles règles sur les traits d'union. On écrit les numéraux composés avec des traits d'union entre chaque élément (ex. : vingt-et-un-mille-trois-cent-deux). Mais milliard (tout comme millier et million) étant un substantif, il n'est pas concerné par cette rectification et ne prendra donc de trait d'union ni avant, ni après (ex. : cinq-cents milliards six-cent-quatre-vingt-dix-sept-mille).
20 -21-22-23-24
-25-26-27-28-29VINGT
vingt et un
vingt-deux
vingt-trois
vingt-quatre
vingt-cinq
vingt-six
vingt-sept
vingt-huit
vingt-neuf60 -61-62-63-64
-65-66-67-68-69SOIXANTE
soixante et un
soixante-deux
soixante-trois
soixante-quatre
soixante-cinq
soixante-six
soixante-sept
soixante-huit
soixante-neuf30 -31-32-33-34
-35-36-37-38-39TRENTE
trente et un
trente-deux
trente-trois
trente-quatre
trente-cinq
trente-six
trente-sept
trente-huit
trente-neuf70 -71-72-73-74
-75-76-77-78-79SOIXANTE-DIX
soixante et onze
soixante-douze
soixante-treize
soixante-quatorze
soixante-quinze
soixante-seize
soixante-dix-sept
soixante-dix-huit
soixante-dix-neuf40 -41-42-43-44
-45-46-47-48-49QUARANTE
quarante et un
quarante-deux
quarante-trois
quarante-quatre
quarante-cinq
quarante-six
quarante-sept
quarante-huit
quarante-neuf80 -81-82-83-84
-85-86-87-88-89QUATRE-VINGTS
quatre-vingt-un
quatre-vingt-deux
quatre-vingt-trois
quatre-vingt-quatre
quatre-vingt-cinq
quatre-vingt-six
quatre-vingt-sept
quatre-vingt-huit
quatre-vingt-neuf50 -51-52-53-54
-55-56-57-58-59CINQUANTE
cinquante et un
cinquante-deux
cinquante-trois
cinquante-quatre
cinquante-cinq
cinquante-six
cinquante-sept
cinquante-huit
cinquante-neuf90 -91-92-93-94
-95-96-97-98-99QUATRE-VINGT-DIX
quatre-vingt-onze
quatre-vingt-douze
quatre-vingt-treize
quatre-vingt-quatorze
quatre-vingt-quinze
quatre-vingt-seize
quatre-vingt-dix-sept
quatre-vingt-dix-huit
quatre-vingt-dix-neuf
§ 3. L'Algorigramme
L’algorigramme de cette fonctionnalité a été réalisé le 18/11/2021 pour argumenter cette discussion. Il associe les deux méthodes de programmation LCP et CORIG. On distingue clairement la structure itérative LCP, de même que les structures linéaires et conditionnelles de CORIG.
L’algorigramme reste au niveau logique des traitements :
┌─────────────────────────────────┐ D-PROG │ v_total = "" │ │ j = 1 │ └────────────────┬────────────────┘ │◄───────────────────────────┐ ┌────────────────────────────┼──────────────────────┐ │ T-EUROS │ ┌────────────────┴────────────────┐ │ │ │ │ J=1 Calcul des milliers d’Euros │ │ │ │ │ J=2 Calcul des Euros de 1 à 999 │ │ │ │ │ v_centaines = "" │ │ │ │ │ v_dizaines = "" │ │ │ │ │ v_unites = "" │ │ │ │ │ v_euros = centaines │ │ │ │ │ v_euros >= 100 ? │ │ │ │ non └────────────────┬────────────────┘ │ │ │ ┌──────────────────────● │ │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ │ v_centaines = libellé centaines │ │ │ │ │ └────────────────┬────────────────┘ │ │ │ └─────────────────────►│ │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ v_euros = dizaines │ │ │ │ │ v_euros >= 20 ? │ │ │ │ non └────────────────┬────────────────┘ │ │ │ ┌──────────────────────● │ │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ │ v_dizaines = libellé dizaines │ │ │ │ │ └────────────────┬────────────────┘ │ │ │ └─────────────────────►│ │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ v_euros = unités │ │ │ │ │ v_euros >= 1 ? │ │ │ │ non └────────────────┬────────────────┘ │ │ │ ┌──────────────────────● │ │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ │ v_unites = libellé unites │ │ │ │ │ └────────────────┬────────────────┘ │ │ │ └─────────────────────►│ │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ v_total = v_total + v_centaines │ │ │ │ │ + v_dizaines │ │ │ │ │ + v_unites │ │ │ │ │ J = J + 1 │ │ │ │ │ J :: 2 │ │ │ │ └────────────────┬────────────────┘ │ │ └────────────────────────────┼──────────────────────┘ = │ ●────────────────────────────┘ ┌────────────────────────────┼──────────────────────┐ F-PROG │ ┌────────────────┴────────────────┐ │ │F-EUROS │ PRINT v_total │ │ │ ├─────────────────────────────────┤ │ │D-CENTIMES │ v_total = "" │ │ │ │ v_dizaines = "" │ │ │ │ v_unites = "" │ │ │ │ v_centimes = dizaines │ │ │ │ v_centimes >= 20 ? │ │ │ non └────────────────┬────────────────┘ │ │ ┌──────────────────────● │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ v_dizaines = libellé dizaines │ │ │ │ └────────────────┬────────────────┘ │ │ └─────────────────────►│ │ │ ┌────────────────┴────────────────┐ │ │ │ v_centimes = unites │ │ │ │ v_centimes > 1 ? │ │ │ non └────────────────┬────────────────┘ │ │ ┌──────────────────────● │ │ │ ┌────────────────┴────────────────┐ │ │ │ │ v_unites = libellé unites │ │ │ │ └────────────────┬────────────────┘ │ │ └─────────────────────►│ │ │ ┌────────────────┴────────────────┐ │ │F-CENTIMES │ v_total = v_total + v_dizaines │ │ │ │ + v_unites │ │ │ │ PRINT v_total │ │ │ └─────────────────────────────────┘ │ └───────────────────────────────────────────────────┘
§ 4. L'Algorithme
Le code source est extrait d’un développement réel datant de février 1995. Le langage « ace » utilisé (compilateur de programmes d’édition du SGBD Informix ISQL) est un langage de gestion proche du SQL, aussi compréhensible qu’un pseudo-langage.
Adapté à des montants inférieurs au million d’Euros, l’algorithme doit d’abord traduire textuellement les milliers d’Euros (s’il y en a), puis les Euros de 1 à 999 (s’il y en a) et traduire enfin les Centimes (s’il y en a).
Je ne garantie pas le respect de la règle des traits d’union que j’ignorais à l’époque. J’ai essayé de la prendre en compte à postériori sans possibilité de tester.
§ 5. Exercice pratique de refactoring
L’algorithme ne respecte pas rigoureusement l’algorigramme. À l’époque, pour ne pas froisser la susceptibilité du compilateur, simplifier la compilation en optimisant le nombre d’instructions était plus important que le respect de l’éthique méthodologique et la recherche de performance.
Il peut être intéressant :
- De transcrire l’algorithme dans le langage que vous pratiquez.
La démarche s’apparente à une intervention de maintenance qui oblige à comprendre, à s’approprier la programmation de quelqu’un d’autre.
- De remplacer la lecture du montant depuis une table BDD par une saisie du montant depuis un écran.
- De remplacer la sortie imprimante par un affichage écran.
- De revisiter l’algorithme pour le rendre performant et cohérent avec l’algorigramme.
Ainsi, la première itération de la boucle DO peut être évitée dans le cas où le montant à traduire est inférieur à 1000 Euros. De même qu’il est possible d’éviter la traduction des centaines s’il n’y en a pas, et/ou des dizaines s’il n’y en a pas, et/ou des unités s’il n’y en a pas.
Peut-être même révélerez-vous quel qu’erreur bien que l’algorithme ait tourné pendant près de 15 ans. Cela dit, je doute que les traitements réels aient permis de tester des montants supérieurs à mille Euros ou même à mille Francs en 1995 lorsque le programme à été développé.
§ 6. ANNEXES
§ 6.1. Divagations méthodologiques
L’originalité de l’algorithme "Traduction textuelle d’un montant numérique" consiste à associer les méthodologies LCP de Jean-Dominique Warnier et CORIG de Robert Mallet, conçues dans les années 1960-70.
Revenir à ces basiques permet bien souvent, au-delà de toute méthode particulière, de retrouver une démarche saine, simple, humaine et maîtrisée pour la résolution des problèmes, même les plus complexes ayant trait aux systèmes d'information.
Ces hypothèses de travail s'avèrent souvent utiles et précieuses à rappeler et peuvent constituer la base d'un enseignement initial et permanent des systèmes d'information et de l'informatique.
Refaire les greniers n'est pas forcément une perte de temps.
Il n’est pas nécessaire de reproduire ici l’intégralité d’un Billet de blog que je consacre au sujet. Ceux que cela intéresse peuvent consulter ce billet de blog :
■ ■ ■ SOMMAIRE ■ ■ ■
- Algorigramme
- CORIG - COnception et Réalisation de l’Informatique de Gestion
- LCP - Logique de Construction de Programme
- PS - Programmation Structurée
- Conclusion
§ 6.2. De l'instruction PRINT FILE
Certains programmes d’édition peuvent être très complexes en termes de traitement d’informations fixes (tableaux, texte aligné/justifié, par exemple) et d’informations variables. L’instruction "PRINT FILE" simplifie la programmation en traitant l’ensemble des informations fixes d’un état sous forme d’un fichier-formulaire imprimable. Cette instruction n’existe pas forcément dans tous les langages. Lorsqu’elle existe, la difficulté consiste toutefois à créer le formulaire.
Un simple traitement de texte mode caractère des années 80, SPRINT de Borland, permet de créer sous MS/DOS un tel formulaire de qualité bureautique très convenable qui peut d’ailleurs éviter dans certains cas l’utilisation de pré-imprimés. Imprimer avec Informix des tableaux complexes, du texte aligné/justifié en différentes polices de tailles différentes, en variant l’interligne… devient facile.
SPRINT permet soit de sauvegarder le formulaire créé en tant que fichier .prn (PCL 5), soit de l’envoyer à l’imprimante. Il suffit d’ouvrir ce fichier .prn produit avec SPRINT et d’y apporter quelques modifications rudimentaires en début et en fin de fichier :
- Sous MS/DOS : Tout d’abord, il faut ajouter un Carriage-return à la fin de chaque ligne du fichier .prn car sinon le fichier transféré sous Unix ne fera qu’un seul item. Il peut alors dépasser la taille maxi et surtout il devient ingérable sous Vi. L’opération peut se faire de différentes façons, soit avec le traitement de texte lui-même qui joue alors le rôle d’un excellent éditeur de texte, soit en convertissant le fichier MS/DOS en fichier Unix (en deux clics avec Notepad++).
- Sous MS/DOS ou Unix : Il convient d’intervenir en début de fichier pour dire à l’imprimante de mémoriser la position du curseur « [Esc]&f0S » et lui signifier un interligne nul « [Esc]&l0C » de façon à annihiler les Carriage-return ajoutés qui se traduiraient par des sauts de ligne. Les sauts de ligne sont déjà assurés par des commandes PCL de mouvement de l’index vertical « [Esc]&a+nnV ».
- Toujours sous MS/DOS ou Unix : Il reste en fin de fichier à remplacer les commandes PCL de saut de page et réinitialisation de l’imprimante (générées par le traitement de texte) par la commande « Rappel de la position du curseur ([Esc]&f1S) ».
Peut-être bien le seul à avoir utilisé cette instruction, j’ai fait part de mon expérience sur le sujet dans cette discussion :
De l'instruction PRINT FILE
§ 6.3. Discussions similaires
- convertir un montant en toutes lettres
Par lido dans le forum Forms
- Cherche un code qui me permet de convertir un montant chiffre en lettre
Par aminem99 dans le forum VB.NET
- Convertir un montant en chiffre en montant en toute lettre
Par graymatter dans le forum WinDev
- Convertir un montant en lettre dans un état Crystal reports
Par gopal dans le forum SAP Crystal Reports
- ?Convertir le montant de ma facture en lettres?
Par Redhouane dans le forum Bases de données
- [VB.NET]Convertir un montant numérique en lettres
Par kinganasius dans le forum Windows Forms
- [Mail] Convertir une somme en toute lettres
Par mijean dans le forum Langage
- Exprimer "textuellement" un montant financier
Par Krashtest dans le forum SQL
FIN - Travaux Pratiques d'algorithmique (Force 3/7)
Traduction textuelle d’un montant numérique