在CentOS中使用readdir
优化代码,通常涉及到对目录进行高效的遍历。readdir
是POSIX标准库函数,用于读取目录中的条目。以下是一些优化建议和示例代码:
opendir
和readdir
首先,确保你使用的是opendir
和readdir
来遍历目录。这是最基本也是最常用的方法。
#include <stdio.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>
void list_directory(const char *path) {
DIR *dir = opendir(path);
if (dir == NULL) {
perror("opendir");
return;
}
struct dirent *entry;
while ((entry = readdir(dir)) != NULL) {
if (entry->d_type == DT_REG) { // 只列出普通文件
printf("%s\n", entry->d_name);
}
}
closedir(dir);
}
int main(int argc, char *argv[]) {
if (argc != 2) {
fprintf(stderr, "Usage: %s <directory>\n", argv[0]);
return EXIT_FAILURE;
}
list_directory(argv[1]);
return EXIT_SUCCESS;
}
每次调用readdir
都会产生一次系统调用,这可能会影响性能。可以通过减少不必要的系统调用来优化。
#include <stdio.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>
void list_directory_optimized(const char *path) {
DIR *dir = opendir(path);
if (dir == NULL) {
perror("opendir");
return;
}
struct dirent *entry;
char full_path[PATH_MAX];
while ((entry = readdir(dir)) != NULL) {
if (entry->d_type == DT_REG) { // 只列出普通文件
snprintf(full_path, sizeof(full_path), "%s/%s", path, entry->d_name);
printf("%s\n", full_path);
}
}
closedir(dir);
}
int main(int argc, char *argv[]) {
if (argc != 2) {
fprintf(stderr, "Usage: %s <directory>\n", argv[0]);
return EXIT_FAILURE;
}
list_directory_optimized(argv[1]);
return EXIT_SUCCESS;
}
如果目录非常大,可以考虑使用多线程来并行处理目录条目。
#include <stdio.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>
#include <pthread.h>
#define NUM_THREADS 4
typedef struct {
const char *path;
int start;
int end;
} thread_data_t;
void *list_directory_thread(void *arg) {
thread_data_t *data = (thread_data_t *)arg;
DIR *dir = opendir(data->path);
if (dir == NULL) {
perror("opendir");
pthread_exit(NULL);
}
struct dirent *entry;
int count = 0;
while ((entry = readdir(dir)) != NULL && count < data->end - data->start) {
if (entry->d_type == DT_REG) { // 只列出普通文件
printf("%s\n", entry->d_name);
}
count++;
}
closedir(dir);
pthread_exit(NULL);
}
void list_directory_multithreaded(const char *path, int num_threads) {
DIR *dir = opendir(path);
if (dir == NULL) {
perror("opendir");
return;
}
struct dirent *entry;
int total_files = 0;
while ((entry = readdir(dir)) != NULL) {
if (entry->d_type == DT_REG) { // 只列出普通文件
total_files++;
}
}
closedir(dir);
pthread_t threads[NUM_THREADS];
thread_data_t thread_data[NUM_THREADS];
int files_per_thread = total_files / num_threads;
for (int i = 0; i < num_threads; i++) {
thread_data[i].path = path;
thread_data[i].start = i * files_per_thread;
thread_data[i].end = (i == num_threads - 1) ? total_files : (i + 1) * files_per_thread;
pthread_create(&threads[i], NULL, list_directory_thread, (void *)&thread_data[i]);
}
for (int i = 0; i < num_threads; i++) {
pthread_join(threads[i], NULL);
}
}
int main(int argc, char *argv[]) {
if (argc != 2) {
fprintf(stderr, "Usage: %s <directory>\n", argv[0]);
return EXIT_FAILURE;
}
list_directory_multithreaded(argv[1], NUM_THREADS);
return EXIT_SUCCESS;
}
readdir_r
在某些系统上,readdir
可能是线程不安全的。可以使用readdir_r
来替代,它是线程安全的版本。
#include <stdio.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>
void list_directory_readdir_r(const char *path) {
DIR *dir = opendir(path);
if (dir == NULL) {
perror("opendir");
return;
}
struct dirent entry;
struct dirent *current;
while (readdir_r(dir, &entry, ¤t) == 0) {
if (current->d_type == DT_REG) { // 只列出普通文件
printf("%s\n", current->d_name);
}
}
closedir(dir);
}
int main(int argc, char *argv[]) {
if (argc != 2) {
fprintf(stderr, "Usage: %s <directory>\n", argv[0]);
return EXIT_FAILURE;
}
list_directory_readdir_r(argv[1]);
return EXIT_SUCCESS;
}
通过这些方法,你可以在CentOS中优化使用readdir
的代码,提高目录遍历的效率。