Appeler une procedure avec un argument fantôme [Résolu]

Messages postés
131
Date d'inscription
dimanche 29 octobre 2006
Statut
Membre
Dernière intervention
30 novembre 2018
- - Dernière réponse : korgis
Messages postés
428
Date d'inscription
samedi 17 mai 2003
Statut
Membre
Dernière intervention
6 mai 2019
- 12 mai 2013 à 11:14
J'ai écrit une procédure très simple:

procedure Sma(A:Array of variant);
var
    S: String;
    I: byte;
    Message: String;
begin
   For I:=0 to Length(A) DO
   begin 
      S:=A[I];
      Message:= Message+S;
   end;
   ShowMessage(Message);
end;


Ce qui me permet d'écrire:
Sma('Les valeurs de X et Y sont ',x,' ',y);
au lieu de
ShowMessage('Les valeurs de X et Y sont '+inttostr(x)+' '+inttostr(y));


C'est bien agréable de se simplifier la vie mais je voudrais aller plus loin et pouvoir écrire deux virgules consécutives pour remplacer un espace entre deux guillemets. Autrement dit, je voudrais pouvoir écrire:
Sma('Les valeurs de X et Y sont ',x,,y);

Pour l'instant, ces deux virgules consécutives provoquent un message d'erreur.

J'ai essayé:
IF A[I]=NIL  then  A[I]=' ';

ainsi que
IF A[I]=''  then  A[I]=' '; 

et
IF A[I]=0  then  A[I]=' ';


Rien de tout ça ne marche.

Sur Internet, j'ai trouvé une façom plus subtile de faire mon ShowMessage amélioré.
On part de la fonction:


FUNCTION MakeStr(Const Args: Array Of Const): String ;
VAR
    I: Integer;
Begin
   Result := '';
   FOR I := 0 TO High(Args) DO
   Begin
      //showmessage(inttostr(ord(args[i].VType)));
      WITH Args[I] DO
         Case VType Of
            VtInteger:  Result := Result + Inttostr(VInteger);
            VtBoolean:  Result := Result + BoolToStr(VBoolean,True);
            VtChar:     Result := Result + VChar;
            VtExtended: Result := Result + FloatToStr(VExtended^);
            VtString:   Result := Result + VString^;
            VtPChar:    Result := Result + VPChar;
            VtObject:   Result := Result + VObject.ClassName;
            VtClass:    Result := Result + VClass.ClassName;
            VtAnsiString:  Result := Result + String(VAnsiString);
            VtCurrency:    Result := Result + CurrToStr(VCurrency^);
            VtVariant:     Result := Result + String(VVariant^);
            VtInt64:       Result := Result + Inttostr(VInt64^);
         End;
   End;
End;


et la procédure Sma devient:

procedure Sma(A: array of const);
begin
   showmessage(MakeStr(A));
end;


Mais cette procédure non plus n'accepte pas deux virgules consécutives.
Je ne vois pas comment utiliser un Try...Except...
D'autres idées ?
Afficher la suite 

12 réponses

Meilleure réponse
Messages postés
2233
Date d'inscription
mardi 10 décembre 2002
Statut
Modérateur
Dernière intervention
15 décembre 2014
5
3
Merci
For I:=0 to Length(A) DO

Composants Cindy pour Delphi
Faites une donation.

Dire « Merci » 3

Quelques mots de remerciements seront grandement appréciés. Ajouter un commentaire

Codes Sources 130 internautes nous ont dit merci ce mois-ci

Commenter la réponse de cs_MAURICIO
Messages postés
428
Date d'inscription
samedi 17 mai 2003
Statut
Membre
Dernière intervention
6 mai 2019
16
3
Merci
Excuse-moi de ne pas connaitre l'unité de monnaie du Portugal


L'Euro !!!!

Dire « Merci » 3

Quelques mots de remerciements seront grandement appréciés. Ajouter un commentaire

Codes Sources 130 internautes nous ont dit merci ce mois-ci

Commenter la réponse de korgis
Messages postés
428
Date d'inscription
samedi 17 mai 2003
Statut
Membre
Dernière intervention
6 mai 2019
16
0
Merci
Salut,

je te conseille d'utiliser la fonction "Format". Voir "Chaînes de format" dans l'aide en ligne de Delphi.
Commenter la réponse de korgis
Messages postés
131
Date d'inscription
dimanche 29 octobre 2006
Statut
Membre
Dernière intervention
30 novembre 2018
1
0
Merci
Merci pour ta réponse.

Mais je ne vois pas où placer le mot format. En faisant des recherches, j'ai découvert que Delphi contenait le mot ShowMessageFmt (pas très connu) qui accepte comme second paramètre un array of const et qui permet d'écrire:

ShowmessageFmt('%s',['x vaut ',,,,x]);

Mais ça aussi, ça donne un message d'erreur
Commenter la réponse de fredelem
Messages postés
4200
Date d'inscription
samedi 16 octobre 2004
Statut
Modérateur
Dernière intervention
2 janvier 2019
26
0
Merci
showMessageFmt('Les valeurs de %s et %s sont %d et %d', ['X','Y', px, py]);

________________________________________________________
Commenter la réponse de f0xi
Messages postés
4200
Date d'inscription
samedi 16 octobre 2004
Statut
Modérateur
Dernière intervention
2 janvier 2019
26
0
Merci
ah oui et je ne vois pas pourquoi tu cherche à mettre des virgules sans paramètres...

c'est normal que le compilateur t'engueule.

Sma('Les valeurs de X et Y sont ',x,,y) <-- ça c'est de la connerie.

Sma('Les valeurs de X et Y sont ',x,' ',y) <-- ça ça sert à rien


Tu peux réécrire ta procédure comme suis :

function Sma(aFmtStr: string; const aConsts: array of const): string;
begin
  result := format(aFmtStr, aConsts);
  showMessage(result);
end;


________________________________________________________
Commenter la réponse de f0xi
Messages postés
131
Date d'inscription
dimanche 29 octobre 2006
Statut
Membre
Dernière intervention
30 novembre 2018
1
0
Merci
Pas d'accord.
Mon but, c'est de m'économiser du travail en donnant à Sma la syntaxe de write qui me convient parfaitement.
Dire que ça ne sert à rien me parait être un jugement très personnel. Moi, je trouve ça génial.

Je ne pense pas non plus que ce soit s'engager sur une impasse que de vouloir écrire
Sma('Les valeurs de X et Y sont ',x,,y)
car dans certains cas, le compilateur de Delphi l'accepte. Par exemple, quand on écrit un Shellexecute, il est permis de mettre deux virgules consécutives. Et même,si on écrit NIL là où il attendait une chaine, il râle un peu mais il accepte. Bien sûr, j'admets qu'il soit généreux envers ses propres enfants, mais je pense que si je sais lui parler comme il faut, il m'accordera les mêmes faveurs.

La solution que tu me proposes, bon, elle marche certes mais elle ne va pas dans le sens que je souhaite: économiser du travail.
Commenter la réponse de fredelem
Messages postés
131
Date d'inscription
dimanche 29 octobre 2006
Statut
Membre
Dernière intervention
30 novembre 2018
1
0
Merci
 
   La réponse de Mauricio m'a beaucoup aidé et du coup, je suis revenu sur les réponses précédentes. Je me suis aperçu que Korgis avait raison, il fallait utiliser la fonction "format". Et l'idée de fOxi était très bonne. Je ne sais pas pourquoi il
s'est amusé à ajouter un px et un py. Je préfère écrire
         showMessageFmt('Les valeurs de X et Y sont %d et %d', [px, py]);


   C'est finalement cette solution que je vais adopter mais il y a encore quelque chose qui me gêne; l'obligation d'écrire des crochets autour des arguments. Pour éviter ça, ma procédure devient:
PROCEDURE Sma(S:String; Const C1: Variant; Const C2: Variant;  Const C3: Variant; Const C4: Variant);
Begin
   ShowMessagefmt(S,[C1,C2,C3,C4]);
End;


J'appelle cette procédure par:
   Sma('Les valeurs de X et Y sont %s et %s',x,y,$,$);
C'est quand même plus sympa que
   Showmessage('Les valeurs de X et y sont '+inttostr(x)+' et '+inttostr(y));

   Évidemment, il y a ces deux dollars à la fin qui sont nécessaires pour avoir les 4 constantes prévues: C1,C2,C3 et C4. J'ai finalement admis qu'on ne pouvait avoir deux virgules consécutives (même pas avec Shellexecute, ma mémoire m'a trompé). Je suis obligé de mettre quelque chose, peu importe quoi puisque ça n'apparait pas dans le showmessage.

   A la place des dollars, j'aurais pu mettre des zéros ou un nom de variable mais pas grand-chose d'autre. Un arobase provoque un message d'erreur. Idem, si je mets l'un des caractères suivants: # % & < > ? ç é à è.
   Pourquoi diable le $ est-il accepté alors que la livre anglaise (£) ou le Yen (¥) provoquent un message d'erreur ?

   Peu importe, ce qui compte, c'est que grâce à votre aide, j'ai abouti à un mélange de solutions qui me conduit à une procédure très simple et performante. Merci à tous.

                       Fred

   PS: J'avais envisagé d'écrire:

   PROCEDURE Sma(S:String; Const C1: Variant; Const C2: Variant='';  Const C3: Variant=''; Const C4: Variant='');


   ce qui m'aurait dispensé d'écrire mes dollars à la fin. Mais ce n'est pas possible, une variante ne peut pas être initialisée. Des idées pour contourner ça ?
Commenter la réponse de fredelem
Messages postés
2233
Date d'inscription
mardi 10 décembre 2002
Statut
Modérateur
Dernière intervention
15 décembre 2014
5
0
Merci
"une variante ne peut pas être initialisée"

Tu peux utiliser le type String!!!

a+


Composants Cindy pour Delphi
Faites une donation.
Commenter la réponse de cs_MAURICIO
Messages postés
131
Date d'inscription
dimanche 29 octobre 2006
Statut
Membre
Dernière intervention
30 novembre 2018
1
0
Merci
   Eh oui, j'y ai pensé. Mais alors, il faut que j'appelle ma procédure par

      Sma('Les valeurs de x et y sont %s et %s', inttostr(x), inttostr(y));

   La cata, juste ce que je veux éviter !


   PS: j'ai trouvé pourquoi "$" est accepté comme variant et pas la livre anglaise ni le yen ni d'ailleurs l'euro ni la peseta. Excuse-moi de ne pas connaitre l'unité de monnaie du Portugal mais je pense qu'elle ne passerait pas non plus. Le $ est accepté car Delphi le voit comme un nombre hexadécimal, un équivalent de $00.
Commenter la réponse de fredelem
Messages postés
131
Date d'inscription
dimanche 29 octobre 2006
Statut
Membre
Dernière intervention
30 novembre 2018
1
0
Merci
@Korgis:

   Je vois que tu es jeune et que tu n'as connu que l'Euro. Mais nous les anciens qui sommes nés avant 2002, nous avons connu le temps où l'unité monétaire du Portugal était l'Escudo.
   Malgré ton jeune âge, tu m'as orienté vers la bonne voie. Mais pour en finir avec mes dollars, personne ne m'a dit qu'il y avait la solution de la surcharge. J'y avais pensé dès le début mais j'aurais préféré trouver autre chose. Je me suis résigné à utiliser cette solution et j'ai écrit 4 procédures Sma avec un nombre d'arguments derrière le format allant de 1 à 4. Pas de pb, ça marche très bien, j'ai ce que je voulais.
   Puisque ça m'a réussi de poser des questions, j'en pose une autre ce matin. J'espère avoir des réponses sérieuses, en particulier de la part des jeunes gorilles.
Commenter la réponse de fredelem
Messages postés
428
Date d'inscription
samedi 17 mai 2003
Statut
Membre
Dernière intervention
6 mai 2019
16
0
Merci
Je vois que tu es jeune et que tu n'as connu que l'Euro


Pour info : 1 EURO = 655 anciens francs...
Commenter la réponse de korgis