2012-02-24 35 views
5

Mã này:In chuỗi mà không cần thoát nhân vật

void Controller::write(const std::string& str) { 
    std::cout << "Writing: [" << str << "] to board." << std::endl; 
    s.write(str); 

mất một string và đẩy nó qua một liên kết nối tiếp với một vi điều khiển. (Điều này làm việc tốt). Tuy nhiên, khi tôi cố gắng đẩy một như thế này: write("ats203?\r"), giao diện điều khiển đầu ra trông như thế này:

] to board.ts203? 

Vì vậy, các Writing: [a bị ghi đè bởi ] to board. sau std::cout gặp các \r trong chuỗi.

Làm cách nào để in chuỗi dưới dạng một chuỗi ký tự thay vì xuất ra bàn điều khiển xén khi gặp phải ký tự thoát?

EDIT: Để làm rõ.

I muốn chuỗi của tôi là ats203?\r. Điều này là do vi điều khiển được điều khiển bằng phiên bản được sửa đổi đôi chút của AT commandkhông chấp nhận lệnh cho đến khi nó đọc một số \r. Khi chuỗi được đẩy vào bộ vi điều khiển, nó đọc số \r dưới dạng dấu xuống dòng và hành động theo thứ mà nó đọc trước số \r.

Điều tôi muốn là hiển thị chuỗi mà tôi đã tạo. Có một loạt các lệnh khác ở nơi khác được tạo tùy thuộc vào các cờ được đặt ở thời gian chạy. Vì vậy, tôi kết thúc với chuỗi trông giống như ate1\ratv0\rat+OSA=7\rat+OSX=255\r.

Tôi muốn xem những gì tôi đã xây dựng và những gì tôi đang thúc đẩy. Tôi không thể làm điều này, bởi vì std::cout đọc trả lại vận chuyển, hành động trên nó, và mangles đầu ra giao diện điều khiển của tôi.

EDIT: Làm rõ, một lần nữa: Tôi muốn std::cout << "Writing: [" << str << "] to board." << std::endl; để sản xuất (khi strats203?\r):

Writing: [ats203?\r] to board. 
+3

Bạn có thể thoát khỏi nhân vật chạy thoát, vì vậy '\\ r' sẽ rời khỏi chuỗi như một chữ ' "\ r"'. ..không chắc chắn nếu đó là những gì bạn muốn hay không. – prelic

+0

Tôi không hiểu, tại sao có một '\ r' trong chuỗi của bạn ngay từ đầu? Bạn muốn xuất kết quả nào? –

+0

'\ r' là ký tự trả về dấu - nó sẽ làm cho" con trỏ "nhảy trở lại đầu dòng. Có lẽ bạn muốn ký tự dòng mới, '\ n'? – jrok

Trả lời

5
void Controller::write(const std::string& command_string) { 

    std::string display_string = std::regex_replace(command_string,std::regex("(\r)"),"\\r"); 

    std::cout << "Writing: [" << display_string << "] to board.\n"; 
    s.write(command_string); 

Vì vậy, sau đó write("ats203?\r") theo nghĩa đen sẽ in ra

ats203?\r 
1

Nó không phải là chính xác 'mangling' các nhân vật vì một dãy thoát. '\ R' đặt lại con trỏ của bạn tức là nó là một trở về vận chuyển. Do đó, con trỏ của bạn đi đến đầu và bất cứ điều gì là gõ bây giờ ghi đè lên bất cứ điều gì là có trên đường dây.

Bạn chỉ có thể xóa bất kỳ trường hợp \r trong chuỗi của bạn:

void Controller::write(const std::string& str) { 
    std::string str2(str); //Make a copy of the string as you are getting a const reference 
    char remove[] = "\r"; //Add any characters you wish to remove 

    for (unsigned int i = 0; i < sizeof(chars); ++i) { 
     str2.erase(std::remove(str2.begin(), str2.end(), chars[i]), str2.end()); 
    } 

    std::cout << "Writing: [" << str2 << "] to board." << std::endl; 
    s.write(str); 
} 

LƯU Ý: remove là một chức năng trong <algorithm>, vì vậy đừng quên #include <algorithm>.

EDIT: Mã để tạo một bản sao thêm, nhờ jrok để chỉ một mà ra :)

+0

Bạn không thể làm điều này, 'str' là const. – jrok

+0

Ồ .. Tôi không thấy điều đó. Tôi sẽ thay đổi. –

+0

Nếu không có giải pháp nào tốt hơn, tôi có thể loại bỏ các ký tự vi phạm trước khi tôi hiển thị chúng; Tôi đã hy vọng có một cách tôi sẽ không phải làm điều đó, mặc dù. – simont

1

Bạn có thể viết một hàm để không dò tìm những ký tự.Ví dụ:

#include <string> 
#include <iostream> 

std::string unescape(const std::string& str){ 

    std::string res; 
    for(int i=0; i<str.length(); ++i){ 
     switch (str[i]){ 
      case '\r': 
       res+="\\r"; 
       break; 
      case '\n': 
       res+="\\n"; 
       break; 
      case '\\': 
       res+="\\\\"; 
       break; 
      case '\t': 
       res+="\\t"; 
       break; 
      //add other special characters if necessary... 
      default: 
       res += str[i]; 
     } 
    } 
    return res; 
} 

int main(){ 
    std::cout << unescape("hello\r\nworld\tsome\\words") << std::endl; 
} 

Output:

hello\r\nworld\tsome\\words 
2

Dưới đây là một vòng lặp nhanh chóng để tạo ra một chuỗi có thể đọc được.

std::string str2; 
for (int i = 0; i < str.length(); ++i) 
{ 
    if (str[i] == '\r') 
    { 
     str2.push_back('\\'); 
     str2.push_back('r'); 
    } 
    else 
     str2.push_back(str[i]); 
} 
Các vấn đề liên quan