Как проверить, существует ли позиция в строке std ?? (C ++) - PullRequest
1 голос
/ 12 апреля 2010

У меня есть длинная строковая переменная, и я хочу найти в ней определенные слова и ограничить текст в соответствии с этими словами.

Скажите, у меня есть следующий текст:

" Это удивительное новое носимое звуковое решение оснащено рабочим динамиком, встроенным в переднюю часть рубашки, и может воспроизводить музыку или звуковые эффекты, подходящие для любой ситуации. Это все равно что сниматься в собственном фильме "

и слова: «решение», «фильм».

Я хочу вычесть из большой строки (как Google на странице результатов):

"... новое носимое аудио решение имеет встроенный рабочий динамик ..." а также "... как в главной роли в вашем собственном фильме "

для этого я использую код:

for (std::vector<string>::iterator it = words.begin(); it != words.end(); ++it)
{
    int loc1 = (int)desc.find( *it, 0 );    
    if( loc1 != string::npos )
    {
        while(desc.at(loc1-i) && i<=80)
        {       
            i++;
            from=loc1-i;
            if(i==80) fromdots=true;
        }
        i=0;
        while(desc.at(loc1+(int)(*it).size()+i) && i<=80)
        {
            i++;
            to=loc1+(int)(*it).size()+i;
            if(i==80) todots=true;
        }

        for(int i=from;i<=to;i++)
        {    
            if(fromdots) mini+="...";
            mini+=desc.at(i);
            if(todots) mini+="...";    
        }    
      }

но desc.at (loc1-i) вызывает исключение OutOfRange ... Я не знаю, как проверить, существует ли эта позиция, не вызывая исключение!

Помогите пожалуйста!

Ответы [ 3 ]

1 голос
/ 12 апреля 2010

Это отличное упражнение, позволяющее воспользоваться преимуществами STL. Вы просто открываете справочник и вишневые алгоритмы и классы для своего решения!

#include <iostream> // algorithm,string,list,cctype,functional,boost/assign.hpp
using namespace std;

struct remove_from {
    remove_from(string& text) : text(text) { }
    void operator()(const string& str) {
        typedef string::iterator striter;
        striter e(search(text.begin(), text.end(), str.begin(), str.end()));
        while( e != text.end() ) {
            striter b = e;
            advance(e, str.length());
            e = find_if(e, text.end(), not1(ptr_fun<int,int>(isspace)));
            text.erase(b, e);
            e = search(text.begin(), text.end(), str.begin(), str.end());
        }
    }
private:
    string& text;
};

int main(int argc, char* argv[])
{
    list<string> toremove = boost::assign::list_of("solution")("movie");
    string text("This amazing new wearable ...");
    for_each(toremove.begin(), toremove.end(), remove_from(text));
    cout << text << endl;
    return 0;
}
1 голос
/ 12 апреля 2010

Вы можете просто проверить desc.size () - если он меньше, чем индекс, который вы ищете + 1, тогда вы получите исключение

0 голосов
/ 12 апреля 2010

Проблема в том, что вы начинаете итерацию с первого слова, затем пытаетесь проверить слово перед ним, следовательно, исключение OutOfRange.

Ваш первый, если может быть:

if( loc1 != string::npos && loc1 != 0)
...