IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

 Delphi Discussion :

Types Incompatibles AnsiChar et Char !


Sujet :

Delphi

  1. #1
    Membre averti
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2018
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 26
    Localisation : Autriche

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Communication - Médias

    Informations forums :
    Inscription : Mai 2018
    Messages : 23
    Par défaut Types Incompatibles AnsiChar et Char !
    Salut tout le monde ! j'ai un petit problème qui me bloque ; j'utilise XE5 , pourquoi j'ai ce message d'erreur en compilant le programme ?
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    procedure TForm1.SpeedButton1Click(Sender: TObject);
    var
     s: string[255];
     c: array[0..255] of Byte absolute s;
     i: Integer;
    begin
     s := Edit1.Text;
     for i := 1 to ord(s[0]) do c[i] := 10 xor c[i];
     Memo1.Text:=s;
     for i:=1 to Length(s) do s[i] := Char(10 xor ord(s[i]));
      Memo2.Text:=s;
    end;
    merci de répondre a ma question

  2. #2
    Rédacteur/Modérateur

    Avatar de SergioMaster
    Homme Profil pro
    Développeur informatique retraité
    Inscrit en
    Janvier 2007
    Messages
    15 569
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 68
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Janvier 2007
    Messages : 15 569
    Billets dans le blog
    65
    Par défaut
    Bonjour,
    Réponse rapide : parce que vous êtes confronté à de l'Unicode.

  3. #3
    Modérateur
    Avatar de tourlourou
    Homme Profil pro
    Biologiste ; Progr(amateur)
    Inscrit en
    Mars 2005
    Messages
    3 910
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 62
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Biologiste ; Progr(amateur)

    Informations forums :
    Inscription : Mars 2005
    Messages : 3 910
    Billets dans le blog
    6
    Par défaut
    Bonjour,
    Il est certain que mentionner l'endroit du code qui déclenche l'erreur est un plus...
    s[i] := Char(10 xor ord(s[i])); // ici, peut-être ?
    je pense que la chaîne s est une AnsiString (caractères sur un octet), mais que le type Char est en Unicode (caractères sur deux octets).
    Delphi 5 Pro - Delphi 11.3 Alexandria Community Edition - CodeTyphon 6.90 sous Windows 10 ; CT 6.40 sous Ubuntu 18.04 (VM)
    . Ignorer la FAQ Delphi et les Cours et Tutoriels Delphi nuit gravement à notre code !

  4. #4
    Membre averti
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2018
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 26
    Localisation : Autriche

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Communication - Médias

    Informations forums :
    Inscription : Mai 2018
    Messages : 23
    Par défaut
    Citation Envoyé par tourlourou Voir le message
    Bonjour,
    Il est certain que mentionner l'endroit du code qui déclenche l'erreur est un plus...
    s[i] := Char(10 xor ord(s[i])); // ici, peut-être ?
    je pense que la chaîne s est une AnsiString (caractères sur un octet), mais que le type Char est en Unicode (caractères sur deux octets).
    Oui vous avez raison le message d'erreur indique cette ligne
    for i:=1 to Length(s) do s[i] := Char(10 xor ord(s[i]));
    mais je ne comprends pas ; tout semble correct comment faire alors?!

  5. #5
    Expert éminent
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 982
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 982
    Par défaut
    C'est ce que l'on appele une ShortString, c'est une Chaine Ansi
    Différent du string sans longueur, le type naturel en Delphi, qui est une Chaine Unicode (depuis une dizaine d'année)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    procedure TForm1.SpeedButton1Click(Sender: TObject);
    var
      s: string[255]; // avec longueur, type ShortString avec AnsiChar
      c: array[0..255] of Byte absolute s;
      i: Integer;
    begin
      s := Edit1.Text; // Ici Problablement un warning de conversion implicite avec perte, cela doit être pris au sérieux et toujours faire en sorte que coder autrement
      for i := 1 to ord(s[0]) do
        c[i] := 10 xor c[i];
      Memo2.Lines.Add(s); // Add sera plus intéressant pour voir les résultats se cumuler
     
      for i:=1 to Length(s) do 
        s[i] := AnsiChar(10 xor ord(s[i])); // Faut juste utiliser le bon type, la réponse était dans le message d'erreur
      Memo2.Lines.Add(s);
    end;
    Attention, absolute c'est rigolo, disons que pour éviter quelques Cast as Class, cela peut rendre le code plus lisible
    Pour l'accès mémoire de type complexe comme les tableaux, c'est une prise de risque notable

    Eviter ShortString, string[...] ou AnsiString la plupart du temps, n'utilisez QUE string
    Votre code sera adapté à l'utilisation de la VCL
    Les autres types seront utile quand vous attaquerez des API plus pointues


    Etudiez le code suivant qui joue avec la différence entre le AnsiChar 8Bits et le WideChar 16Bits

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    var
      s: string; // sans longueur, type UnicodeString avec WideChar synonyme de Char en DXE5
      i: Integer;
    begin
      // La différence commencera à se voir si vous sortez du Latin1 classique comme Œ ou œ qui appartiennent à la seconde page Unicode
      s := Edit1.Text + '"Œ" ou "œ"';
      for i := 1 to Length(S) do
        s[i] := Char(10 xor Ord(s[i])); // Cette fois c'est Ord et Char, Ord ne renvoi pas un Byte comme le dit la Doc mais bien un Word, registe ASM 16Bits utilisé CX pour un XOR CX
      Memo2.Lines.Add(s);
     
      for i:=1 to Length(s) do
        s[i] := Char(10 xor Ord(s[i]));
      Memo2.Lines.Add(s);
     
      s := Edit1.Text + '"Œ" ou "œ"';
      for i := 1 to Length(S) do
        s[i] := Char(10 xor Word(s[i])); // Cette fois c'est Word et Char, toujours en XOR CX opération ASM 16Bits
      Memo2.Lines.Add(s);
     
      for i:=1 to Length(s) do
        s[i] := Char(10 xor Word(s[i]));
      Memo2.Lines.Add(s);
     
      s := Edit1.Text + '"Œ" ou "œ"';
      for i := 1 to Length(S) do
        s[i] := Char(10 xor Byte(s[i])); // C'est un Byte explicite, le registre sera réduit à CL, donc un 8Bit XOR CL
      Memo2.Lines.Add(s);
     
      for i:=1 to Length(s) do
        s[i] := Char(10 xor Byte(s[i])); // Et ici on constate la perte du passage en Byte (AnsiChar) au lieu de manipuler un Char
      Memo2.Lines.Add(s);
    end;
    Aide via F1 - FAQ - Guide du développeur Delphi devant un problème - Pensez-y !
    Attention Troll Méchant !
    "Quand un homme a faim, mieux vaut lui apprendre à pêcher que de lui donner un poisson" Confucius
    Mieux vaut se taire et paraître idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la médiocrité !

    L'expérience, c'est le nom que chacun donne à ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  6. #6
    Membre Expert
    Avatar de ALWEBER
    Homme Profil pro
    Expert Delphi
    Inscrit en
    Mars 2006
    Messages
    1 519
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 70
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Expert Delphi

    Informations forums :
    Inscription : Mars 2006
    Messages : 1 519
    Billets dans le blog
    10
    Par défaut
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    var
     s1 : AnsiSTring ;
     i: Integer;
    begin
     s1 := Edit1.Text;
     for i := 1 to length (s1) do s1[i] := ansiChar(10 xor byte(s1[i]));
     Memo1.Text:=s1;
     ....
    end;

  7. #7
    Membre averti
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2018
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 26
    Localisation : Autriche

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Communication - Médias

    Informations forums :
    Inscription : Mai 2018
    Messages : 23
    Par défaut
    Merci ! vous êtes super gentil ! merci aussi a ALWEBER,tourlourou,SergioMaster

  8. #8
    Expert éminent
    Avatar de Paul TOTH
    Homme Profil pro
    Freelance
    Inscrit en
    Novembre 2002
    Messages
    8 964
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Freelance
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Novembre 2002
    Messages : 8 964
    Par défaut
    tant qu'à fait des choses crades

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
    procedure TMain.Edit1Change(Sender: TObject);
    {$POINTERMATH ON}
    var
      s: string;
      w: PWord;
      i: Integer;
    begin
      s := Edit1.Text;
      w := Pointer(s);
      Dec(w); // car 0 basé
      for i := 1 to Length(s) do
        w[i] := 10 xor w[i];
      Edit2.Text := s;
    end;
    mais attention, les string Unicode ne sont pas neutres...jusque Delphi 2009 le type String était un blob binaire dans lequel on pouvait faire ce qu'on voulait, mais depuis l'unicode, les caractères ont un sens, et notamment si on fait passer la chaîne transformée dans une chaîne Ansi (pour la stocker dans un fichier INI Ansi par exemple) puis qu'on la remet dans un String Unicode, il y a des chances qu'elle ne soit pas correctement décodée par la suite. Car il n'y a pas forcément une conversion sans perte de l'Unicode avec des caractères 16bits vers de l'Ansi...on a même un Warning à ce sujet
    Developpez.com: Mes articles, forum FlashPascal
    Entreprise: Execute SARL
    Le Store Excute Store

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. "Types incompatibles" : char* et char[5000]
    Par Invité dans le forum Débuter
    Réponses: 4
    Dernier message: 26/09/2011, 21h55
  2. [VB.NET] Type Incompatible
    Par Cyrilange dans le forum Windows Forms
    Réponses: 6
    Dernier message: 08/11/2009, 20h08
  3. ODBC Access => Type Incompatible avec un champ DATE ?
    Par MaTHieU_ dans le forum C++Builder
    Réponses: 6
    Dernier message: 23/04/2005, 02h02
  4. Types Incompatibles
    Par olivierlsf dans le forum Bases de données
    Réponses: 1
    Dernier message: 11/03/2005, 18h01
  5. [LG]Problême "types incompatibles"
    Par pierrOPSG dans le forum Langage
    Réponses: 7
    Dernier message: 23/04/2004, 21h34

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo