Advanced File Techniques
File Positioning and Navigation
Seeking in Files
graph LR
A[File Pointer] --> B[Beginning]
A --> C[Current Position]
A --> D[End]
B --> E[fseek()]
C --> E
D --> E
Precise File Navigation Functions
Function |
Purpose |
Usage |
fseek() |
Move file pointer |
Precise positioning |
ftell() |
Get current position |
Determine file offset |
rewind() |
Reset to file start |
Quick repositioning |
Advanced File Manipulation Example
#include <stdio.h>
int process_large_file(const char* filename) {
FILE* file = fopen(filename, "rb");
if (!file) return -1;
// Get file size
fseek(file, 0, SEEK_END);
long file_size = ftell(file);
rewind(file);
// Dynamic memory allocation
char* buffer = malloc(file_size + 1);
if (!buffer) {
fclose(file);
return -1;
}
// Read specific sections
fseek(file, file_size / 2, SEEK_SET);
size_t bytes_read = fread(buffer, 1, file_size / 2, file);
buffer[bytes_read] = '\0';
fclose(file);
free(buffer);
return 0;
}
Memory-Mapped File I/O
Advantages of Memory Mapping
graph TD
A[Memory-Mapped Files] --> B[Direct Memory Access]
A --> C[Performance Optimization]
A --> D[Simplified File Handling]
Memory Mapping Implementation
#include <sys/mman.h>
#include <fcntl.h>
#include <unistd.h>
void* map_file(const char* filename, size_t* file_size) {
int fd = open(filename, O_RDONLY);
if (fd == -1) return NULL;
struct stat sb;
if (fstat(fd, &sb) == -1) {
close(fd);
return NULL;
}
*file_size = sb.st_size;
void* mapped = mmap(NULL, *file_size, PROT_READ, MAP_PRIVATE, fd, 0);
close(fd);
return mapped == MAP_FAILED ? NULL : mapped;
}
Concurrent File Access
Thread-Safe File Operations
Technique |
Description |
Use Case |
File Locking |
Prevent simultaneous access |
Multi-threaded applications |
Atomic Operations |
Ensure consistent updates |
Concurrent file modifications |
Buffered vs Unbuffered I/O
graph LR
A[File I/O Strategies] --> B[Buffered I/O]
A --> C[Unbuffered I/O]
B --> D[Standard Library Functions]
C --> E[Direct System Calls]
Complex File Processing Technique
#include <stdio.h>
typedef struct {
char* buffer;
size_t size;
} FileContext;
FileContext* create_file_context(const char* filename) {
FILE* file = fopen(filename, "rb");
if (!file) return NULL;
FileContext* context = malloc(sizeof(FileContext));
fseek(file, 0, SEEK_END);
context->size = ftell(file);
rewind(file);
context->buffer = malloc(context->size + 1);
fread(context->buffer, 1, context->size, file);
context->buffer[context->size] = '\0';
fclose(file);
return context;
}
void free_file_context(FileContext* context) {
if (context) {
free(context->buffer);
free(context);
}
}
Key Advanced Techniques
- Understand file positioning methods
- Implement memory-mapped I/O
- Use thread-safe file access
- Optimize I/O performance
- Manage file resources efficiently
LabEx Learning Recommendations
- Practice advanced file handling scenarios
- Experiment with different I/O techniques
- Understand system-level file operations
- Develop robust error handling strategies