日本免费高清视频-国产福利视频导航-黄色在线播放国产-天天操天天操天天操天天操|www.shdianci.com

學無先后,達者為師

網站首頁 編程語言 正文

boost.asio框架系列之buffer函數_C 語言

作者:天方 ? 更新時間: 2022-08-11 編程語言

創建buffer

在io操作中,對數據的讀寫大都是在一個緩沖區上進行的,在asio框架中,可以通過asio::buffer函數創建一個緩沖區來提供數據的讀寫。buffer函數本身并不申請內存,只是提供了一個對現有內存的封裝。

char?d1[128];
size_t?bytes_transferred = sock.receive(asio::buffer(d1));

直接用字符串做buffer也是常見的形式:

string?str =?" hello world "?;
size_t?bytes_transferred = sock.send(asio::buffer(str));

除了這些基礎類型外,也可以使用stl中的容器,非常方便。

asio::buffer(std::vector<char>(128));
asio::buffer(std::array<char,128>());

將buffer還原為數據對象

前面的操作是通過把數據對象封裝成buffer,在使用過程中往往也需要把buffer還原為數據對象。

char* p1 = asio::buffer_cast<char*>(buffer);

獲取buffer大小

可以通過buffer_size函數獲取buffer大小。

size_t?s1 = asio::buffer_size(buf);

讀寫buffer

讀寫buffer一般都是和io對象相關聯的,io對象成員函數中就提供了讀寫操作。以tcp::socket對象為例,它提供了read_some和write_some來實現讀寫操作:

std::array<char, 128> buf;
sock.read_some(asio::buffer(buf));

另外,asio名字空間下也提供了通用的read、write函數,通過它們可以實現更加高級的讀寫功能

size_t?bytes_transfered = asio::read(sock, asio::buffer(buf),?asio::transfer_all(), err);

這里我就使用了transfer_all標記強制讀滿buffer才返回,另外還有兩個比較常用的標記transfer_at_least()和transfer_exactly(),非常方便。

streambuf

asio::streambuf則是提供了一個流類型的buffer,它自身是能申請內存的。它的好處是可以通過stl的stream相關函數實現緩沖區操作,處理起來更加方便。

    //通過streambuf發送數據
    asio::streambuf b;
    std::ostream os(&b);
    os << "Hello, World!\n";

    size_t n = sock.send(b.data());    // try sending some data in input sequence
    b.consume(n); // sent data is removed from input sequence

 

    //通過streambuf讀數據
    asio::streambuf b;
    asio::streambuf::mutable_buffers_type bufs = b.prepare(512);    // reserve 512 bytes in output sequence
    size_t n = sock.receive(bufs);
    b.commit(n);    // received data is "committed" from output sequence to input sequence

    std::istream is(&b);
    std::string s;
    is >> s;

另外,asio名字空間下還提供了一個的read_until函數,可以實現讀到滿足指定條件的字符串為止,對于解析協議來說非常有用。

size_t?n = asio::read_until(sock, stream,?'\n');
asio::streambuf::const_buffers_type?bufs = sb.data();
std::string?line(asio::buffers_begin(bufs), asio::buffers_begin(bufs) + n);

這個指定條件除了是字符串外,還可以是正則表達式,非常給力。這也是asio庫為什么要依賴于boost.regex的原因。(雖然regex已經標準化了,但仍得使用boost.regex庫。等什么時候asio也標準化后估計就可以直接使用std.regex庫了)

自定義內存分配

異步IO操作時往往會申請動態內存,使用完后就釋放掉;在IO密集型的場景中,頻繁的申請釋放內存對性能會有較大影響。為了避免這個問題,asio提供了一個內存池式的模型?asio_handler_allocate?和?asio_handler_deallocate?來復用內存。

原文鏈接:https://www.cnblogs.com/TianFang/archive/2013/02/03/2890983.html

欄目分類
最近更新