【问题标题】:C++ - Splitting Filename and File ExtensionC++ - 拆分文件名和文件扩展名
【发布时间】:2011-05-17 21:36:14
【问题描述】:

好的,首先我不想使用 Boost 或任何外部库。我只想使用 C++ 标准库。我可以使用我的split() 函数轻松地拆分带有给定分隔符的字符串:

void split(std::string &string, std::vector<std::string> &tokens, const char &delim) {
    std::string ea;
    std::stringstream stream(string);
    while(getline(stream, ea, delim))
        tokens.push_back(ea);
}

我对文件名执行此操作。但是有一个问题。有些文件的扩展名如下:tar.gztar.bz2 等。还有一些文件名带有额外的点。 Some.file.name.tar.gz。我希望将Some.file.nametar.gz 分开注意:文件名中的点数不是恒定的。

我也试过PathFindExtension,但没有运气。这可能吗?如果有,请赐教。谢谢。

编辑:我很抱歉没有指定操作系统。是 Windows。

【问题讨论】:

  • 您只想使用 C++ 标准库,所以您尝试使用操作系统特定的函数PathFindExtension...

标签: c++ windows string split


【解决方案1】:

我认为您可以使用std::stringfind_last_of 来获取最后一个. 的索引,并使用substr 来剪切字符串(尽管涉及多个点的“复杂扩展”需要额外的工作)。

【讨论】:

  • 此方法在遇到路径如下的文件时会失败:C:\Some.Folder\somefile
  • @b1naryatr0phy,您可以使用 find_last_of("/\\.") 并检查它是否是 . 以防止您的示例。
【解决方案2】:

如果不涉及用于您目的的扩展数据库,就无法做您想做的事情。扩展名没有什么神奇之处,它们只是文件名的一部分(如果你gunzip foo.tar.gz,你可能会得到一个 foo.tar,所以对于这个应用程序,.gz 实际上是“扩展名”)。所以,为了做你想做的事,建立一个你想寻找的扩展数据库,如果找不到,就回退到“最后一个点”。

【讨论】:

  • +1 表示“为您的目的”这一短语。一般的文件名拆分几乎是不可能的;而且不是很有用。 (如果应用程序必须是可移植的,那么应该扩展“最后一个点”启发式以处理名称以点开头的 Unix 隐藏文件。)
【解决方案3】:

C++ 标准库中没有任何内容——也就是说,标准中没有——但我所知道的每个操作系统都以多种方式提供此功能。

在 Windows 中可以使用 _splitpath(),在 Linux 中可以使用 dirname() & basename()

【讨论】:

    【解决方案4】:

    问题确实是像*.tar.gz 这样的文件名,由于(至少在Windows 中).tar 部分不是扩展名的一部分,因此不能一致地拆分。您要么必须为这些特殊情况保留一个列表,然后使用一个点 string::rfind 其余部分,要么找到一些预先实现的方法。请注意,.tar.* 扩展不是无限的,而且非常标准化(我认为大约有十个)。

    【讨论】:

    • 但据我所知,tar 实用程序确实始终使用 tar.gz、tar.bz2、tar.7z、tar.z 等。 Tar 甚至会在创建具有此类扩展名的文件时自动检测您想要的压缩算法。你的例子不是我(和 OP)所说的(tar.* 文件)
    • GNU tar 可以;并非所有版本都可以。其他 GNU 应用程序或 POSIX 应用程序也没有。这应该清楚为什么这些知识不能在 C++ 标准库中。
    【解决方案5】:

    您可以创建一个您认为可能会遇到的文件扩展名的查找表。如果您遇到任何新问题,还可以添加一个命令行选项以将新选项添加​​到查找表中。然后通过文件名进行解析,看查找表中是否有条目是文件名中的子串。

    编辑:你也可以参考这个问题:C++/STL string: How to mimic regex like function with wildcards?

    【讨论】:

      猜你喜欢
      • 2012-12-19
      • 2011-05-31
      • 1970-01-01
      • 2013-12-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-12-20
      相关资源
      最近更新 更多