C Tutorial-File Handling (1)


Introduction

Part of any useful computer program is often going to be manipulation of external data sources. The file is the basic unit of storage for many operating systems, from Unix to Mac. Any C development environment on these platforms will include functions allowing the programmer to:
  • Open & Close files;
  • Read from & Write to files;
  • Delete files.
Commands for all of the above are found in the stdio.h header file.

Opening & Closing Files

The basic command used to open a file is:

FILE * fopen(char * filename, char * mode)
The value returned is a handle to a file, defined in stdio.h, as FILE *. A null pointer is returned and can be tested for in case the call fails. So, the following is a good test for presence of a file:
FILE * hFile;
hFile = fopen( filename, "r");
if (hFile == NULL)
{
// Error, file not found
}
else
{
// Process & close file
fclose(hFile);
}
The mode value in the above example is set to 'r', indicating that we want to read from the file. Other possible values are:
  • w - write to the file, overwriting existing data
  • a - append to an existing file
  • r+ - read and write to a file
Using 'r+' means that all writing will take place at the end of the file, and that reading is sequential. The fclose function closes a valid file handle.

Reading & Writing Data

Once a file is open, we can read from it in one of two ways. We can use the standard printf functions for formatted output, or we can use the 'binary' file functions:


int fread(void * buffer, int size, int num, FILE * hFile)
int fwrite(void * buffer, int size, int num, FILE * hFile)
Both of these can accept any variable that can be cast internally in the first parameter. Be aware, however, that if it is not a pointer type (int *, char * etc.), then it will need to be passed by reference (&nNumber, for example). This will create the appropriate cast to the variable being passed. So, to read a number, we would use:
int nRead = fread(&nNumber, sizeof(int), 1, hFile);
In this example, we have provided the size of an integer (since we don't know the platform that we are compiling for), and a count of 1. This will cause the program to read the appropriate amount of data. We can also write the data back out using:
int nWritten = fwrite(&nNumber, sizeof(int), 1, hFile);
Of course, if we were to have a string that needed to be written to the file, so long as it is null terminated, we can use fwrite as follows:
int nWritten = fwrite(szString, sizeof(char), strlen(szString), hFile);
This will write out the string, but not the null terminator. Care, therefore, must be taken when using this function.
If we want to read the data back in, without knowing the length of the string, we need to perform two operations for each file access:
int nStrLen = strlen(szString);
int nWritten = fwrite(&nStrLen, sizeof(int), 1, hFile);
int nWritten = fwrite(szString, sizeof(char), nStrLen, hFile);
We can then read the variable length string back in as follows:
int nStrLen;
int nRead = fread(&nStrLen, sizeof(int), 1, hFile);
int nRead = fread(szString, sizeof(char), nStrLen, hFile);
szString[nStrLen] = '\0'; // Append null terminator
This trick can be used for any data types, including user defined data types, such as structs.

Deleting Files

The command to delete a file is:
remove (char * szFileName);
This will simply delete the file, with no way to get it back again without an external program.

0 comments:

Post a Comment

 
The Techiebyte © 2012 | Designed by Pranav Talwar