Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/150.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 字符串::查找问题(C+;+;)_C++_String_Find - Fatal编程技术网

C++ 字符串::查找问题(C+;+;)

C++ 字符串::查找问题(C+;+;),c++,string,find,C++,String,Find,我的string::find实现有一个小问题 输入是一个长字符串,由以下可能的示例组成:input=“壹仟零壹” 我的问题似乎是,在包含多个“and”的输入字符串中,只有第一个and被删除,而其他的则没有 这是到目前为止我的代码,它找到了“and”,但唯一删除的是当“a”之前的字母不是“s”(表示“千”)时 编辑:我忘了提到,输入中唯一包含“and”的单词是“千”,所以这是一个特例。我会使用正则表达式(来自boost、PCRE或C++11标准)-但是如果我必须自己做的话,我的代码看起来会像这样:

我的string::find实现有一个小问题

输入是一个长字符串,由以下可能的示例组成:input=“壹仟零壹”

我的问题似乎是,在包含多个“and”的输入字符串中,只有第一个and被删除,而其他的则没有

这是到目前为止我的代码,它找到了“and”,但唯一删除的是当“a”之前的字母不是“s”(表示“千”)时

编辑:我忘了提到,输入中唯一包含“and”的单词是“千”,所以这是一个特例。

我会使用正则表达式(来自boost、PCRE或C++11标准)-但是如果我必须自己做的话,我的代码看起来会像这样:

string toKill = "and";
size_t pos = 0;
while( ( pos = s.find(toKill, pos) )!=std::string::n_pos )
{
  //Check it doesn't start with an additional letter
  if( pos!=0 && is_alpha(s[pos-1]) ) { pos++; continue; }
  //Check it doesn't end with an additional letter
  if( pos+toKill.size()!=s.size() && is_alpha(s[pos+toKill.size()]) { pos++; continue;}
  //Remove it and the trailing whitespace (or punctuation)
  s.erase(pos,toKill.size()+1);
}
我会为此使用正则表达式(来自boost、PCRE或C++11标准),但如果我必须自己做,我的代码看起来会像这样:

string toKill = "and";
size_t pos = 0;
while( ( pos = s.find(toKill, pos) )!=std::string::n_pos )
{
  //Check it doesn't start with an additional letter
  if( pos!=0 && is_alpha(s[pos-1]) ) { pos++; continue; }
  //Check it doesn't end with an additional letter
  if( pos+toKill.size()!=s.size() && is_alpha(s[pos+toKill.size()]) { pos++; continue;}
  //Remove it and the trailing whitespace (or punctuation)
  s.erase(pos,toKill.size()+1);
}
在代码中还需要(至少)两样东西。第一个循环用于处理
字符串的整个字符串,第二个循环用于跳过已检查的字符串

您可能还希望处理字符串可能以
开头的可能性,尽管这种可能性不大:对您期望的内容要自由,对您提供的内容要具体

以下代码将是一个很好的起点:

#include <iostream>
#include <string>

int main (void) {
    std::string inputStr = "one thousand and fifty one";
    std::string killStr = "and ";

    size_t startPos = 0;
    size_t andPos;
    while ((andPos = inputStr.find (killStr, startPos)) != std::string::npos) {
        if ((andPos == 0) || (inputStr[(andPos - 1)] != 's')) {
            inputStr.erase(andPos, killStr.length());
            startPos = andPos;
        } else {
            startPos = andPos + 1;
        }
    }

    std::cout << inputStr << '\n';
    return 0;
}

(a) 如果我想成为一名学究,我最好把它做好:-)

您的代码中还需要(至少)两样东西。第一个循环用于处理
字符串的整个字符串,第二个循环用于跳过已检查的字符串

您可能还希望处理字符串可能以
开头的可能性,尽管这种可能性不大:对您期望的内容要自由,对您提供的内容要具体

以下代码将是一个很好的起点:

#include <iostream>
#include <string>

int main (void) {
    std::string inputStr = "one thousand and fifty one";
    std::string killStr = "and ";

    size_t startPos = 0;
    size_t andPos;
    while ((andPos = inputStr.find (killStr, startPos)) != std::string::npos) {
        if ((andPos == 0) || (inputStr[(andPos - 1)] != 's')) {
            inputStr.erase(andPos, killStr.length());
            startPos = andPos;
        } else {
            startPos = andPos + 1;
        }
    }

    std::cout << inputStr << '\n';
    return 0;
}

(a) 如果我想成为一个学究,我最好把它做好:-)

试试这个:

string toKill = "and";
size_t andF = 0;

while ((andF = input.find(toKill, andF)) != string::npos) {
    if (andF == 0 || input[andF - 1] != 's') {
        input.erase(andF, 4);
    }
    else ++andF;
}
试试这个:

string toKill = "and";
size_t andF = 0;

while ((andF = input.find(toKill, andF)) != string::npos) {
    if (andF == 0 || input[andF - 1] != 's') {
        input.erase(andF, 4);
    }
    else ++andF;
}


那么,你该怎么处置丈夫、乐队、格兰德或安卓呢?也许你想在之前检查一个非alpha,而不仅仅是“s”?也许你也想在单词后面检查一下。对于“android”,它会崩溃,因为它会在字符串边界之外访问:
input[-1]
@Michael,我知道它会做什么,我实际上更多的是问海报想做什么:-)@Andrew,如果它是防故障的,我仍然会说它对学习和未来都有好处(达到合理水平)现在。@Andrew:如果您删除了搜索字符串,您需要一个while循环并继续搜索字符串,从当前位置减去搜索字符串的长度。那么您应该如何处理丈夫、乐队、grand或android?也许您希望在之前检查非alpha,而不仅仅是“s”?也许您希望在之后检查r这个词也是。对于“android”,它会崩溃,因为它会在字符串边界之外访问:
input[-1]
@Michael,我知道它会做什么,实际上我更多的是问海报想做什么:-)@Andrew,如果它是防故障的(达到合理的水平),我仍然会说它对学习和未来都有好处现在。@Andrew:您需要一个while循环并继续搜索字符串,如果您删除了搜索字符串,则从当前位置减去搜索字符串的长度。如果字符串包含千,则无限循环。如果您不调用
erase(),则需要从
pos
搜索
否则,如果字符串包含千,则会得到一个无限循环。如果不调用
erase()
则需要从
pos
进行搜索,否则会得到一个无限循环。我会删除4的硬编码,只是为了使其更一般。看起来我忘记了需要一个while循环。@MichaelAnderson我也会,但我基于他的代码,我想弄清楚遗漏了什么。我删除了4的硬编码,只是为了让它更通用。看起来我忘记了需要一段时间的循环。@MichaelAnderson我也想,但我基于他的代码,我希望它能清楚地知道遗漏了什么。我喜欢在toKill字符串中添加空格——它修复了尾随字符的问题。但是,它不会捕获尾随的“and”-比如
“一百零一”
,但是我假设这对于OPs来说是可以的。我喜欢在toKill字符串中添加空格-它修复了尾随字符的问题。然而,它不会捕获尾随的“and”-比如
“一百零一”
,但是我假设这对于OPs来说是可以的。