2016-04-25 7 views
0

Ich habe eine TXT-Datei, die eine unbekannte (jedes Mal) Anzahl von Zeilen enthält. In jeder Zeile gibt es 4 Floats, getrennt durch das Leerzeichen.Lesen Sie eine Zeile aus einer TXT-Datei und teilen Sie sie in Gleitkommazahlen.

Mein Problem ist, dass ich keine Ahnung habe, wie man jedes float von den anderen in jeder Zeile trennt und es an der richtigen Stelle der Matrix platziert.

Dies ist der Code, den ich bisher gemacht habe (er geht jede Zeile zum ersten Mal durch, so dass ich die Anzahl der Zeilen kenne, um meine Matrix zu deklarieren, gibt aber nur den ersten der vier Werte zurück):

#include <stdio.h> 

FILE *fr; 

main() { 

    float time, xaxis, yaxis, zaxis; 
    char line[40]; 
    int n = 0; 

    fr = fopen ("walk-after-excel.txt", "r"); 

    while (fgets (line, 80, fr) != NULL) { 
     n++; 
    } 
    rewind (fr); 
    printf ("%u", n); 
    float values[n][4]; 
    int i; 
    for (i = 0; i < n; i++) { 
     values[i][0] = 0; 
     values[i][1] = 0; 
     values[i][2] = 0; 
     values[i][3] = 0; 
    } 
    while (fgets (line, 80, fr) != NULL) { 
     sscanf (line, "%f", &time); 
     printf ("%f\n", time); 
    } 
    for (i = 0; i < n; i++) { 
     printf ("%f, %f, %f, %f \n", values[i][0], values[i][1], values[i][2], 
       values[i][3]); 
    } 
    printf ("%u", n); 
    fclose (fr); 
} 

Jede Hilfe wird sehr geschätzt.

+0

Sie müssen zeigen, was Sie bisher selbst gemacht haben? –

+0

Nicht viel, ich lese gerade die .txt-Datei durch und drucke sie aus. Verwenden von Code, der im Internet verfügbar ist. Ich bin wirklich in der Dunkelheit mit dem, was ich tun muss – user2149122

+0

Sie können 'scanf()' verwenden, um jedes Float in eine andere Variable zu lesen. Verwenden Sie 'malloc()' und 'realloc()', um ein Array dynamisch zuzuweisen und es nach Bedarf zu vergrößern. – Barmar

Antwort

2

Sie haben hier ein paar Probleme bekommen:

  1. In der modernen C, Sie immer einen Rückgabetyp für Ihre Funktionen, einschließlich main angeben sollen. Dies bedeutet, dass Sie int main(void) { ... } verwenden sollten.
  2. Sie geben eine Puffergröße von 40 Bytes an, aber Sie sagen fgets, dass Ihr Puffer 80 Bytes ist, das ist ein riesiges No-No. Sie dürfen den Funktionen niemals vorgeben, dass Ihr Puffer größer ist, als er wirklich ist, sonst werden Sie auf Pufferüberläufe stoßen (die in der realen Welt zu ausnutzbaren Sicherheitslücken werden können). Da Sie einen Array-Typ verwenden, können Sie einfach sizeof line an fgets übergeben, und dann ist es egal, wenn Sie die Größe von line ändern, es wird immer den richtigen Wert an fgets übergeben.
  3. Sie scannen nur die erste Variable jeder Zeile ein, deshalb sehen Sie nur den ersten Wert jeder Zeile.
  4. Sie deklarieren ein VLA (Variable Length Array). Diese sind nützlich, aber in den meisten (wenn nicht allen) Implementierungen verbrauchen VLAs Stack-Speicherplatz, der begrenzt ist. Wenn Sie versuchen, ein zu großes VLA zu deklarieren, wird Ihre Anwendung wahrscheinlich zum Absturz gebracht. Der Weg dazu ist malloc oder calloc zu verwenden. calloc ist wie malloc, außer dass es automatisch den zugewiesenen Speicher für Sie ausfüllt.
  5. Ihre fr Variable muss nicht global sein.

Da jede Zeile der Datei einen “ Datensatz repräsentiert ”, könnten Sie eine Struktur, wie diese erklären:

struct record 
{ 
    float time; 
    float xaxis; 
    float yaxis; 
    float zaxis; 
}; 

Auch, weil es eine unbekannte Anzahl von Datensätzen in der Datei sind, gibt es mindestens zwei Möglichkeiten, genügend Speicher für alle Datensätze zuzuweisen. Eine besteht darin, zuerst alle Zeilen in der Datei zu zählen und dann den Speicher basierend auf der Anzahl der Zeilen zuzuweisen. Dies hat den Vorteil, dass Sie genau die richtige Speichermenge zuweisen, die Sie benötigen, aber Sie müssen die Datei zweimal lesen. Eine andere Möglichkeit besteht darin, genügend Speicher zuzuweisen, um eine ordentliche Anzahl von Datensätzen zu speichern und dann “ diese Speicherzuweisung zu erweitern, wenn sich herausstellt, dass sie nicht groß genug ist. Dies hat den Vorteil, dass Sie die Datei nur einmal lesen müssen, aber am Ende möglicherweise Speicherplatz verschwenden.

Sie verwenden bereits die “ gezählte Anzahl der Datensätze zuerst zuteilen später ” Ansatz, so brauchen wir nur die oben genannten Probleme zu beheben.

#include<stdio.h> 

struct record 
{ 
    float time; 
    float xaxis; 
    float yaxis; 
    float zaxis; 
}; 

int main(void) 
{ 
    FILE *fr; 
    char line[80]; 
    int n = 0; 

    fr = fopen ("walk-after-excel.txt","r"); 
    if (fr == NULL) 
    { 
     printf("Couldn't open file!\n"); 
     return 1; 
    } 

    while(fgets(line, sizeof line, fr) != NULL) 
    { 
     n++; 
    } 
    rewind(fr); 
    printf("%d",n); // use %d for int types 

    struct record *records = calloc(n, sizeof(struct record)); 

    for (int i = 0; i < n; i++) 
    { 
     fgets(line, sizeof line, fr); 

     sscanf(line, "%f %f %f %f", &records[i].time, &records[i].xaxis, &records[i].yaxis, &records[i].zaxis); 
    } 

    // records now contains all the data in the file! 

    // to access the 5th line's xaxis value, use: 
    printf("%f\n", records[4].xaxis); 
    // (remember that arrays in C are 0-based) 

    // when you are done, free the memory allocated by malloc/calloc with free() 

    free(records); 

    fclose(fr); 
} 
+0

das sieht wirklich sehr ähnlich aus, was ich brauche, aber es bekommt immernoch nur den ersten der 4 Floats. Ich habe eine for-Schleife hinzugefügt, um die Datensätze zu drucken, und ich bekomme nur die erste Zahl von meinen Floats. für (i = 0; i user2149122

+0

Eine Zeile in der TXT-Datei sieht folgendermaßen aus: 205 \t -2,3080597 \t 3,5524445 \t 11,668289 – user2149122

+0

Ich habe das Problem gefunden. In meiner .txt-Datei hatte floats "," anstelle von ".". – user2149122