Using.NET comment convertir en UTF-8 les fichiers texte encodés ISO 8859-1 qui contiennent des caractères accentués latins-1

on m'envoie des fichiers texte enregistrés dans le format ISO 88591-1 qui contiennent des caractères accentués de la gamme Latin-1 (ainsi que des ASCII A-z normaux, etc.). Comment convertir ces fichiers en UTF-8 en utilisant C# pour que les caractères accentués à un octet dans la norme ISO 8859-1 deviennent des caractères UTF-8 valides?

j'ai essayé d'utiliser un StreamReader avec ASCIIEncoding, puis de convertir la chaîne ASCII en UTF-8 par instanciation encodage ascii et encodage utf8 et ensuite en utilisant Encoding.Convert(ascii, utf8, ascii.GetBytes( asciiString) ) - mais les caractères accentués sont rendus comme des points d'interrogation.

quelle étape je rate?

15
demandé sur Peter Mortensen 2010-04-07 23:50:43

2 réponses

vous devez obtenir l'objet approprié Encoding . ASCII est comme il est appelé: ASCII, ce qui signifie qu'il ne supporte que les caractères ASCII 7 bits. Si ce que vous voulez faire est de convertir des fichiers, alors c'est probablement plus facile que de traiter les tableaux d'octets directement.

using (System.IO.StreamReader reader = new System.IO.StreamReader(fileName,
                                       Encoding.GetEncoding("iso-8859-1")))
{
    using (System.IO.StreamWriter writer = new System.IO.StreamWriter(
                                           outFileName, Encoding.UTF8))
    {
        writer.Write(reader.ReadToEnd());
    }
}

Cependant, si vous voulez avoir les tableaux d'octets, c'est assez facile à faire avec Encoding.Convert .

byte[] converted = Encoding.Convert(Encoding.GetEncoding("iso-8859-1"), 
    Encoding.UTF8, data);

Il est important de noter ici, cependant, que si vous voulez suivre cette voie alors vous devriez pas utiliser un lecteur de chaîne de caractères basé sur l'encodage comme StreamReader pour votre fichier IO. FileStream serait mieux adapté, il va lire les octets des fichiers.

dans l'intérêt de l'exploration complète de la question, quelque chose comme ceci fonctionnerait:

using (System.IO.FileStream input = new System.IO.FileStream(fileName,
                                    System.IO.FileMode.Open, 
                                    System.IO.FileAccess.Read))
{
    byte[] buffer = new byte[input.Length];

    int readLength = 0;

    while (readLength < buffer.Length) 
        readLength += input.Read(buffer, readLength, buffer.Length - readLength);

    byte[] converted = Encoding.Convert(Encoding.GetEncoding("iso-8859-1"), 
                       Encoding.UTF8, buffer);

    using (System.IO.FileStream output = new System.IO.FileStream(outFileName,
                                         System.IO.FileMode.Create, 
                                         System.IO.FileAccess.Write))
    {
        output.Write(converted, 0, converted.Length);
    }
}

dans cet exemple ,la variable buffer est remplie avec les données réelles dans le fichier comme byte[] , donc aucune conversion n'est effectuée. Encoding.Convert spécifie un encodage source et destination, puis stocke les octets convertis dans la variable named... converted . Ceci est ensuite écrit directement dans le fichier de sortie.

comme je l'ai dit, la première option utilisant StreamReader et StreamWriter sera beaucoup plus simple si c'est tout ce que vous faites, mais le dernier exemple devrait vous donner plus d'un indice sur ce qui se passe réellement.

33
répondu Adam Robinson 2013-12-20 17:33:55

si les fichiers sont relativement petits (disons, ~10 mégaoctets), vous n'aurez besoin que de deux lignes de code:

  string txt = System.IO.File.ReadAllText(inpPath, Encoding.GetEncoding("iso-8859-1"));
  System.IO.File.WriteAllText(outPath, txt);
10
répondu Hans Passant 2010-04-07 20:31:01