2014-11-12 2 views
0

Я пишу программу, которая использует аргументы командной строки для получения имени текстового файла от пользователя. Текстовый файл очень простой CSV-файл, такие как:Чтение текстового файла в массив символов в c

Bob's experiment,12,14,15,16 
Mary's experiment,16,15,18 

Я просто хочу, чтобы напечатать название эксперимента, то среднее значение всех числовых значений. Я пытаюсь сделать это, поместив все числа и запятые в массив символов, и я не знаю, где я ошибся.

Это то, что у меня есть:

int main(int argc, char *argv[]) 
    { 
    if(argc == 2) { 
      FILE *txt_file; 
      txt_file=fopen(argv[1], "rt"); 
      char str[4096]; 

      if(!txt_file) { 
        printf("File does not exist.\n"); 
        return 1; 
      } 

      while(!feof(txt_file)){ 
        char s; 
        s = fgetc(txt_file); 

        //prints experiment name 
        if(s != ',' && (!isdigit(s))) { 
          printf("%c", s); 
        } 

        if(isdigit(s) || s == ',') { 
          fgets(str, 4096, txt_file); 
        } 
       } 
      fclose(txt_file); 
      return 0; 
     } 
+0

Что не работает? Каков ваш реальный вопрос? –

+0

Возможно, функция функций strchr и atoi полезна. Используйте atoi, чтобы найти значение первого числа в str, а затем используйте цикл с strchr, чтобы найти следующую запятую. –

+0

Возможный дубликат [вычисления среднего значения из файла CSV в C] (http://stackoverflow.com/questions/26877131/calculating-average-of-values-from-a-csv-file-in-c) – BLUEPIXY

ответ

-1

Я думаю, что это будет делать то, что вы хотите.

#include <stdio.h> 

int main(int argc, char* argv[]) 
{ 
    int n = 0, count = 0, t = 0; 
    if(argc == 2) { 
      FILE *txt_file; 
      txt_file=fopen(argv[1], "rt"); 
      char str[4096]; 

      if(!txt_file) { 
        printf("File does not exist.\n"); 
        return 1; 
      } 

      while(!feof(txt_file)){ 
        char s; 

        s = fgetc(txt_file); 

        //prints experiment name 
        if(s != ',' && (!isdigit(s))) { 
          if(n!=0) { 
           printf("%d\n", n/count); 
           n = 0; 
           count = 0; 
          } 
          printf("%c", s); 
        } 

        if(s == ',') { 
          fscanf(txt_file, "%d", &t); 
          n+=t; 
          count++; 
        } 
       } 
      printf("%d\n", n/count); 
      fclose(txt_file); 
      return 0; 
     } 
} 
+0

Код создает «Исключение с плавающей запятой». –

+0

Между запятыми и числами не должно быть пробелов. – Venkatesh

+0

Проверьте, где вы делитесь на 'count'. Что происходит, когда 'count = 0'? –

0

Есть несколько способов сделать это, но вы должны адаптировать свою входную рутину с типом данными, которые вы читаете из файла. Здесь вы читаете строк данных, поэтому вам следует сфокусироваться на ориентированных на линию процедуры ввода (fgets, getline, или обувная машина scanf). Основной подход состоит в том, чтобы прочитать строку ввода из вашего файла в buffer, а затем проанализировать строку по мере необходимости. Вы можете сделать это, динамически распределяя все необходимое хранилище, или вы можете определить максимальное значение, которое должно быть достаточно большим для обработки ваших данных.

Далее вам нужно будет разобрать buffer чтения из файла, чтобы получить experiment name и каждый из values, связанных с тем, что average может быть вычислен. Опять же, есть много способов сделать это, но strtol предназначен для этой цели. Он принимает pointer в строку для преобразования и возвращает endptr следующему символу, который не является числом. Это позволяет вам считывать значения и устанавливать pointer = endptr+1, что позволяет вам читать следующий номер.

Я собрал эти части в приведенном ниже примере. Он прокомментирован, чтобы помочь вам следовать. Оставьте комментарий, если у вас есть какие-либо дополнительные вопросы:

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 

#define MAXEXPS 256 

int main (int argc, char* argv[]) 
{ 
    if (argc < 2) { 
     fprintf (stderr, "error: insufficient input. Usage %s <filename>\n", argv[0]); 
     return 1; 
    } 

    char *line = NULL;    /* line read from file (getline allocates if NULL) */ 
    size_t n = 0;     /* number of characters to read (0 - no limit)  */ 
    ssize_t nchr = 0;    /* number of characters actually read by getline */ 
    char *p = NULL;     /* pointer to use parsing values from line   */ 
    char *lnp = NULL;    /* second pointer to use parsing values from line */ 
    char *expname[MAXEXPS] = {0}; /* array of MAXEXPS pointers for experiment names */ 
    int expavg[MAXEXPS] = {0};  /* array of MAXEXPS ints to hold averages   */ 
    int val = 0;     /* val returned by each call to strtol    */ 
    int eidx = 0;     /* experiment index         */ 
    int idx = 0;     /* value index          */ 

    FILE *txt_file = fopen(argv[1], "r"); 
    if (!txt_file) { 
     fprintf (stderr, "error: unable to open file '%s'\n", argv[1]); 
     return 1; 
    } 

    while ((nchr = getline (&line, &n, txt_file)) != -1) /* read each line in file */ 
    { 
     p = strchr (line, ',');        /* find first ','   */ 
     *p = 0;            /* set it to null (zero) */ 
     expname[eidx] = strdup (line); /* copy exp name to array (strdup allocates) */ 
     lnp = ++p;           /* set lnp to next char  */ 
     int sum = 0;          /* reset sum to 0   */ 
     idx = 0;           /* reset idx to 0   */ 
     while ((val = (int)strtol (lnp, &p, 10)) != 0 && lnp != p) /* read next number */ 
     { 
      sum += val;          /* add val to sum   */ 
      lnp = ++p;          /* set lnp to next char  */ 
      idx++;           /* inc idx     */ 
     } 
     expavg[eidx++] = (idx > 0) ? sum/idx : 0;   /* calc avg for experiment */ 
    } 

    fclose (txt_file); 

    /* print the averages of experiments */ 
    n = 0; 
    printf ("\n Experiment   Avg\n"); 
    printf (" -----------------------\n"); 
    while (expname[n]) 
    { 
     printf (" %-18s %d\n", expname[n], expavg[n]); 
     n++; 
    } 
    printf ("\n"); 

    /* free all allocated memory  */ 
    n = 0; 
    if (line) 
     free (line); 
    while (expname[n]) 
     free (expname[n++]); 

    return 0; 
} 

выход:

$ ./bin/csvavgfixed dat/csvavg.dat 

    Experiment   Avg 
    ----------------------- 
    Bob's experiment 14 
    Mary's experiment 16 

память выделение/свободное Резюме:

==22148== HEAP SUMMARY: 
==22148==  in use at exit: 0 bytes in 0 blocks 
==22148== total heap usage: 4 allocs, 4 frees, 723 bytes allocated 
==22148== 
==22148== All heap blocks were freed -- no leaks are possible 
==22148== 
==22148== For counts of detected and suppressed errors, rerun with: -v 
==22148== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 2 from 2) 
Смежные вопросы