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

C# Discussion :

Traiter un fichier .txt avec plusieurs colonnes


Sujet :

C#

  1. #1
    Membre régulier
    Homme Profil pro
    Technicien réseau
    Inscrit en
    Janvier 2010
    Messages
    119
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Autre

    Informations professionnelles :
    Activité : Technicien réseau
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Janvier 2010
    Messages : 119
    Points : 77
    Points
    77
    Par défaut Traiter un fichier .txt avec plusieurs colonnes
    Bonjour à tous,
    Je travaille sous Visual Studio. Mon problème est le suivant :
    J'ai un fichier texte qui comporte des informations de la façon suivante :
    [Code Opération (2)][N° E (1)][N° séquence (5)][Date du jour (6) ][Code (5) ][code guichet (5) ][N° compte (12)][Clé RIB (2)][Matricule (7) ][Nom et P (24)][Libellé B.(17) ][Libellé O. (30) ][Montants (12) ]
    02200002200614123540111111111111111183203 totototo ZZZZZZZZZZZZZZZ Virement 000000645029

    Les valeurs entre parenthèses sont le nombres caractères maximum et minimum que les données de la colonne doivent avoir y compris les espaces qui constituent aussi des caractères.

    Je souhaiterais récupérer ces informations et les enregistrer d'abord dans un dataset ensuite pouvoir faire des requêtes les colonnes et vérifier qu'il n'y a pas d'erreurs enfin enregistrer les erreurs trouvées dans un fichier texte. Mon souci c'est que je n'arrive pas à délimiter les colonnes avec la fonction split() vu que se sont des colonnes comportant plusieurs données.

    Ci-dessous mon code :
    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
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
     
    string delimiter = "";
                string tablename = "DTable";
                DataSet dataset = new DataSet();
                utf8 = new UTF8Encoding(false);
                StreamReader sr = new StreamReader(TXTSOURCEBIAO.Text, utf8);
                string csv = File.ReadAllText(FILEDIALOGBIAO.FileName);
     
                dataset.Tables.Add(tablename);//création d'une table mémoire
                //définition des colonne de la table mémoire ou tampon
                dataset.Tables[tablename].Columns.Add("C1");
                dataset.Tables[tablename].Columns.Add("C2");
                dataset.Tables[tablename].Columns.Add("C3");
                dataset.Tables[tablename].Columns.Add("C4");
                dataset.Tables[tablename].Columns.Add("C5");
                dataset.Tables[tablename].Columns.Add("C6");
                dataset.Tables[tablename].Columns.Add("C7");
                dataset.Tables[tablename].Columns.Add("C8");
                dataset.Tables[tablename].Columns.Add("C9");
                dataset.Tables[tablename].Columns.Add("C10");
                dataset.Tables[tablename].Columns.Add("C11");
                dataset.Tables[tablename].Columns.Add("C12");
                dataset.Tables[tablename].Columns.Add("C13");
                dataset.Tables[tablename].Columns.Add("C14");
                dataset.Tables[tablename].Columns.Add("C15");
                dataset.Tables[tablename].Columns.Add("C16");
                dataset.Tables[tablename].Columns.Add("C17");
                dataset.Tables[tablename].Columns.Add("C18");
                dataset.Tables[tablename].Columns.Add("C19");
                dataset.Tables[tablename].Columns.Add("C20");
                string allData = sr.ReadToEnd();
                string[] rows = allData.Split("\r".ToCharArray());
                int count = rows.Length;
                foreach (string r in rows)
                {
                    //découpe la chaine en un tableau de chaine ou de mot délimiter par la valeur de variable délimité
                    string[] items = r.Split(delimiter.ToCharArray());
     
                    dataset.Tables[tablename].Rows.Add(items);
                }
     
                int x = 0;
                int y = 0;
                //remplissage du dataset avec les données du fichier txt
                int count1 = dataset.Tables[tablename].Rows.Count;

  2. #2
    Membre actif
    Profil pro
    Inscrit en
    Juin 2010
    Messages
    210
    Détails du profil
    Informations personnelles :
    Localisation : France, Yvelines (Île de France)

    Informations forums :
    Inscription : Juin 2010
    Messages : 210
    Points : 243
    Points
    243
    Par défaut
    Bonjour,

    Le fichier vous le récupérer ou vous le créer ?

    Les valeurs entre parenthèses sont le nombres caractères maximum et minimum que les données de la colonne doivent avoir y compris les espaces qui constituent aussi des caractères.
    maximum et minimum ? c'est à dire que [code guichet (5) ] par exemple est obligé de faire 5 caractères ?

    Si c'est le cas, n'ayant pas de séparateur, vous pouvez définir vos colonnes grâce à cette valeur que vous connaissez.

    A+.

  3. #3
    Membre émérite Avatar de shadowmoon
    Homme Profil pro
    Expert technique et fonctionnel .Net
    Inscrit en
    Mai 2005
    Messages
    1 066
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Expert technique et fonctionnel .Net
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2005
    Messages : 1 066
    Points : 2 645
    Points
    2 645
    Par défaut
    Bonjour,

    Effectivement, si pour chaque ligne de votre fichier texte, la taille de chaque colonne est fixée à la valeur que vous indiquez, il est plus judicieux d'utiliser cette donnée.

    Et si j'ai bien, compris ce que vous voulez faire, je remplirait plutôt le dataset, a part du fichier texte, ligne par ligne en utilisant Substring pour décomposer "02200002200614123540111111111111111183203 totototo ZZZZZZZZZZZZZZZ Virement 000000645029".

  4. #4
    Membre régulier
    Homme Profil pro
    Technicien réseau
    Inscrit en
    Janvier 2010
    Messages
    119
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Autre

    Informations professionnelles :
    Activité : Technicien réseau
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Janvier 2010
    Messages : 119
    Points : 77
    Points
    77
    Par défaut
    Merci à shadowmoon et egautier18 pour vos réponses.
    Le fichier je le crée dans un premier module et dans le deuxième module je le récupérer pour des contrôles. Certaines personnes peuvent avoir la mauvaise intention de modifier le contenu du fichier alors je dois pouvoir le contrôler, voir si les numéros de compte ne sont pas en doublon, si la date du jour est différente sur toutes les lignes etc...
    je vais d'abord m'orienter sur la piste de la définition de mes colonnes grâce aux valeurs que je connais ensuite essayer la fonction Substring pour décomposer enfin je vous reviendrai pour vous faire un point.

  5. #5
    Modérateur
    Avatar de DotNetMatt
    Homme Profil pro
    CTO
    Inscrit en
    Février 2010
    Messages
    3 611
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : Etats-Unis

    Informations professionnelles :
    Activité : CTO
    Secteur : Finance

    Informations forums :
    Inscription : Février 2010
    Messages : 3 611
    Points : 9 743
    Points
    9 743
    Billets dans le blog
    3
    Par défaut
    Inutile de réinventer la roue, il existe un parser prêt à l'emploi dans le .NET Framework. Voir la classe TextFieldParser. Il faudra au préalable ajouter une référence à l'assembly Microsoft.VisualBasic.dll.

  6. #6
    Membre régulier
    Homme Profil pro
    Technicien réseau
    Inscrit en
    Janvier 2010
    Messages
    119
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Autre

    Informations professionnelles :
    Activité : Technicien réseau
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Janvier 2010
    Messages : 119
    Points : 77
    Points
    77
    Par défaut
    Merci à tous
    j'ai finalement utilisé la fonction Substring.

  7. #7
    Expert éminent
    Avatar de StringBuilder
    Homme Profil pro
    Chef de projets
    Inscrit en
    Février 2010
    Messages
    4 170
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

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

    Informations forums :
    Inscription : Février 2010
    Messages : 4 170
    Points : 7 421
    Points
    7 421
    Billets dans le blog
    1
    Par défaut
    Bonjour,

    Je te conseille TRES FORTEMENT de te baser sur quelque chose du genre de ce qui suit.

    En effet, noyer des substring dans tous les sens dans le code risque de poser de graves problèmes :
    - de réutilisabilité du code
    - de maintenance en cas d'évolutions du format

    Donc je te conseille comme moi de passer par une première classe abstraite qui contient les mécanismes permettant de transformer une ligne "brute" en une liste indexable.

    Et dériver de cette classe abstraite pour chaque format de ligne à charger.

    On y gagne grandement en lisibilité et en évolutivité :
    Code c# : 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
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
     
    using System;
    using System.Collections.Generic;
    using System.Text;
     
    namespace SandBox
    {
        class Program
        {
            static void Main(string[] args)
            {
                Operation operation = new Operation();
                operation.Load("02200002200614123540111111111111111183203    totototo                ZZZZZZZZZZZZZZZ  Virement                      000000645029");
     
                Console.WriteLine("N° Compte : {0}", operation["N° Compte"]);
                Console.WriteLine("Date du Jour : {0}", operation["Date du Jour"]);
                Console.WriteLine("Nom et P : {0}", operation["Nom et P"]);
     
                Console.ReadKey();
            }
        }
     
        struct FieldDefinition
        {
            public string Name;
            public int Length;
        }
     
        abstract class LineLoader
        {
            protected List<FieldDefinition> fielddefinitions;
            private string[] data;
     
            public void Load(string line)
            {
                data = new string[fielddefinitions.Count];
                int index = 0;
                for (int i = 0, cpt = fielddefinitions.Count; i < cpt; i++)
                {
                    data[i] = line.Substring(index, fielddefinitions[i].Length);
                    index += fielddefinitions[i].Length;
                }
            }
     
            private int getfieldindex(string name)
            {
                for (int i = 0, cpt = fielddefinitions.Count; i < cpt; i++)
                {
                    if (fielddefinitions[i].Name == name)
                    {
                        return i;
                    }
                }
                throw new KeyNotFoundException();
            }
     
            public string this[int index]
            {
                get
                {
                    return data[index];
                }
                set
                {
                    data[index] = value;
                }
            }
     
            public string this[string fieldname]
            {
                get
                {
                    return data[getfieldindex(fieldname)];
                }
                set
                {
                    data[getfieldindex(fieldname)] = value;
                }
            }
        }
     
        class Operation : LineLoader
        {
            public Operation()
            {
                fielddefinitions = new List<FieldDefinition>();
                fielddefinitions.Add(new FieldDefinition() { Name = "Code Opération", Length = 2 });
                fielddefinitions.Add(new FieldDefinition() { Name = "N° E", Length = 1 });
                fielddefinitions.Add(new FieldDefinition() { Name = "N° Séquence", Length = 5 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Date du Jour", Length = 6 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Code", Length = 5 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Code Guichet", Length = 5 });
                fielddefinitions.Add(new FieldDefinition() { Name = "N° Compte", Length = 12 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Clé RIB", Length = 2 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Matricule", Length = 7 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Nom et P", Length = 24 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Libellé B", Length = 17 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Libellé O", Length = 30 });
                fielddefinitions.Add(new FieldDefinition() { Name = "Montants", Length = 12 });
            }
        }
    }

  8. #8
    Membre régulier
    Homme Profil pro
    Technicien réseau
    Inscrit en
    Janvier 2010
    Messages
    119
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Autre

    Informations professionnelles :
    Activité : Technicien réseau
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Janvier 2010
    Messages : 119
    Points : 77
    Points
    77
    Par défaut
    Bonsoir StringBuilder,
    Merci pour ton idée, Je vais l’implémenter et voir comment elle fonctionnera.

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

Discussions similaires

  1. comment traiter un fichier.txt avec "replace" ?
    Par pasrico dans le forum VB 6 et antérieur
    Réponses: 13
    Dernier message: 11/04/2011, 23h06
  2. Réponses: 3
    Dernier message: 31/05/2010, 17h58
  3. Réponses: 4
    Dernier message: 12/05/2009, 12h21
  4. Réponses: 1
    Dernier message: 04/05/2005, 11h43
  5. Pb import fichier txt avec lignes de longueurs diverses
    Par zebulon90 dans le forum MS SQL Server
    Réponses: 2
    Dernier message: 09/12/2004, 08h32

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