让我坚定使用using而不是typedef进行类型声明的原因,除了因为它是新标准以外,更重要的就是using的模板声明能力。

首先考虑如下一个类中的各个回调函数的形式声明。可以看到,声明中多次使用了冗余的std::function。虽然使用的是using,但并没有体现出using的优势。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
class TcpConnectionPtr;

class TcpConnection : // noncopyable
public std::enable_shared_from_this<TcpConnection>
{
// kDisconnecting - LIKE POLLRDHUP, the write endian is closed
enum StateEnum {kConnecting, kConnected, kDisconnecting, kDisconnected};
using ConnectionCallback = std::function<void (const TcpConnectionPtr &)>;
// using MessageCallback = std::function<void (const TcpConnectionPtr &, const std::string &)>;
using MessageCallback = std::function<void (const TcpConnectionPtr &, muduo::net::Buffer *, muduo::Timestamp)>;
using CloseCallback = std::function<void (const TcpConnectionPtr &)>;
using WriteCompleteCallback = std::function<void (const TcpConnectionPtr &)>;
using HighWaterCallback = std::function<void (const TcpConnectionPtr &)>;
// ...
}

下面是改进版本。是不是简洁多了?^-^核心原因就是using的泛化能力,减少了重复代码的编写。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
class TcpConnectionPtr;

class TcpConnection : // noncopyable
public std::enable_shared_from_this<TcpConnection>
{
// kDisconnecting - LIKE POLLRDHUP, the write endian is closed
enum StateEnum {kConnecting, kConnected, kDisconnecting, kDisconnected};
// using ConnectionCallback = std::function<void (const TcpConnectionPtr &)>;
// // using MessageCallback = std::function<void (const TcpConnectionPtr &, const std::string &)>;
// using MessageCallback = std::function<void (const TcpConnectionPtr &, muduo::net::Buffer *, muduo::Timestamp)>;
// using CloseCallback = std::function<void (const TcpConnectionPtr &)>;
// using WriteCompleteCallback = std::function<void (const TcpConnectionPtr &)>;
// using HighWaterCallback = std::function<void (const TcpConnectionPtr &)>;
template<typename ...T>
using Callback = std::function<void(const TcpConnectionPtr &, T...)>;
using ConnectionCallback = Callback<>;
using MessageCallback = Callback<muduo::net::Buffer *, muduo::Timestamp>;
using CloseCallback = Callback<>;
using WriteCompleteCallback = Callback<>;
using HighWaterCallback = Callback<>;