2012-02-19 8 views
3

理解することが説明が必要:私はASIO仕事を高める方法を理解しようとしているJavaプログラマだは私がフルで見ていたサンプルはASIO REFERENCE_COUNTED例

#include <boost/asio.hpp> 
#include <boost/bind.hpp> 
#include <boost/enable_shared_from_this.hpp> 
#include <boost/shared_ptr.hpp> 
#include <iostream> 
#include <vector> 

using boost::asio::ip::tcp; 

// A reference-counted non-modifiable buffer class. 
class shared_const_buffer 
{ 
public: 
    // Construct from a std::string. 
    explicit shared_const_buffer(const std::string& data) 
    : data_(new std::vector<char>(data.begin(), data.end())), 
     buffer_(boost::asio::buffer(*data_)) 
    { 
    } 
    // Implement the ConstBufferSequence requirements. 
    typedef boost::asio::const_buffer value_type; 
    typedef const boost::asio::const_buffer* const_iterator; 
    const boost::asio::const_buffer* begin() const { return &buffer_; } 
    const boost::asio::const_buffer* end() const { return &buffer_ + 1; } 

private: 
    boost::shared_ptr<std::vector<char> > data_; 
    boost::asio::const_buffer buffer_; 
}; 

class session 
    : public boost::enable_shared_from_this<session> 
{ 
public: 
    session(boost::asio::io_service& io_service) 
    : socket_(io_service) 
    { 
    } 

    tcp::socket& socket() 
    { 
    return socket_; 
    } 

    void start() 
    { 
    using namespace std; // For time_t, time and ctime. 
    time_t now = time(0); 
    shared_const_buffer buffer(ctime(&now)); 
    boost::asio::async_write(socket_, buffer, 
     boost::bind(&session::handle_write, shared_from_this())); 
    } 

    void handle_write() 
    { 
    } 

private: 
    // The socket used to communicate with the client. 
    tcp::socket socket_; 
}; 

typedef boost::shared_ptr<session> session_ptr; 

class server 
{ 
public: 
    server(boost::asio::io_service& io_service, short port) 
    : io_service_(io_service), 
     acceptor_(io_service, tcp::endpoint(tcp::v4(), port)) 
    { 
    session_ptr new_session(new session(io_service_)); 
    acceptor_.async_accept(new_session->socket(), 
     boost::bind(&server::handle_accept, this, new_session, 
      boost::asio::placeholders::error)); 
    } 

    void handle_accept(session_ptr new_session, 
     const boost::system::error_code& error) 
    { 
    if (!error) 
    { 
     new_session->start(); 
    } 

    new_session.reset(new session(io_service_)); 
    acceptor_.async_accept(new_session->socket(), 
     boost::bind(&server::handle_accept, this, new_session, 
      boost::asio::placeholders::error)); 
    } 

private: 
    boost::asio::io_service& io_service_; 
    tcp::acceptor acceptor_; 
}; 

int main(int argc, char* argv[]) 
{ 
    try 
    { 
    if (argc != 2) 
    { 
     std::cerr << "Usage: reference_counted <port>\n"; 
     return 1; 
    } 

    boost::asio::io_service io_service; 

    using namespace std; // For atoi. 
    server s(io_service, atoi(argv[1])); 

    io_service.run(); 
    } 
    catch (std::exception& e) 
    { 
    std::cerr << "Exception: " << e.what() << "\n"; 
    } 

    return 0; 
} 

、私は助けを必要といくつかのポイントがあります。私の質問は次のとおりです。

これらの行で
  1. const boost::asio::const_buffer* begin() const { return &buffer_; } 
    const boost::asio::const_buffer* end() const { return &buffer_ + 1; } 
    

    このshared_const_bufferは後でasync_writeに使用しているので、私はそれがバッファのいくつかの種類を実装する必要がありますが、私は任意の継承署名が表示されていないと思います。だからbegin()end()で十分ですか?

  2. そして、これらの行で

    shared_const_buffer buffer(ctime(&now)); 
    boost::asio::async_write(socket_, buffer, 
             boost::bind(&session::handle_write, 
                shared_from_this()));  
    

    share_const_bufferdata_が共有ポインタでありますが、それ自体、どのようにbuffer有効async_writeまで、実際にデータの書き込みを行うのですか?

答えて

1

このshared_const_buffer後でasync_write()に使用しているので、私はそれが バッファのいくつかの種類を実装する必要がありますが、私は任意の継承 署名が表示されていないと思います。だからbegin()end()で十分ですか?

shared_const_bufferクラスによって使用されるバッファは、_dataメンバー、boost::shared_ptr<std::vector<char> >あります。イテレータをバッファに公開すると、async_write()で十分です。

share_const_bufferdata_を持っているasync_write()は、実際にデータを書き込むまで がバッファ有効であるか、それ自身共有ポインタではなく?

shared_const_bufferクラスは、それがコピーされasync_writeを呼び出すときに、documentationは明示的に述べASIO ConstBufferSequenceタイプの要件

// Implement the ConstBufferSequence requirements. 
    typedef boost::asio::const_buffer value_type; 
    typedef const boost::asio::const_buffer* const_iterator; 
    const boost::asio::const_buffer* begin() const { return &buffer_; } 
    const boost::asio::const_buffer* end() const { return &buffer_ + 1; } 

を実装します。

バッファ

ワンまたはそれ以上のバッファconta書き込まれるデータを読み込む。 バッファオブジェクトは必要に応じてコピーできますが、 の所有権は呼び出し側によって保持されます。 は、ハンドラが呼び出されるまで有効であることを保証する必要があります。

ただし、基礎データはshared_ptrに保持されているためコピーされません。あなたは

は最後 shared_const_bufferが行くまで、だから、実際のバッファが有効のまま
Sam-Millers-MacBook-Pro:stackoverflow samm$ telnet localhost 1234 
Trying ::1... 
telnet: connect to address ::1: Connection refused 
Trying 127.0.0.1... 
Connected to localhost. 
Escape character is '^]'. 
Sun Feb 19 08:22:56 2012 
Connection closed by foreign host. 
Sam-Millers-MacBook-Pro:stackoverflow samm$ 

これは別のシェルで

Sam-Millers-MacBook-Pro:stackoverflow samm$ ./a.out 1234 
shared_const_buffer() 
~shared_const_buffer() buffer use count: 8 
~shared_const_buffer() buffer use count: 7 
~shared_const_buffer() buffer use count: 6 
~shared_const_buffer() buffer use count: 5 
~shared_const_buffer() buffer use count: 4 
~shared_const_buffer() buffer use count: 3 
~shared_const_buffer() buffer use count: 3 
~shared_const_buffer() buffer use count: 2 
handle_write 
~shared_const_buffer() buffer use count: 2 
~shared_const_buffer() buffer use count: 1 

--- reference_counted.cpp 2012-02-19 08:30:32.000000000 -0600 
+++ reference_counted_good.cpp 2012-02-19 08:26:27.000000000 -0600 
@@ -26,9 +26,7 @@ 
    : data_(new std::vector<char>(data.begin(), data.end())), 
     buffer_(boost::asio::buffer(*data_)) 
    { 
-  std::cout << "shared_const_buffer()" << std::endl; 
    } 
- ~shared_const_buffer() { std::cout << "~shared_const_buffer() buffer use count: " << data_.use_count() << std::endl; } 

    // Implement the ConstBufferSequence requirements. 
    typedef boost::asio::const_buffer value_type; 
@@ -66,7 +64,6 @@ 

    void handle_write() 
    { 
-  std::cout << "handle_write" << std::endl; 
    } 

private: 

いくつかのデバッグ文を散水し、

それを実行することで見ることができます見ることができますスコープ外にあり、ディスクリプタを実行する

+0

okie、java-worldでは、shared_const_bufferが必要一種のバッファを実装してベース型にキャストできるようにし、インタフェースメソッドを呼び出してバッファを取得します。 C++のshared_const_bufferの場合、どのくらいの量で動作しますか? – secmask

+0

私は他のテストを作成しました.C++は型チェックを必要としないので、shared_const_bufferは明示的にインターフェイスを実装する必要はありません。 – secmask

+0

@secmask Javaのように動作しなければならないと仮定して、C++プログラミングプロジェクトに近づくよう勧めません。 –

関連する問題