Odczyt/Zapis pliku CSV bez użycia split

0

Witam wszystkich,

Może i problem dla wielu z Was wydawać się błahy, jednak potrzebuję pomocy. Mam do napisania na poprawkę program, który ma operować na csv'kach i elemencie listview. Poprzednio zawaliłem sprawę, gdyż nie wiedziałem, że wykładowca jest strasznie uczulony na funkcję wymienioną w temacie. Zaproponował użycie prasera bądź gotowej biblioteki. Jednak sam za bardzo nie wiem jak to ogarnąć.

Poprzednio kod wyglądał w taki sposób:

Odczyt:

var parsedData=new List<string[]>();
             using (OpenFileDialog otwieraniepliku = new OpenFileDialog())
                try
                {
                    //Otwieranie pliku
                    otwieraniepliku.InitialDirectory = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
                    otwieraniepliku.DefaultExt = "csv";
                    otwieraniepliku.Title = "Otwórz plik";
                    otwieraniepliku.Filter = "Dokumenty (*.csv)|*.csv";
                    //Interakcja po zatwierzeniu
                    if (otwieraniepliku.ShowDialog() == DialogResult.OK)
                    {
                        listView1.Items.Clear();
                        FileStream srcFS;
                        srcFS = new FileStream(otwieraniepliku.FileName, FileMode.Open);
                        StreamReader srcSR = new StreamReader(srcFS,System.Text.Encoding.Default);
                        string line;
                        int k=0, p=0;
                        bool firstLine=true;
                        //Odczytywanie linii z pliku tekstowego
                        while ((line = srcSR.ReadLine()) != null)
                        {
                            if (firstLine != true)
                            {
                                string row3;
                                
                                string[] rows = line.Split(',');
                                for (int i = 0; i < line.Length; i++)
                                {
                                    if (line[i] == '')
                                    {
                                        p = i;
                                        p++;
                                        break;
                                    }

                                }

                                line = line.Remove(0, p);

                                for (int i = line.Length - 1; i > 0; i--)
                                {
                                    if (line[i] == '')
                                    {
                                        k = i;
                                        break;
                                    }

                                }
                                row3 = line.Remove(k, line.Length - k);
                                

                                ListViewItem item = new ListViewItem(rows[0]);
                                item.SubItems.Add(rows[1]);
                                item.SubItems.Add(row3);
                                item.SubItems.Add(rows[rows.Length - 2]);
                                item.SubItems.Add(rows[rows.Length - 1]);

                                listView1.Items.Add(item);
                            }
                            firstLine = false;
                        }
                        srcSR.Close();
                    }
                    toolStripButton2.Enabled = activetoolStripButton2(listView1);
                    zapiszToolStripMenuItem.Enabled = toolStripButton2.Enabled;
                    
                }
                catch (Exception errorMsg)
                {
                    MessageBox.Show(errorMsg.Message,"Błąd odczytu pliku",MessageBoxButtons.OK,MessageBoxIcon.Error);
                }
             updateSelectedRecord();

Zapis:

bool firstLine = true;
                using (SaveFileDialog zapisaniepliku = new SaveFileDialog())
                try
                {
                    zapisaniepliku.InitialDirectory = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
                    zapisaniepliku.DefaultExt = "csv";
                    zapisaniepliku.Title = "Zapisz plik";
                    zapisaniepliku.FileName = "baza_danych";
                    zapisaniepliku.Filter = "Dokumenty (*.csv)|*.csv";
                    if (zapisaniepliku.ShowDialog() == DialogResult.OK)
                    {
                        FileStream destFS;
                        destFS = new FileStream(zapisaniepliku.FileName, FileMode.Create);
                        StreamWriter destSW = new StreamWriter(destFS, System.Text.Encoding.Default);
                        if (firstLine == true)
                        {
                            firstLine = false;
                            destSW.Write(this.listView1.Columns[0].Text+",");
                            destSW.Write(this.listView1.Columns[1].Text+",");
                            destSW.Write(this.listView1.Columns[2].Text+",");
                            destSW.Write(this.listView1.Columns[3].Text+",");
                            destSW.Write(this.listView1.Columns[4].Text+"\r\n");
                        }

                        for (int i = 0; i < listView1.Items.Count; i++)
                        {
                            for (int j = 0; j < 5; j++)
                            {
                                if (j != 2)
                                {
                                    destSW.Write(this.listView1.Items[i].SubItems[j].Text);
                                    if (j + 1 < 5)
                                        destSW.Write(",");
                                }
                                else
                                {

                                    destSW.Write(this.listView1.Items[i].SubItems[j].Text);
                                    destSW.Write(",");
                                }


                            }
                            
                            destSW.Write("\r\n");
                        }
                        destSW.Close();
                    }
                }
                catch (Exception errorMsg)
                {
                    MessageBox.Show(errorMsg.Message, "Błąd odczytu pliku", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }

Dodam jeszcze, że program ma z góry określoną liczbę kolumn (pola tj. imię, nazwisko, adres, telefon, email).

Wyżej pokazany łobuz wysypał się na wpisaniu znaków specjalnych. Będę niezmiernie wdzięczny jeśli ktoś nakieruje mnie na dobrą drogę.

0

Spróbuj coś takiego:

static void QueryCsv()
{

    OleDbConnection cn = new OleDbConnection (@"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=
C:\;Extended Properties=""Text;HDR=No;FMT=Delimited""");
    OleDbCommand cmd = new OleDbCommand(@"SELECT * FROM C:\Temp\teams.csv", cn);
    OleDbDataAdapter da = new OleDbDataAdapter(cmd);

    cn.Open();

    DataTable dt = new DataTable();

    da.Fill(dt);

    var teams = from r in dt.AsEnumerable()
                where r.Field(2) == "NL"
                select new { City = r.Field(0), TeamName= r.Field(1) };

    foreach (var team in teams)
    {
        // Tutaj zamiast Console... da to Twoje ListView i już. ;)
        Console.WriteLine(String.Format("The {0} {1}",team.TeamName,team.City));
    }

    Console.ReadLine();

    cn.Close();

}

Dla przykładowego pliku CSV który wygłąda tak:

"Mets","New York","NL"
"Marlins","Florida","NL"
"Orioles","Baltimore","AL"
"Pirates","Pittsburgh","NL"
"Phillies","Philadelphia","NL"

Źródło: http://rudesyle.wordpress.com/2008/01/28/using-linq-to-query-a-csv-file/

Można by to zrobić szybciej i zgrabniej: http://stackoverflow.com/questions/5116604/read-csv-using-linq
Ale pojawia się Split więc rozumiej jest on nie mile widziany. :P

0

@Azarien: no ale pokaż przykładowy plik danych, bo nikomu nie będzie się chciało zgadywać…

Załączam archiwum z przykładowym plikiem CSV oraz projekt.

Dzięki DibbyDum, spróbuję ogarnąć to z tym OleDb, niestety wysypuje mi błąd przy tworzeniu tabeli. Zmierzę się z tym jutro, dziś już z lekka nie kontaktuję.

Jeszcze jedno pytanie do ogółu, czy ktoś z Was korzystał z http://www.codeproject.com/Articles/9258/A-Fast-CSV-Reader ? Też poległem na wykorzystaniu tego. Czuję się z lekka sfrustrowany ponieważ nic dzisiaj nie poszło po mojej myśli z tym ustrojstwem. ;(

1 użytkowników online, w tym zalogowanych: 0, gości: 1