C++ C++;-拆分文件名和文件扩展名

C++ C++;-拆分文件名和文件扩展名,c++,windows,string,split,C++,Windows,String,Split,好的,首先我不想使用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(st

好的,首先我不想使用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);
}
void拆分(std::string和string、std::vector和tokens、const char和delim){
std::字符串ea;
std::stringstream(字符串);
while(getline(stream、ea、delim))
代币。推回(ea);
}
我在文件名上这样做。但是有个问题。有些文件具有扩展名,如:
tar.gz
tar.bz2
,等等。还有一些文件名具有额外的点
Some.file.name.tar.gz
。我希望将
Some.file.name
tar.gz
分开。注意:文件名中的点数不是恒定的

我也尝试了
PathFindExtension
,但没有成功。这可能吗?如果是的话,请告诉我。多谢各位


编辑:我很抱歉没有指定操作系统。它是Windows。< /P> < P>在C++标准库中没有任何东西,也就是说,它不在标准中,但是我知道的每个操作系统都以各种方式提供了这个功能。
在Windows中可以使用_splitpath(),在Linux中可以使用dirname()&basename()

我认为可以使用
std::string
获取最后一个
的索引,并剪切字符串(尽管涉及多个点的“复杂扩展”需要额外的工作)问题确实是像
*.tar.gz
这样的文件名,由于
.tar
部分(至少在Windows中)不是扩展的一部分,因此无法一致地分割这些文件名。您必须为这些特殊情况保留一个列表,并使用一个单点
string::rfind
作为其余部分,或者找到一些预先实现的方法。请注意,
.tar.*
扩展并不是无限的,而且非常标准化(我认为大约有十个扩展)。

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

你可以创建一个你认为可能遇到的文件扩展名的查找表。还可以添加一个命令行选项,以便在遇到任何新问题时向查找表中添加一个新选项。然后解析文件名,查看查找表中的任何条目是否是文件名中的子字符串


编辑:您也可以参考此问题:

+1了解短语“出于您的目的”。一般的文件名拆分几乎是不可能的;而且不是很有用。(如果应用程序必须是便携的,那么“最后一点”的试探应该被扩展来处理UNIX隐藏文件,这些文件的名字从一个点开始。)您只想使用C++标准库,所以您可以尝试OS特定的函数<代码> PosiDeXrase…但是TAR实用程序确实使用了TAR.GZ、TAR.BZ2、TAR.7Z、TARA.Z、在我看来,这是始终如一的。Tar甚至可以在创建具有这样扩展名的文件时自动检测所需的压缩算法。你的例子不是我(和OP)所说的(GNUtar的
tar.*
文件);并非所有版本都有。其他GNU应用程序或POSIX应用程序也没有。这应该说明为什么这种知识不能在C++标准库中使用。这种方法在遇到文件路径时会失败,例如:c:\\Falth\\文件夹。somefile@b1naryatr0phy,您可以执行
查找(“/\\”)的最后一个
并检查它是否为
,以保护您的示例。