如何在不使用dirname()的情况下从完整路径获取目录名称?

时间:2017-08-29 05:13:07

标签: c

dirname()非常糟糕,因为它修改了参数,因此它需要另一个原始字符串的丑陋副本。所以没有dirname(),请。

是否有类似的功能,但能够安全使用?

3 个答案:

答案 0 :(得分:1)

编辑:当我愚蠢时(两年前)修复可怕的解决方法;

std::string_view getDirName(std::string_view filePath) {
    return filePath.substr(0, filePath.rfind('/'));
}

答案 1 :(得分:1)

标准C99或C11不了解目录,这是一些操作系统API(或其上面的一些外部库)提供的概念。

在Linux上,dirname(3)手册页显示了调用strdup(3)的示例:

       char *dirc, *basec, *bname, *dname;
       char *path = "/etc/passwd";

       dirc = strdup(path);
       basec = strdup(path);
       dname = dirname(dirc);
       bname = basename(basec);
       printf("dirname=%s, basename=%s\n", dname, bname);

(当然您应该free dircbasec,并且上面的代码不会检查strdup的失败

您可能还需要使用realpath(3)的路径的规范目录。例如,您可以编码:

char* filepath = something();
char* canpath = realpath(filepath, NULL);
if (!canpath) { perror("realpath"); exit(EXIT_FAILURE); };
// so canpath is malloc-ed
char *candir = dirname(canpath); // would modify the string in canpath
/// use candir here, e.g.
printf("canonical directory for %s is %s\n", filepath, candir);
free (canpath);

BTW,glib提供g_path_get_dirname(其结果应为free d)。

答案 2 :(得分:0)

dirname(3)的freebsd手册页说明了 dirname()函数返回指向第一次调用时分配的内部存储空间的指针,该调用将被后续调用覆盖。所以检查你的文档。无论如何,如果您的实现直接使用以下命令修改输入字符串,则可以获得安全调用:

char *aux = dirname(strdup(the_path));
...
free(aux);