Reputation: 85
i have a CSV file with ; separator. Data are double type e.g: 0.66985787869876;0.254886543778;475.36552366\n 0.454585787869854;0.484254886543755578;512.36552374\n
Updated code after the answer of CyberSpock. My problem seems to be the fgets that have (shows with printf) the first value only rather than the full line
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
double LoadCSV(double *Tab[][100])
{
char* token;
double intermed;
char* test;
FILE *fp;
fp = fopen("file.csv","r");
char line[128];
int i=0, j=0;
while (fgets(line, sizeof(line), fp) != NULL)
{
for (token = strtok(line,";"); token != NULL ; token = strtok(NULL, ";"))
{
token=strchr(token, "\n") ;
intermed=atof(token);
printf("%f", intermed);
*Tab[i][j]= intermed;
i++;
}
printf("%f", *Tab[3][j]);
j++;
}
//fclose(fp);
return 0;
}
int main(){
double Tab[50][100]; //max fixed size
int k=0;
int l=0;
LoadCSV(Tab);
while (k< 4)
{
printf("Tab = %f", Tab[k][l]);
k++;
}
}
OLD POST The size of the input CSV can be different each time: one time 3 columns and another 46 columns.
Then I think that I can't use scanf like scanf(file, "%f";"%f";"%f", varA, varB, VarC); Because vars are fixed one time.
Although i try this code but i have a problem with the var named c:
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
double TabInput[100]; //max fixed size
double LoadCSV()
{
FILE *fp;
int c;
char cumulate[100];
int i=0;
fp = fopen("file.csv","r");
if(fp == NULL)
{
perror("Error in opening file");
}
while(1)
{
c = fgetc(fp);
if( feof(fp) )
{
break ;
}
if (c != ";" || c != "\n")
{
printf("%s",c);//*************PROBLEM C is an int
strcat(cumulate, d);//********PROBLEM THERE
}
else
{
TabInput[i]= atof(cumulate); //str to double
i++;
}
if (c == "\n")
{
break ;
}
}
fclose(fp);
//return(TabInput);
}
int main(){
int j=0;
LoadCSV();
while (j< 4)
{
printf("Tab = %f", TabInput[j]);
j++;
}
}
Thank's for your help. Best.
Upvotes: 1
Views: 5659
Reputation: 36082
use strtok instead
char line[128];
fgets( line, sizeof(line), fp );
for (char* token = strtok( line, ";"); token != NULL; token = strtok(NULL, ";"))
{
TabInput[i++] = atof(token);
}
So you read one line at a time and then parse the line using strtok
.
strtok
splits up the string line
into several strings and returns pointers to \0 terminated strings. the only thing you need to do is to convert the string to float/double using atof. in each iteration of the for loop token will point to a new string in line
.
In order to split a CSV file into rows and columns you could do something like this
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAXROWS 10
#define MAXCOLS 5
int main()
{
int rowIndex = 0;
double rows[MAXROWS][MAXCOLS] = {{0,0}};
char line[128];
char* token = NULL;
FILE* fp = fopen("myfile.csv","r");
if (fp != NULL)
{
while (fgets( line, sizeof(line), fp) != NULL && rowIndex < MAXROWS)
{
int colIndex = 0;
for (token = strtok( line, ";"); token != NULL && colIndex < MAXCOLS; token = strtok(NULL, ";"))
{
rows[rowIndex][colIndex++] = atof(token);
}
rowIndex++;
}
fclose(fp);
}
for (int i = 0; i < rowIndex; ++i)
{
for (int j = 0; j < MAXCOLS; ++j)
printf("%10.4lf", rows[i][j]);
putchar('\n');
}
return 0;
}
Upvotes: 3