【问题标题】:How to find substring from string?如何从字符串中找到子字符串?
【发布时间】:2012-11-02 12:34:12
【问题描述】:

如何使用 C/C++ 从字符串路径“/user/desktop/abc/post/”中找到子字符串?我想检查该路径中是否存在文件夹“abc”。

路径是字符指针char *ptr = "/user/desktop/abc/post/";

【问题讨论】:

  • strstr()std::string::find().
  • 这是1中的2题,C和C++是两种完全不同的语言。

标签: c++ c


【解决方案1】:

使用std::stringfind

std::string str = "/user/desktop/abc/post/";
bool exists = str.find("/abc/") != std::string::npos;

【讨论】:

  • 如果 "/user/desktop/abc" 那么如何找到 "abc" 文件夹
  • std::string::npos,它与初始位置比较?我没有得到你告诉我的“我们检查它是否是最后一个位置。”?
  • @user1511510 否,如果未找到子字符串,npos 将由 find 返回。
  • 我没有得到您所说的“只需检查它是否是最后一个位置”。在“user/desktop/abc”的情况下,如何找到“abc”文件夹?
  • @user1511510 哦……好吧,我不打算为你写代码。你自己想不出来吗?这只是处理一个角落案例,我希望你能管理。
【解决方案2】:

在 C 中,使用 @987654321@ 标准库函数:

const char *str = "/user/desktop/abc/post/";
const int exists = strstr(str, "/abc/") != NULL;

注意不要意外找到太短的子字符串(这是开始和结束斜线的用途)。

【讨论】:

  • hmm.. 如果它是路径的最后一部分呢?
  • 如果 "/user/desktop/abc" 那么如何找到 "abc" 文件夹。
【解决方案3】:

使用std::string find method的示例:

#include <iostream>
#include <string>

int main (){
    std::string str ("There are two needles in this haystack with needles.");
    std::string str2 ("needle");

    size_t found = str.find(str2);
    if(found!=std::string::npos){ 
        std::cout << "first 'needle' found at: " << found << '\n';
    }

    return 0;
}

结果:

first 'needle' found at: 14.

【讨论】:

    【解决方案4】:

    使用strstr(const char *s , const char *t)include&lt;string.h&gt;

    您可以编写自己的函数,其行为与strstr 相同,也可以根据您的要求进行修改

    char * str_str(const char *s, const char *t)
    {
    int i, j, k;
    for (i = 0; s[i] != '\0'; i++) 
    {
    for (j=i, k=0; t[k]!='\0' && s[j]==t[k]; j++, k++);
    if (k > 0 && t[k] == '\0')
    return (&s[i]);
    }
    return NULL;
    }
    

    【讨论】:

    • 这个函数看起来比想象的要复杂......为什么你在最后返回“nothing”,因为函数应该返回 int 参数?
    • 您可以自己编写,但在大多数情况下这样做是错误的。 c 库中的函数通常比你自己编写的东西更高效,测试也更好。
    • 是的,在某些情况下它肯定会失败,但是......我试过了,我这样做了,所以想把它粘贴在这里......
    【解决方案5】:

    正如 user1511510 所指出的,在 abc 位于文件名末尾时存在一种不寻常的情况。我们需要查找/abc//abc,后跟字符串终止符'\0'。一种天真的方法是检查 /abc//abc\0 是否是子字符串:

    #include <stdio.h>
    #include <string.h>
    
    int main() {
        const char *str = "/user/desktop/abc";
        const int exists = strstr(str, "/abc/") || strstr(str, "/abc\0");
        printf("%d\n",exists);
        return 0;
    }
    

    exists 将是 1,即使 abc 后面没有空终止符。这是因为字符串文字"/abc\0" 等价于"/abc"。更好的方法是测试/abc 是否为子字符串,然后查看该子字符串后面的字符(使用strstr() 返回的指针进行索引)是/ 还是'\0'

    #include <stdio.h>
    #include <string.h>
    
    int main() {
        const char *str = "/user/desktop/abc", *substr;
        const int exists = (substr = strstr(str, "/abc")) && (substr[4] == '\0' || substr[4] == '/');
        printf("%d\n",exists);
        return 0;
    }
    

    这应该适用于所有情况。

    【讨论】:

    • "exists = (substr = strstr(str, "/abc")) &amp;&amp; (substr[4] == '\0' || substr[4] == '/'); 应该适用于所有情况" - 不是这样...假设说"/abcd/abc" 你会被d 窒息...正确,如果substr[4] 测试失败,您需要继续搜索到字符串。 (在搜索 /abc/ 之前添加尾随“/”可能更容易。)
    • @TonyD 好收获!我完全同意,请随时编辑帖子。
    【解决方案6】:

    如果你过多地使用数组,那么你应该包含cstring.h,因为它有太多的功能,包括查找子字符串。

    【讨论】:

    • 你的意思是,我们没有任何标准函数可以从字符串中找出子字符串。
    【解决方案7】:

    在 C++ 中

    using namespace std;
    
    string my_string {"Hello world"};
    string element_to_be_found {"Hello"};
    
    if(my_string.find(element_to_be_found)!=string::npos)
       std::cout<<"Element Found"<<std::endl;
    

    【讨论】:

    • 这个答案给出了误报,例如。用于“/Hello2/world”路径。
    • 这给出了完美的答案。
    猜你喜欢
    • 2021-06-11
    • 2018-11-24
    • 2016-09-14
    • 2021-03-19
    • 1970-01-01
    • 2017-10-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多