Reputation: 118
Despite the numerous examples on here I can't seem to get this working...
I have a text file, containing many rows, each row has three (int) values separated by a single space. For example:
1 0 0
0 0 0
1 0 1
0 0 2
1 0 2
I am trying to read this into a 2d array.
My code so far:
int main(void)
{
char c;
int i = 0;
int maxLines = 18;
char lines[maxLines][BUFSIZ];
FILE *fp = fopen("inputs/control.txt", "r");
if (fp == 0)
{
fprintf(stderr, "failed to open inputs/control.txt\n");
exit(1);
}
char buffer[maxLines];
while (i < maxLines && fgets(buffer[i], sizeof(buffer[0]), fp))
{
sscanf (buffer, "%d %d %d", &lines[i][0], &lines[i][1], &lines[i][2]);
i++;
}
fclose(fp);
return 0;
}
Can someone provide advice how I can develop this further so that each value in the row is stored in a separate array index? In my example above, we would store something like:
lines[0][0] = 1
lines[0][1] = 0
lines[0][2] = 0
and so on.....
Currently it stores the entire row in a single array pos.
As you can probably tell I'm a C noob, any help would be fantastic!
Upvotes: 2
Views: 4451
Reputation: 84561
You were well on your way, you just had problems thinking you were reading a character array instead of an array of signed characters (which could be changed to int, etc) Here is your example:
#include <stdio.h>
#define MAXB 32
#define MAXL 18
#define MAXD 3
int main(void)
{
int i = 0;
int numlines = 0;
char buf[MAXB] = {0};
char lines[MAXL][MAXD];
FILE *fp = fopen("inputs/control.txt", "r");
if (fp == 0)
{
fprintf(stderr, "failed to open inputs/control.txt\n");
return 1;
}
while (i < MAXL && fgets (buf, MAXB - 1, fp))
{
if (sscanf (buf, "%hhd %hhd %hhd", &lines[i][0], &lines[i][1], &lines[i][2]) == 3)
i++;
}
fclose(fp);
numlines = i;
int j = 0;
for (i = 0; i < numlines; i++)
for (j = 0; j < MAXD; j++)
printf (" line[%2d][%2d] : %hhd\n", i, j, lines[i][j]);
printf ("\n");
return 0;
}
Output
$ ./bin/read_array_a3
line[ 0][ 0] : 1
line[ 0][ 1] : 0
line[ 0][ 2] : 0
line[ 1][ 0] : 0
line[ 1][ 1] : 0
line[ 1][ 2] : 0
line[ 2][ 0] : 1
line[ 2][ 1] : 0
line[ 2][ 2] : 1
line[ 3][ 0] : 0
line[ 3][ 1] : 0
line[ 3][ 2] : 2
line[ 4][ 0] : 1
line[ 4][ 1] : 0
line[ 4][ 2] : 2
Note: char lines[MAXL][MAXD];
is fine, you just must understand that each element is restricted to an 8-bit signed value, meaning values between -128 < val < 127
. You can make them int
if you need to store larger values.
Upvotes: 3
Reputation: 650
Use scanf
. Example:
#include <stdio.h>
int main(int argc, char *argv[]) {
int i, j;
int lines[18][3];
i = 0;
while (
i != sizeof(lines) / sizeof(lines[0])
&& 3 == scanf("%i %i %i", lines[i] + 0, lines[i] + 1, lines[i] + 2)
) {
i++;
}
for (j = 0; j !=i; j++) {
printf("%i %i %i\n", lines[j][0], lines[j][1], lines[j][2]);
}
return 0;
}
Note that the input is read from stdin (use fscanf
for more flexibility), meaning that the snippet above must be called as ./a.out < data.txt
.
Upvotes: 3
Reputation: 1392
Using fgets you are reading the whole line from the file. You will need to then parse this line to extract individual numbers and store them into the array. In the while loop you can read the line in a buffer and then use something like strtok/sscanf to parse each number.
Upvotes: 2