Hello.. im having a problem with my code.. when i save a file, then choose another variable and load the file, then try to display it, all that it display are garbage values.. i know the problem is either in function save_file or function load_file.. can anyone please help me..

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

#define max 20

typedef struct
{
	 char LN[16];
	 char FN[24];
	 char MI;
}name;

typedef struct
{
	 unsigned long ID;
	 name n;
	 char course[8];
	 int year;
}studrec[max];

void save_file(studrec s, int n)
{
	 FILE *fp;
	 char filename[30];
	 int ctr;

	 printf("What is the name of the file? ");
	 flushall();
	 gets(filename);

	 if((fp = fopen(filename, "wb")) == 0)
	 {
	printf("Cannot write file");

	 }
	 for(ctr = 0; ctr < n; ctr++)
	fwrite(&(s[ctr]), sizeof(studrec), 1, fp);

	 printf("File Saved");
	 fclose(fp);
	 getch();
	 clrscr();
}

void load_file(studrec r)
{
	 FILE *fp;
	 int ctr;
	 char filename[30];

	 printf("What is the filename? ");
	 flushall();
	 gets(filename);
	 if((fp = fopen(filename, "rb")) == 0)
	 {
	printf("File does not exist");

	 }
	 for(ctr = 0; fp == 0; ctr++)
	fread(&(r[ctr]), sizeof(studrec), 1, fp);

	 printf("File Loaded");
	 getch();
	 clrscr();
}

I sense a problem here in your load file function :

for(ctr = 0; fp == 0; ctr++)
            fread(&(r[ctr]), sizeof(studrec), 1, fp);

You can correct it as

size_t c;
for(ctr = 0; c != 0; ctr++)
	c=fread(&(r[ctr]), sizeof(studrec), 1, fp);

Above code will take one extra loop to find the end so better

size_t c;
for(ctr = 0;; ctr++)
{
	c = fread(&(r[ctr]), sizeof(studrec), 1, fp);
        if(!c) break;
}

There are far better ways,this is just the least modification of your code.:)

And sorry salem this is happening second time with me today when I begin writin there would be no post and when I post it there would be a reply already...and we cant delete any post made :(

Comments
Don't sweat it, sometimes I'm 3rd or 4th - it's all good :)

most of these trifling problems will go away when you throw away the P.O.S. Borland/Turbo compiler and get a real C/C++ compiler like CodeBlocks or Bloodshed Dev C++.

these GCC-based, standard C compilers wont let you use worthless functions like flushall(), obsolete libraries like conio.h, and will complain heartily if you try and hang yourself by using gets()

.

@Salem:
Im using borland c
fp == 0 in for loop of function load_file is supposed to find the end of file.. I don't know how to do it so I tried that.
Please help me find a better way..:)

@csurfer
I tried the modified code and it work the first time but when I close the program and run it again and load the file that I saved in the first program, it displays garbage values.:(

Post in your code or else attach the file.

I told you earlier itself that was just to show you the implementation.Thats it you need to research the things and work out for yourself. We here at Daniweb just show you the way we don't give you every details :)

ok here it is..

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

#define max 20

typedef struct
{
	 char LN[16];
	 char FN[24];
	 char MI;
}name;

typedef struct
{
	 unsigned long ID;
	 name n;
	 char course[8];
	 int year;
}studrec[max];

void input(studrec s, int n);
void view(studrec s, int n);
void save_file(studrec s, int n);
void load_file(studrec r);

void input(studrec s, int n)
{
	 int ctr;

	 for(ctr = 0; ctr < n; ctr++)
	 {
	printf("Input student %d's Last Name [enter] First Name [enter] Middle Initial [enter]: \n", ctr + 1);
	flushall();
	gets(s[ctr].n.LN);
	flushall();
	gets(s[ctr].n.FN);
	scanf("%c", &s[ctr].n.MI);

	printf("What is student %d's ID number? ", ctr + 1);
	scanf("%d", &s[ctr].ID);

	printf("What is student %d's course? ", ctr + 1);
	flushall();
	gets(s[ctr].course);

	printf("What is student %d's year? ", ctr + 1);
	scanf("%d", &s[ctr].year);

	printf("\n");
	 }
}

void save_file(studrec s, int n)
{
	 FILE *fp;
	 char filename[30];
	 int ctr;

	 printf("What is the name of the file? ");
	 flushall();
	 gets(filename);

	 if((fp = fopen(filename, "wb")) == 0)
	 {
	printf("Cannot write file");

	 }
	 for(ctr = 0; ctr < n; ctr++)
	fwrite(&(s[ctr]), sizeof(studrec), 1, fp);

	 printf("File Saved");
	 fclose(fp);
	 getch();
	 clrscr();
}

void load_file(studrec r)
{
	 FILE *fp;
	 int ctr;
	 char filename[30];
	 size_t c;

	 printf("What is the filename? ");
	 flushall();
	 gets(filename);
	 if((fp = fopen(filename, "rb")) == 0)
	 {
	printf("File does not exist");

	 }
	 for(ctr = 0; c != 0; ctr++)
	c=fread(&(r[ctr]), sizeof(studrec), 1, fp);

	 printf("File Loaded");
	 getch();
	 clrscr();
}

void view(studrec s, int n)
{
	 int ctr;

	 for(ctr = 0; ctr < n; ctr++)
	 {
	printf("%s, %s %c.\n", s[ctr].n.LN, s[ctr].n.FN, s[ctr].n.MI);
	printf("%d\n", s[ctr].ID);
	puts(s[ctr].course);
	printf("%d\n", s[ctr].year);
	printf("\n");
	 }
}

void main(void)
{
	  studrec s, r;
	  char ans;
     int quit = 0, n;

     clrscr();

     do
	  {
	 printf("Press\nI for Input\nS to save file\nL to load a file\nV to view\nQ to quit\n");
	 ans = getch();
	 clrscr();

	 if(ans == 'I' || ans == 'i')
	 {
	     printf("How many records? ");
		  scanf("%d", &n);
	     clrscr();

	     input(s, n);
		  clrscr();
	 }
	 else if(ans == 'S' || ans == 's')
	     save_file(s, n);
	 else if(ans == 'L' || ans == 'l')
	 {
		  load_file(r);
	     view(r, n);
	 }
	 else if(ans == 'V' || ans == 'v')
	 {
	     view(s, n);
		  getch();
		  clrscr();
	 }
	 else if(ans == 'Q' || ans == 'q')
		  quit = 1;
	  }while(quit == 0);
}

Some major problems :

1>Get a standard compiler for yourself. They are all free of cost.Boreland C and Tc and all are not going to take you anywhere.

2>The load function works fine better use the second method I had suggested for "for loop" rather than the one implemented.Because the present condition loops one time extra.But still works.Some bug may creep in so the suggestion.

3>Problem is with your view function.You are calling it as view(s,n); .You cannot just pass any value for n you should keep a counter for total number of records in the file and that should be passed as n.Or atleast if you think that is users work to remember the number of records you atleast need to take the input for n before calling view as:

printf("Input the number records you want to view / input the number of records in file that you remember :");
scanf("%d",&n);
view(r,n)

It should be mainly implemented this is the function looping infinitely.With arbitrary value for n it will loop any random number of times.So infinite loop.

Some major problems :

1>Get a standard compiler for yourself. They are all free of cost.Boreland C and Tc and all are not going to take you anywhere.

2>The load function works fine better use the second method I had suggested for "for loop" rather than the one implemented.Because the present condition loops one time extra.But still works.Some bug may creep in so the suggestion.

3>Problem is with your view function.You are calling it as view(s,n); .You cannot just pass any value for n you should keep a counter for total number of records in the file and that should be passed as n.Or atleast if you think that is users work to remember the number of records you atleast need to take the input for n before calling view as:

printf("Input the number records you want to view / input the number of records in file that you remember :");
scanf("%d",&n);
view(r,n)

It should be mainly implemented this is the function looping infinitely.With arbitrary value for n it will loop any random number of times.So infinite loop.

thanks man.. it worked!:)
I need to use tc and borland c for now because its what we are using in school.

thanks man.. it worked!:)
I need to use tc and borland c for now because its what we are using in school.

Forget what you are using in school.Those are outdated and useless. Get a good compiler like code blocks or devc++ or VC++ ok.If you work on these standard compilers then you can always work on less standard or totally crap compilers like TC which doesn't give you errors for most of the operations you do.

This question has already been answered. Start a new discussion instead.