2017-04-07 146 views
2

現在,當我瞭解代碼的工作原理時,我想將其轉換爲C++。將代碼從Python轉換爲C++

原來的Python代碼:

def recv_all_until(s, crlf): 
    data = "" 
    while data[-len(crlf):] != crlf: 
     data += s.recv(1) 
    return data 

這裏是我的嘗試:

std::string recv_all_until(int socket, std::string crlf) 
{ 
    std::string data = ""; 
    char buffer[1]; 
    memset(buffer, 0, 1); 


    while(data.substr(data.length()-2, data.length()) != crlf) 
    { 
     if ((recv(socket, buffer, 1, 0)) == 0) 
     { 
      if (errno != 0) 
      { 
       close(socket); 
       perror("recv"); 
       exit(1); 
      } 
     } 
     data = data + std::string(buffer); 
     memset(buffer, 0, 1); 
    } 

    return data; 
} 

但它顯示:

terminate called after throwing an instance of 'std::out_of_range' 
    what(): basic_string::substr 

據我所知,這個問題是while循環,因爲裏面首先數據字符串是空的。那麼如何改進它使它和Python一樣工作呢?謝謝。

+1

僅供參考,Python字符串有這使得該方法'endswith'你的while循環意圖更清晰:'while data.endswith(crlf)'。考慮到這一點,[此SO回答](http://stackoverflow.com/a/2072890/4859885)爲您提供了一個非常優雅的解決方案。 –

回答

1

如果我們先改變你的Python代碼位:

def recv_all_until(s, crlf): 
    data = "" 
    while not data.endswith(crlf): 
     data += s.recv(1) 
    return data 

我們需要在C++做什麼變得更加清晰:

bool ends_with(const std::string& str, const std::string& suffix) 
{ 
    return str.size() >= suffix.size() && 
     std::equal(suffix.rbegin(), suffix.rend(), str.rbegin()); 
} 

std::string recv_all_until(int socket, const std::string& crlf) 
{ 
    std::string data = ""; 
    char buffer[1]; 
    memset(buffer, 0, 1); 

    while (!ends_with(data, crlf)) 
    { 
     if ((recv(socket, buffer, 1, 0)) == 0) 
     { 
      if (errno != 0) 
      { 
       close(socket); 
       perror("recv"); 
       exit(1); 
      } 
     } 
     data = data + std::string(buffer); 
     memset(buffer, 0, 1); 
    } 

    return data; 
} 
2

您的while循環的第一次迭代的問題:

由於data是空stringdata.length()等於0,因此你打電話data.substr(-2, 0)

要解決此問題,您需要在while語句中添加一行檢查行長。

另外,還有一種方法可以比編寫有關它的stackoverflow問題更快地找到這樣的錯誤。考慮閱讀this文章。