2014-01-12 29 views
0

在我的應用程序中,我有一個字符串矢量。在這個矢量中,我有各種字符串,並想從我的矢量字符串中只包含字母。我寫的是這樣的:如何從字符串中刪除字符?我的代碼不會刪除我需要刪除的每個字符串

#include <iostream> 
#include <vector> 
#include <string> 
#include <algorithm> 
using namespace std; 

bool lettersOnly(std::string text) 
{ 
    for(int i=0; i<text.length(); i++) 
    { 
     if(!isalpha(text.at(i))) 
      return false; 
    } 
    return true; 
} 

void removeWordsWithLettersOnly(std::vector<std::string> &vec) 
{ 
    for(int i=0; i<vec.size(); i++) 
    { 
     std::string text = vec.at(i); 
     if(lettersOnly(text)) 
      vec.erase(remove(vec.begin(), vec.end(), text), vec.end()); 
    } 
} 

int main() 
{ 
    vector<string> vec; 

    vec.push_back("Someletters"); 
    vec.push_back("Bomeletters"); 
    vec.push_back("someletters"); 
    vec.push_back("123456543"); 
    vec.push_back("098765"); 
    vec.push_back("someletters"); 
    vec.push_back("someletters"); 
    vec.push_back("someletters234567"); 

    for(int i=0; i<vec.size(); i++) 
     cout << vec[i] << "\n"; 

    cout << "\n\n\n"; 
    removeWordsWithLettersOnly(vec); 

    for(int i=0; i<vec.size(); i++) 
     cout << vec[i] << "\n"; 

    return 0; 

} 

的問題是,曾經我用我的方法,我的載體,它不會刪除每個字符串應該。對於我上面的示例代碼,它不會刪除字符串Bomeletters。這是爲什麼?這個字符串只有字母,所以應該刪除。有任何想法嗎?

回答

4

您的循環通過從腳下移除元素來複雜化事物。

您可以簡單地使用std::remove_if與謂詞是這樣的:

void removeWordsWithLettersOnly(std::vector<std::string> &vec) 
{ 
    vec.erase(remove_if(vec.begin(), vec.end(), lettersOnly), vec.end()); 
} 

有了到位,你的代碼按預期工作。

請注意,您的lettersOnly謂詞正在爲傳遞給它的每個字符串做不必要的副本。您可以通過它的參數const引用,而不是解決這個問題:

bool lettersOnly(const std::string& text) { /* as before */ } 
+1

也用'std :: find_if_not(...,:: isalpha)== end'代替'lettersOnly'。 – chris

+0

@chris或'std :: all_of' – juanchopanza

+0

這樣會更好,是不是:p – chris

2

您從向量同時迭代它刪除。

例如: 當「Someletters」被刪除時 - >您的向量尺寸減小,現在「Bomeletters」位於位置0.但是您的計數器i已經位於位置1 - >因此錯過了「Bomeletters」。

解決此問題的最簡單方法是將未過濾的字符串複製到新的向量中,然後使用「swap()」替換2個向量的內容。