【发布时间】:2020-08-07 07:41:34
【问题描述】:
我正在尝试实现一个表示文件夹树的链表数据结构。
以下结构:
typedef struct SRC_ERROR SRC_ERROR;
struct SRC_ERROR {
int error_code;
char *error;
};
typedef struct SRC_FILE SRC_FILE;
struct SRC_FILE {
char *entry;
char md5[MD5_DIGEST_LENGTH];
};
typedef struct SRC SRC; //Source file tree with md5 entry char for source verification.
struct SRC {
SRC_ERROR error;
char *name;
char *full_path;
SRC_FILE **entries;
SRC *next_dir;
};
想法是将每个目录存储在SRC 中,SRC_FILE 将用作一个数组来存储每个文件的文件名和 MD5 哈希。
下面的scan_source() 填充结构。
SRC *scan_source(char *source_path) {
SRC *source = malloc(sizeof(SRC));
source->error.error_code = OK;
int count = 0;
DIR *dir;
struct dirent *entry;
if (!(dir = opendir(source_path))) {
source->error.error_code = ERROR;
source->error.error = "Unable to open source directory.\n";
return source;
}
source->entries = (SRC_FILE **)malloc(sizeof(SRC_FILE *) * count);
if (source->entries == NULL) {
source->error.error_code = ERROR;
source->error.error = "Unable to allocate memory to file entry tree\n";
}
while ((entry = readdir(dir)) != NULL) {
if (entry->d_type == DT_DIR) {
char path[PATH_MAX];
if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0)
continue;
snprintf(path, sizeof(path), "%s/%s", source_path, entry->d_name);
printf("[%s] - %s\n", entry->d_name, path);
//add new node
source = add_dir(source, insert_dir_node(entry->d_name, path));
scan_source(path);
} else
if (entry->d_type == DT_REG) {
printf("[FILE] - %s\n", entry->d_name);
source->entries[count]->entry = entry->d_name; //SEGFAULT HERE
count++;
source->entries = realloc(source->entries, sizeof(SRC_FILE *) * (count));
}
}
closedir(dir);
return source;
}
我遇到了内存管理问题。当目录以某种方式构建时,我会遇到间歇性段错误。
我已经标记了调试器标记的行
source->entries[count]->entry = entry->d_name; //SEGFAULT HERE
我以为我为每个结构都分配了内存,但也许我没有正确执行此操作,或者数据结构完全存在潜在问题?
例如:
test> tree
.
└── Text
0 directories, 1 file
这会导致段错误。然而,这不会:
/test> tree
.
├── another sample
│ └── Text
└── sample folder
2 directories, 1 file
使用的附加功能:
SRC *add_dir(SRC *file_tree, SRC *new_dir) {
new_dir->next_dir = file_tree;
return new_dir;
}
SRC *insert_dir_node(char *name, char *full_path) {
SRC *next_dir;
next_dir = (SRC *)emalloc(sizeof(SRC));
next_dir->name = name;
next_dir->full_path = full_path;
next_dir->next_dir = NULL;
return next_dir;
}
【问题讨论】:
-
为什么这个标签是
c++? -
类似的语言,都具有某种手动内存管理功能。有问题吗?
-
@cigien 也许是因为这种代码如果用 C++ 编写会简单得多。
-
@hdcdigi 问题是你在 C 和 C++ 中处理这个问题的方式是完全不同的。您编写的代码可能是非常好的 C(尽管有错误),但它确实是糟糕的 C++。
-
明白。也觉得懂c++的人可能也有一些c知识。
标签: c memory-management linked-list malloc