In this section we will read about functions that are used to randomly access a record stored in a binary file. These functions include fseek (), ftell(), rewind (), fgetpos (), and fsetpos ().
FUNCTIONS
FOR SELECTING A RECORD RANDOMLY
In
this section we will read about functions that are used to randomly access a
record stored in a binary file. These functions include fseek (), ftell(),
rewind (), fgetpos (), and fsetpos ().
The
function fseek () is used to reposition a binary stream. The prototype of
fseek() function which is defined in stdio.h can be given as
int fseek (FILE *stream, long
offset, int origin);
fseek()
is used to set the file position pointer for the given stream. The variable
offset is an integer value that gives the number of bytes to move forward or
backward in the file. The value of offset may be positive or negative, provided
it makes sense. For example, you cannot specify a negative offset if you are
starting at the beginning of the file. The origin value should have one of the
following values (defined in stdio.h):
•
SEEK_SET: to perform input or output on offset bytes from start of the file
•
SEEK_CUR: to perform input or output on offset bytes from the current position
in the file
•
SEEK_END: to perform input or output on offset bytes from the end of the file
•
SEEK_SET, SEEK_CUR and SEEK END are defined constants with value 0, 1, and 2,
respectively.
Programming Tip:
While using fseek(), if the third
parameter is specified as SEEK_END, then you must provide a negative offset,
otherwise it will try to access beyond EOF.
On
successful operation, fseek() returns zero and in case of failure, it returns a
non-zero value. For example, if you try to perform a seek operation on a file
that is not opened in binary mode then a non-zero value will be returned.
fseek()
can be used to move the file pointer beyond a file, but not before the
beginning.
Note
If a file has been opened for
update and later if you want to switch from reading to writing or vice versa,
then you must use the fseek().
The
fseek() is primarily used with binary files as it has limited functionality
with text files.
25.
Write a program to randomly read the nth records of a binary file.
#include <stdio.h>
#include <conio.h>
main()
{
typedef struct employee
{
int emp_code;
char name [20];
int hra;
int da;
int ta;
};
FILE *fp;
struct employee e;
int result, rec_no;
fp =
fopen("employee.txt", "rb");
if (fp==NULL)
{
printf("\n Error opening
file");
exit (1);
}
printf("\n\n Enter the rec_no
you want to read: ");
scanf("%d", &rec_no);
if (rec_no >= 0)
{
/* from the file pointed by fp read
a record of the specified record starting from the beginning of the file*/
fseek (fp, (rec_no-1) * sizeof (e),
SEEK_SET);
result = fread (&e, sizeof (e),
1, fp);
if (result == 1)
{
printf("\n EMPLOYEE CODE:
%d", e.emp_code);
printf("\n Name: %s",
e.name);
printf("\n HRA, TA, and DA: %d
%d %d", e.hra, e.ta, e.da);
}
else
printf("\n Record Not
Found");
}
fclose(fp);
getch();
return 0;
}
Output
Enter the rec_no you want to read:
06
EMPLOYEE CODE: 06
Name: Tanya
HRA, DA and TA: 20000 10000 3000
26.
Write a program to print the records in reverse order. The file must be opened
in binary mode. Use fseek().
#include <stdio.h>
#include <conio.h>
main()
{
typedef struct employee
{
int emp_code;
char name [20];
int hra;
int da;
int ta;
};
FILE *fp;
struct employee e;
int result, i;
fp =
fopen("employee.txt", "rb");
if (fp==NULL).
{
printf("\n Error opening
file");
exit (1);
}
for (i=5;i>=0;i--)
{
fseek (fp, i* sizeof (e),
SEEK_SET);
fread (&e, sizeof (e), 1, fp);
printf("\n EMPLOYEE CODE:
%d", e.emp_code);
printf("\n Name: %s",
e.name);
printf("\n HRA, TA and DA: %d
%d %d", e.hra, e.ta, e.da);
}
fclose(fp);
getch();
return 0;
}
Output
EMPLOYEE CODE: 06
Name: Tanya
HRA, DA and TA: 20000 10000 3000
EMPLOYEE CODE: 05
Name: Ruchi
HRA, DA and TA: 10000 6000 3000
27.
Write a program to edit a record in binary mode using fseek().
#include <stdio.h>
#include <conio.h>
main()
{
typedef struct employee
{
int emp_code;
char name [20];
int hra;
int da;
int ta;
};
FILE *fp;
struct employee e;
fp =
fopen("employee.txt", "r+");
if (fp==NULL)
{
printf("\n Error opening
file");
exit(1);
}
printf("\n Enter record no. to
be modified: ");
scanf("%d", &rec_no);
fseek (fp, (rec_no-1)* sizeof (e),
SEEK_SET);
fread (&e, sizeof (e), 1, fp);
printf("\n Enter modified name
of the employee: ");
scanf("%s", e.name);
printf("\n Enter the modified
HRA, TA, and DA of the employee: ");
scanf("%d %d %d",
&e.hra, &e.ta, &e.da);
fwrite(&e, sizeof (e), 1, fp);
fclose (fp);
printf("\n Record
Edited");
getch();
return 0;
}
Output
Enter record no. to be modified: 04
Enter the modified HRA, TA, and DA
of the employee: 30000 1000 5000
Record Edited
The
ftell () function is used to know the current position of file pointer. It is
at this position where the next input or ouput operation will be performed. The
syntax of ftell (), defined in stdio.h, can be given as
long ftell (FILE *stream);
Here,
stream points to the file whose file position indicator has to be determined.
If successful, ftell () function returns the current file position (in bytes)
for stream. However, in case of error, ftell () returns -1.
When
using ftell (), error can occur either because of two reasons:
•
First, using ftell() with a device that cannot store data (e.g., keyboard).
•
Second, when the position is larger than that can be represented in a long
integer. This will usually happen when dealing with very large files.
Look
at the program code which illustrates the use of ftell ().
/*The
program writes data to a file, saves the number of bytes stored in it in a
variable n (by using ftell ()) and then re-opens the file to read n bytes from
the file and simultaneously display it on the screen.*/
main ()
{
FILE *fp;
char c;
int n;
fp=fopen("abc",
"w");
if(fp==NULL)
{
printf("\n Error Opening The
File");
exit (1);
}
while ((c=getchar()) != EOF)
putc(c, fp);
n = ftell (fp);
fclose(fp);
fp=fopen("abc",
"r");
if (fp==NULL)
{
printf("\n Error Opening The
File");
exit (1);
}
while (ftell (fp) <n)
{
c= fgetc (fp);
printf("%c", c);
}
fclose(fp);
}
Output
abcdefghijkjdqjdh
Note
ftell () is useful when we have to
deal with text files for which position of the data cannot be calculated.
rewind
() is used to adjust the position of file pointer so that the next I/O
operation will take place at the beginning of the file. It is defined in
stdio.h and its prototype can be given as
void rewind (FILE *f);
rewind
() is equivalent to calling fseek() with following parameters:
fseek (f, OL, SEEK_SET);
We
have seen earlier that if a file is opened for writing and you want to read it
later, then you have to close the existing file and reopen it so that data can
be read from the beginning of the file. The other alternative is to to use the
rewind (). Look at the program code given below which demonstrates the use of
rewind ().
#include <stdio.h>
main()
{
FILE *fp;
char feedback [80];
int i=0;
fp =
fopen("comments.txt", "w+");
if (fp==NULL)
{
printf("\n Error Opening The
File");
exit (1);
}
printf("\n Provide comments on
this book: ");
scanf("%s", feedback);
while (feedback [i] != '\0')
{
fputc(feedback [i], fp);
i++;
}
rewind (fp);
printf("\n Contents of the
file are: ");
while (feof (fp)==0)
printf("%c", fgetc (fp);
fclose(fp);
return 0;
}
Output
Provide comments on this book: Good
Contents of the file are: Good
However,
you must prefer to use fseek() equivalent code rather calling rewind () because
it is impossible to determine if rewind () was successful or not.
The
fgetpos () is used to determine the current position of the stream. The
prototype of the fgetpos () as given in stdio.his
int fgetpos (FILE *stream, fpos_t
*pos);
Here,
stream is the file whose current file pointer position has to be determined.
pos is used to point to the location where fgetpos () can store the position
information. In simple words, fgetpos () stores the file position indicator of
the given file stream in the pos variable. The pos variable is of type fpos_t
which is defined in stdio.h and is basically an object that can hold every
possible position in a FILE.
On
success, fgetpos () returns zero and in case of an error a non-zero value is
returned. The value of pos obtained through fgetpos () can be used by the
fsetpos () to return to this same position.
The
fsetpos () is used to move the file position indicator of a stream to the
location indicated by the information obtained in 'pos' by making a call to the
fgetpos (). Like fgetpos (), fsetpos () is defined in stdio.h and its prototype
can be given as
int fsetpos (FILE *stream, const
fpos_t pos);
Here,
stream points to the file whose file pointer indicator has to be re-positioned.
pos points to positioning information as returned by fgetpos.
On
success, fsetpos () returns a zero and clears the EOF indicator. In case of
failure it returns a non-zero value.
Programming Tip:
An
error will be generated if you try to place the file position indicator before
the first byte of the file.
After
the successful call to fsetpos (), the next operation on a stream in update
mode may be input or output. Look at the program code given below which
illustrates the use of fgetpos () ent and fsetpos () functions.
//
The program opens a file and reads bytes at several different locations.
#include <stdio.h>
main()
{
FILE *fp;
fpost_pos;
char text [20];
fp = fopen("practise.c",
"rb");
if (fp ==NULL)
{
printf("\n Error opening
file");
exit(1);
}
/* Read some data and then check
the position. */
fread (text, sizeof (char), 20,
fp);
if (fgetpos (fp, &pos) != 0)
{
printf("\n Error in fgetpos ()
");
exit(1);
}
fread(text, sizeof(char), 20, fp);
printf("\n 20 bytes at byte
%ld: %s", pos, text);
/* Set a new random position and
read more data */
pos = 90;
if (fsetpos (fp, &pos) != 0)
{
printf("\n Error in fsetpos
()");
exit(1);
}
fread (text, sizeof (char), 20,
fp);
printf("\n 20 bytes at byte
%ld: %s", pos, text);
fclose(fp);
}
Output
20 bytes at byte 20: #include
<conio.h>
ma
20 bytes at byte 90: getch();
90 return 0;
}
Only use values for fsetpos() that
are returned from fgetpos().
Programming in C: Unit V: File processing : Tag: : Syntax with Example C Programs | File processing - Function for Selecting a Record Randomly
Programming in C
CS3251 2nd Semester CSE Dept 2021 | Regulation | 2nd Semester CSE Dept 2021 Regulation