How to read data from file with fscanf in c-language - arrays

I want to import numbers (40000 in total, space-separated) (format: 2.000000000000000000e+02) with "fscanf" and put it in a 1D-Array. I tried a lot of things, but the numbers I am getting are strange.
What I've got until now:
int main() {
FILE* pixel = fopen("/Users/xy/sample.txt", "r");
float arr[40000];
fscanf(pixel,"%f", arr);
for(int i = 0; i<40000; i++)
printf("%f", arr[i]);
}
I hope somebody can help me, I am a beginner ;-)
Thank you very much!!

Instead of:
fscanf(pixel,"%f", arr);
which is the exact equivalent of this and which read only one single value:
fscanf(pixel,"%f", &arr[0]);
you want this:
for(int i = 0; i<40000; i++)
fscanf(pixel,"%f", &arr[i]);
Complete code:
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE* pixel = fopen("/Users/xy/sample.txt", "r");
if (pixel == NULL) // check if file could be opened
{
printf("Can't open file");
exit(1);
}
float arr[40000];
int nbofvaluesread = 0;
for(int i = 0; i < 40000; i++) // read 40000 values
{
if (fscanf(pixel,"%f", &arr[i]) != 1)
break; // stop loop if nothing could be read or because there
// are less than 40000 values in the file, or some
// other rubbish is in the file
nbofvaluesread++;
}
for(int i = 0; i < nbofvaluesread ; i++)
printf("%f", arr[i]);
fclose(pixel); // don't forget to close the file
}
Disclaimer: this is untested code, but it should give you an idea of what you did wrong.

You need to call fscanf() in a loop. You're just reading one number.
int main() {
FILE* pixel = fopen("/Users/xy/sample.txt", "r");
if (!pixel) {
printf("Unable to open file\n");
exit(1);
}
float arr[40000];
for (int i = 0; i < 40000; i++) {
fscanf(pixel, "%f", &arr[i]);
}
for(int i = 0; i<40000; i++) {
printf("%f", arr[i]);
}
printf("\n");
}

Related

fscanf not reading from a file containing asterisk characters

I tried to read a file containing an empty box of '*', the error message doesn't get printed, so the file is opened, but the scan doesn't work. I tried to print the count variable, and the value of count is 0. I don't really know where the fault is. Please help... Thanks
the file content that I want to read
int openmap(int file_no){
char filename[32];
char mapp[100][100];
int number;
int count;
int x[100];
int nomor = 1;
for(int i = 1; i <= file_no; i++){
sprintf(filename, "map%d.txt", i);
FILE *test = fopen(filename,"r");
if(test)
{
printf("%2d. Map %d\n", nomor, i);
x[nomor-1] = i;
nomor++;
fclose(test);
}else if(!test && i > file_no){
printf("No map available!");
return 1;
}
}
do{
printf("[0 to cancel] [1 - %d]>> ", nomor-1);
scanf("%d", &number);
}while(number < 0 || number > file_no);
if(number > 0){
sprintf(filename,"map%d.txt", x[number-1]);
printf("%s", filename);
FILE *open = fopen(filename, "r");
if(!open){
printf("error");
}
while(!feof){
fscanf(open, "%[^\n]\n", mapp[count]);
count++;
}
fclose(open);
for(int i = 0; i < count ; i++){
printf("%s\n", mapp[i]);
}
}
}
I created a small test program:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void main () {
char mapp[100][100];
int i, count = 0;
char filename[32];
sprintf(filename, "test.txt");
FILE *open = fopen(filename, "r");
if(!open){
printf("error");
}
while(!feof(open)){
fscanf(open, "%[^\n]\n", mapp[count]);
count++;
}
fclose(open);
for(i = 0; i < count ; i++){
printf("%s\n", mapp[i]);
}
}
as far as i can see the only issue you have regarding the relevant section is your while loop condition, you should use: while(!feof(open)) - i tested my solution and it works so it seems that this is the only issue in your solution

Fscanf Seg Error

Working on a project where I have to have a file that is generated numbers. First line is a generated int. Followed by a floats (separate lines). (I'm doing it separate lines because I feel it makes more sense as I have to read it two different ways for the bin packing problems which I need this for... Like one way of reading one at a time and another storing it in an array.. But want to get this down first)
Getting a seg fault when I try to read my file for a float after reading an int. Edit: Error occurs in readOffline.
int randomFunction()
{
FILE *fp;
int i;
fp = fopen("theItems.txt", "w" );
if (fp == NULL)
printf("Error: file can't be opened.\n");
srand(time(NULL) );
int random_number = rand();
printf("Random Number %d\n", random_number);
fprintf(fp,"%d",random_number);
fclose(fp);
fp = fopen("theItems.txt", "a");
int numberOfItems = rand();
printf("NumberOfItems: %d\n",numberOfItems);
for(i = 0; i < 10; i++)
{
fp = fopen("theItems.txt", "a");
float number = (float)rand()/(float)(RAND_MAX);
fprintf(fp,"%f",number);
fprintf(fp,"%s", "\n");
fclose(fp);
}
return numberOfItems;
}
void readOffline( int numberOfItems)
{
FILE *fp;
int n = 0,i;
float nu = 0.00;
fp = fopen("theItems.txt", "r");
if (fp == NULL)
printf("Error: file can't be opened.\n");
fseek(fp,SEEK_SET,0);
fscanf(fp,"%d",&n);
printf("Number read: %d\n", n);
float array[numberOfItems];
// for(i = 0; i < 3; i++)
// {
fscanf(fp,"%f",&nu);
// array[i] = nu;
// }
fclose(fp);
printf("Int:%d\n", n);
int j;
// for(j = 0; j < 3; j++)
// printf("Float Number:%f\n", array[j]);
}
int main()
{
int numberOfItems = randomFunction();
readOffline(numberOfItems);
return 0;
}
Just trying to get an understanding why it causes a seg error when I // it out I can get it to read my int but sometimes it isn't the right int read. But yeah.
Please let me know if I need any more details or need to be more clear anywhere
You have multiple issues in your code:
You open the output file multiple times in randomFunction(), you even leak a stream handle and leave it open.
You do not exit the function when fopen() returns NULL. The rest of the code invokes undefined behavior if fp == NULL.
The same problem is present in readOffline(): if fp == NULL, you should return from the function immediately.
you do not output a linefeed after the first random number in the output file.
you always output 10 random numbers.
most importantly: the random number returned by the randomFunction() is potentially huge, allocating an array with local storage larger than a few megabytes is likely to cause undefined behavior. Try and reduce the maximum random number of values.
Here is a proposed correction:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int randomFunction(void) {
FILE *fp;
int i;
fp = fopen("theItems.txt", "w");
if (fp == NULL) {
printf("Error: file can't be opened.\n");
return -1;
}
srand(time(NULL));
int random_number = rand();
printf("Random Number %d\n", random_number);
fprintf(fp, "%d\n", random_number);
int numberOfItems = 1 + rand() % 100; /* between 1 and 100 */
printf("NumberOfItems: %d\n", numberOfItems);
for (i = 0; i < numberOfItems; i++) {
float number = rand() / (float)(RAND_MAX);
fprintf(fp, "%f\n", number);
}
fclose(fp);
return numberOfItems;
}
void readOffline(int numberOfItems) {
FILE *fp;
int n = 0, i;
fp = fopen("theItems.txt", "r");
if (fp == NULL) {
printf("Error: file can't be opened.\n");
return;
}
fscanf(fp, "%d", &n);
printf("Number read: %d\n", n);
float array[numberOfItems];
for (i = 0; i < numberOfItems; i++) {
if (fscanf(fp, "%f", &array[i]) != 1)
break;
}
fclose(fp);
printf("Int:%d\n", n);
for (int j = 0; j < i; j++) {
printf("Float Number %d: %f\n", j, array[j]);
}
}
int main(void) {
int numberOfItems = randomFunction();
readOffline(numberOfItems);
return 0;
}
Note that I kept your semantics: the random number at the start of the file is not the number of floating point values that follow. I suspect it should be?
I would say that depending on the particular compiler that you are using, then this could be a problem in setting up the actual array. This is (as an example) discussed in Variable Sized Arrays vs calloc in C From the discussions, you should use calloc and free. Another point is that you need to make sure that your value is greater than 3 and not too big. Since the array is only in the local scope of readOffline(), you should not connect it to the variable numberOfItems.
float array[3];
for(i = 0; i < 3; i++)
{
fscanf(fp,"%f",&nu);
array[i] = nu;
}

C Reading numbers from file into array

hey so i m trying to read numbers from text file and put them into an array but ive been getting weird numbers when i try to print them. text file looks like:
45
77
8
...
i guess theres something wrong with the loop i m using but i cant seem to find out what.
thanks for your help!
code:
#define MAX_ARRAY_SIZE 20
int main(int argc, char * argv[])
{
FILE *myFile;
int myArray[MAX_ARRAY_SIZE];
//char filename[32];
//printf("enter filename\n");
//scanf("%s", filename);
myFile = fopen("asdf.txt", "r");
if (!myFile) {
printf("cant open file\n");
return 1;
}
int status;
int i = 0;
while ((status = fscanf(myFile, "%2d", &myArray[i])) == 1 && i < MAX_ARRAY_SIZE - 1) {
++i;
}
fclose(myFile);
int a;
for (a = 0; i < MAX_ARRAY_SIZE; ++i) {
printf("%d ", myArray[i]);
}
printf("\n");
return 0;
}
The problem is in your print loop:
for (a = 0; i < MAX_ARRAY_SIZE; ++i)
There is no guarantee you are reading MAX_ARRAY_SIZE values. Also, if you ar using 'a' as your loop iterator, then you need to use 'a'. Your loop should be:
for (a = 0; a < i; ++a)
printf("%d ", myArray[a]);
You also do not need a field-width in your format-specifier, fscanf(myFile, " %d", &myArray[i])) will do.
Try this
while ((status = fscanf(myFile, "%d\n", &myArray[i])) == 1 && i < MAX_ARRAY_SIZE - 1) {
++i;
}
True... I have not seen print loop code.. Sorry.
Problem is in print loop not fscan, please ignore my answer

How to return an array from a specific function?

I have been working on this function for the past two days and I cant seem to figure it out. The function displayBoard() opens up a text file, in this case "board.txt" and places it into a 1D array. The code was provided by my professor. I made it into a function and tried to return the array board[] so I can manipulate it in main but I am unable to do it, What am I missing?
void displayBoard ()
{
FILE *pInputFile; // file pointer
char board[64]; // the 8x8 board
int i=0; // loop counter
char inputFileName[] = "board.txt";
// Associate the actual file name with file pointer and try to open it
pInputFile = fopen(inputFileName, "r");
// Verify input file was found
if (pInputFile == NULL) {
printf("Attempt to open file %s failed. Exiting ... \n", inputFileName);
exit( -1);
}
// Read from the file into the board. Space in front of %c is important!
while (fscanf(pInputFile, " %c", &board[i]) != EOF) {
i++;
}
fclose(pInputFile); // close input file
// show contents of board
printf("Board is: ");
for (i=0; i<64; i++) {
if (i%8 == 0) {
printf("\n");
}
printf("%c ", board[ i]);
}
printf("\n\n");
return board;
}
int main ()
{
printf(" %s", board); // This is my printf statement to see if I am able to access
// board[] from the function
}
You need to make the method return a char * by declaring the function
char * displayBoard {
...
}
You can not. You have to pass the array you want to modify using pointers and modify it inside the function.
#include <stdio.h>
void function(int b[][10], int m, int n){
int i = 0, j = 0;
for(i = 0; i < m; ++i){
for(j = 0; j < n; ++j){
b[i][j] = i + j;
}
}
}
int main(){
int board[10][10] = {0};
int i = 0, j = 0;
for(i = 0; i < 10; ++i){
for(j = 0; j < 10; ++j){
printf("%d ", board[i][j]);
}
printf("\n");
}
function(board, 10, 10);
for(i = 0; i < 10; ++i){
for(j = 0; j < 10; ++j){
printf("%d ", board[i][j]);
}
printf("\n");
}
return 0;
}
Ok I decided to part my function into 2, one to generate the board and one to to display the board, so I can just use displayBoard() whenever I want to re-display it in main.
void generateBoard (char board[]){
FILE *pInputFile; // file pointer
int i=0; // loop counter
char inputFileName[] = "board.txt";
// Associate the actual file name with file pointer and try to open it
pInputFile = fopen(inputFileName, "r");
// Verify input file was found
if( pInputFile == NULL) {
printf("Attempt to open file %s failed. Exiting ... \n", inputFileName);
exit( -1);
}
// Read from the file into the board. Space in front of %c is important!
while( fscanf(pInputFile, " %c", &board[ i]) != EOF) {
i++;
}
fclose( pInputFile); // close input file
}
void displayBoard (char board[]){
// show contents of board
printf("Board is: ");
int i;
for( i=0; i<64; i++) {
if( i%8 == 0) {
printf("\n");
}
printf("%c ", board[ i]);
}
printf("\n\n");
}
I have an update on my function, I am a first time user of this site so im not sure if I should be posting it here or on my OP. This is what I came up with
char* displayBoard (char board[]){
FILE *pInputFile; // file pointer
int i=0; // loop counter
char inputFileName[] = "board.txt";
// Associate the actual file name with file pointer and try to open it
pInputFile = fopen(inputFileName, "r");
// Verify input file was found
if( pInputFile == NULL) {
printf("Attempt to open file %s failed. Exiting ... \n", inputFileName);
exit( -1);
}
// Read from the file into the board. Space in front of %c is important!
while( fscanf(pInputFile, " %c", &board[ i]) != EOF) {
i++;
}
fclose( pInputFile); // close input file
// show contents of board
printf("Board is: ");
for( i=0; i<64; i++) {
if( i%8 == 0) {
printf("\n");
}
printf("%c ", board[ i]);
}
printf("\n\n");
return board;
}
When you write code returning results in an array, it is better to let the caller provide the array in which the code should return its results than to let the code allocate itself an array.
The reason for this is that pointer ownership transfers make it hard to reason about memory management, so it is better to keep their amount at a minimum.

Error when trying to read in numbers from txt file in C

I am new to C programming and I am getting a THREAD 1: EXC_BAD_ACCESS(code = 1, address 0x68)
when I run my program. The purpose of my code is to read from a txt file that contains positive and negative numbers and do something with it.
#include <stdio.h>
int main (int argc, const char * argv[]) {
FILE *file = fopen("data.txt", "r");
int array[100];
int i = 0;
int num;
while( fscanf(file, "%d" , &num) == 1) { // I RECEIVE THE ERROR HERE
array[i] = num;
printf("%d", array[i]);
i++;
}
fclose(file);
for(int j = 0; j < sizeof(array); j++){
printf("%d", array[j]);
}
}
After
FILE *file = fopen("data.txt", "r");
Say
if(file == 0) {
perror("fopen");
exit(1);
}
Just a guess, the rest of the code looks ok, so likely this is the problem.
Also worth noting that you might have more than 100 numbers in your file, in which case you will blow past the size of your array. Try replacing the while loop with this code:
for (int i = 0; i < 100 && ( fscanf(file, "%d" , &num) == 1); ++i)
{
array[i] = num;
printf("%d", array[i]);
}
Do you have the file "data.txt" created and local?
touch data.txt
echo 111 222 333 444 555 > data.txt
Check that your file open succeeded.
Here is a working version,
#include <stdio.h>
#include <stdlib.h> //for exit
int main (int argc, const char * argv[])
{
FILE *fh; //reminder that you have a file handle, not a file name
if( ! (fh= fopen("data.txt", "r") ) )
{
printf("open %s failed\n", "data.txt"); exit(1);
}
int array[100];
int idx = 0; //never use 'i', too hard to find
int num;
while( fscanf(fh, "%d" , &num) == 1) { // I RECEIVE THE ERROR HERE
array[idx] = num;
printf("%d,", array[idx]);
idx++;
}
printf("\n");
fclose(fh);
//you only have idx numbers (0..idx-1)
int jdx;
for(jdx = 0; jdx<idx; jdx++)
{
printf("%d,", array[jdx]);
}
printf("\n");
}

Resources