Nur bestimmte Zeilen aus einer CSV einlesen - [C]

blub11

Mitglied
Hallo,
ich möchte aus einer .csv-Datei nur eine bestimmte Anzahl an Zeilen auslesen, z.B. ab Zeile 5 die nächsten 16 Zeilen (da dort drüber noch andere Sachen stehen).

Wie könnte man das ((wenn möglich mit fgets)) realiseren?

Grüße
 
Hi

Um die ersten vier Zeilen zu überspringen, musst du eben viermal fgets aufrufen.
Oder alles buchstabenweise mit fgetc durchgehen und mitzählen, wieviel Zeilenumbrüche dabei waren (nach dem vierten eben aufhören).

Wirklich in der Datei herum-"springen" kann man nur, wenn man die Byteposition weiß.
zB zum insgesamt 123. Byte, oder Byte Nummer 456 ...etc
Wenn alle Zeilen der CSV-Datei gleichviel Zeichen hätten (und damit auch gleichviel Byte), könnte man sich ja noch ausrechnen, bei welcher Bytenummer die fünfte Zeile beginnt. Aber man kann sich bei csv leider nicht darauf verlassen, das alles gleich lang ist.

Was du schon machen kannst, wenn du wieder zurück willst: Zum Dateianfang springen.
Wenn deine FILE*-Variable datei heißt, würde das so ausschauen:
C++:
fseek(datei,0,SEEK_SET);

Gruß
 
meinst du mit dem 4x fgets aufrufen das ungefähr so?:
Code:
for(i=0;i<4;i++){
    fgets(blablub[i],100,datei);
    }


Aber eine Frage hätte ich noch:
ist es auch möglich z.b dann mit fgets auch nur die 2. und 3. spalte einzulesen?
Ich hab hier mal nen Screenshot von der CSV angehängt. Also ich möchte nur die Ergebnisse wieder einlesen können (2. + 3. Spalte), am besten wieder in ein zweidimensionales Array:
Code:
int arrayergebnisse_r1[24][2]
 

Anhänge

  • Unbenannt-2.jpg
    Unbenannt-2.jpg
    88,2 KB · Aufrufe: 61
Zuletzt bearbeitet:
Zum Ersten: Wenn blablub[i] ein min. 100 Zeichen langer String ist, ist das ok.

Zum Zweiten:
Lies eine Zeile als String ein und such den ersten Srichpunkt.
Bis dorthin ist es der Mannschaftsname
Von dort weg kannst du sscanf auf den String loslassen

Bsp:
C++:
FILE *datei;
char string[1024];
int k,a,b;

...

for(...)
{
    fgets(string,1024,datei);
    k=0;
    while(string[k]!=';')k++;
    string[k]='\0';
    printf("Mannschaften: ");
    puts(string);
    sscanf(&string[k+1],"%d;%d",&a,&b);
    printf("Ergebnis: %d:%d\n\n",a,b);
}

Und sowas in der Art für jede Zeile der Datei.

Gruß
 
warning: passing argument 1 of 'fgets' makes pointer from integer without a cast
note: expected 'char *' but argument is of type 'char'

d.h. ich muss noch ein "&" Zeichen bei fgets vor das Zielarray setzen? Dann funktioniert es. Denn fgets erwartet einen Pointer, richtig?
Code:
_CRTIMP char* __cdecl __MINGW_NOTHROW	fgets (char*, int, FILE*);

Danke! :)

Edit: Noch eine Frage: Weißt du vielleicht, warum er bei der Ausgabe der Mannschaften immer eine Leerzeile mehr macht?
 

Anhänge

  • Unbenannt-2.jpg
    Unbenannt-2.jpg
    72,2 KB · Aufrufe: 60
Zuletzt bearbeitet:
Hi.
d.h. ich muss noch ein "&" Zeichen bei fgets vor das Zielarray setzen?
Eigentlich nicht.
Dann funktioniert es. Denn fgets erwartet einen Pointer, richtig?
Ja, aber string ist bereits ein Zeiger (bzw. kann implizit in einen Zeiger gewandelt werden). Vermutlich hast du soetwas geschrieben?
C:
fgets(string[0], 1024, datei);
Edit: Noch eine Frage: Weißt du vielleicht, warum er bei der Ausgabe der Mannschaften immer eine Leerzeile mehr macht?
Weil im printf nunmal 2 \n Zeichen stehen? Oder was meinst du?

Gruß
 
Hi!
Zum Ersten: Ja das hab ich getan.

Zum Zweiten: Also ich meine nicht die Absätze (/n), sondern die Leerzeilen bei der Ausgabe zwischen
"Mannschaften:" und den Mannschaftsnamen, die darauf folgen. Nach dem Doppelpunkt gibt es in jeder Zeile eine Leerstelle mehr und so verschiebt sich alles mit der Zeit nach Rechts. Wie man gut auf dem Screenshot in meinem letzten Post erkennen kann.

Also ich bin da draus nicht schlau geworden. Könnte das Problem beim Einlesen liegen?

Grüße
 
Hi

Zum Ersten: Das [0] gehört weg. Siehe meinen Code oben.
string[0] ist nur der erste Buchstabe.
fgets ist aber dafür gemacht, einen ganzen String einzulesen und kann mit Einzelbuchstaben nichts anfangen.

Zum Zweiten: Das sind dann wohl eher Leerspalten statt Zeilen.
Zeig vllt. einmal den aktuellen Code. Sind in der csv-Datei sicher keine Leerzeichen drin, die das verursachen können?
 
Code:
.......
 //WENN NUR RUNDE 1 vorhanden

    if(runde==1){

        //überspringt die ersten 4 Zeilen
        for(i=0;i<3;i++){
            fgets(&speicher[i],1024,turnierliste);
        }

    //liest ab der 4. Zeile die nächsten 24 ein
        for(i=0;i<24;i++){                           //speichert jede Zeile einmal in einem String
        fgets(&speicher[i],1024,turnierliste);

            while(speicher[k]!=';'){                //wenn ";" im string gefunden wird (d.h. nach Mannschaftsname), wird der string mit "\0" abgeschlossen
                k++;
            }
            speicher[k]='\0';
            strcpy (einteilung_r1[k],speicher);         //eingelesene Mannschaftseinteilung im string "speicher" wird in array kopiert
            printf("Mannschaften: %s\n", einteilung_r1[k]); //zum TEST
            sscanf(&speicher[k+1],"%d;%d",&arrayergebnisse_r1[i][0],&arrayergebnisse_r1[i][1]); //nach der Mannschaft, ist das nächste Zeichen die erste Zahl vom Ergebnis, dann ; und dann die letzte Zahl vom Ergebnis
            printf("Ergebnis: %d:%d\n\n",arrayergebnisse_r1[i][0],arrayergebnisse_r1[i][1]); //zum TEST
        }
........

EDIT: Ich hab den Fehler..Wie du schon meintest. Ich hatte, wie du oben sehen kannst,
Code:
fgets(&speicher[i],1024,turnierliste);
hingeschrieben...Ist ja auch kompletter Schwachsinn, speicher ist ja nen string und kein array..
Das &-Zeichen hab ich jetzt mittlerweile wieder rausgenommen, da er nun (nach dem Entfernen von dem speicher[i]) das wieder angemeckert hat..

Jetzt funktioniert die Ausgabe :)
 
Zuletzt bearbeitet:
Hi

string ist schon auch ein char-Array (und ein String - ist das Gleiche :) )

Aber wie du ja gemerkt hast, wird bei &...i erst beim i-ten Buchstaben das Einlesen begonnen.
Und weil i durch die for-Schleife immer eins raufgeht, kommt dann sowas raus...

Schön, dass es jetzt funktioniert :)

Gruß
 
Zuletzt bearbeitet:
Zurück