1

コードの繰り返しを簡単に削除する方法を考えています。使用可能か、良いか、アップグレードしようかどうかを理解するのを手伝ってください。

struct NetAdres
{
    /*#1*/NetAdres(const std::string &str, uint16_t port);  //#1
    /*#2*/NetAdres(std::string &&str, uint16_t port) : NetAdres(std::move(str), port) {};  //#2
    /*#3*/NetAdres(const char *str, uint16_t port) : NetAdres(std::string(str), port) {};  //#3
}

この呼び出し

NetAdres("192.168.2.3", 80);

私が呼び出しを理解する限り#3-> #2-> #1. そして、この呼び出し

NetAdres(std::string("192.168.2.3"), 80);

#2-> #1. そのような実装は余分なコピーを提供しませんstd::stringか?

4

1 に答える 1

2

考えられる解決策の 1 つは、値渡しです。たとえば、次のようになります。

struct NetAddress
{
    std::string addr_;
    uint16_t port_;
    NetAddress(std::string addr, uint16_t port)
        : addr_(std::move(addr)) // <--- always involves one move
        , port_(port)
    {}
};

そして、次のように呼び出します。

NetAddress a("example.com", 443);

// or
std::string addr("example.com");
NetAddress b(addr, 443);

// or with move
NetAddress c(std::move(addr), 443); 

欠点は、std::move省略される場合とされない場合がある 1 つが常に含まれることです。

g++-6.2および pre-C++11ではstd::string、 の最後の行でstd::move最短のアセンブリ コードが生成されます。

于 2016-11-18T18:50:46.733 に答える