JFrame(用C++11特性重构系列——Lazy的实现)
1 #ifndef LAZY_H 2 #define LAZY_H 3 #include <Optional.hpp> 4 #include <functional> 5 6 template<typename T> 7 struct Lazy 8 { 9 Lazy(){} 10 template <typename Func, typename... Args> 11 Lazy(Func&& f, Args && ... args) 12 { 13 // 使用 lambda 来包装 函数 + 参数 14 m_func = [&f, &args...]{return f(args...); }; 15 // 也可以写为 16 // m_func = std::bind(f, std::forward<Args>(args)...); 17 } 18 19 T& Value() 20 { 21 if (!m_value) 22 { 23 m_value = m_func(); 24 } 25 26 return *m_value; 27 } 28 29 bool IsValueCreated() const 30 { 31 return m_value.IsInit(); 32 } 33 34 private: 35 std::function<T()> m_func; 36 Optional<T> m_value; 37 }; 38 39 template<class Func, typename... Args> 40 Lazy<typename std::result_of<Func(Args...)>::type> // 使用 std::result_of 推断出 Func 的返回类型 41 lazy(Func && fun, Args && ... args) 42 { 43 return Lazy<typename std::result_of<Func(Args...)>::type>(std::forward<Func>(fun), std::forward<Args>(args)...); 44 } 45 46 #endif // LAZY_H
使用到的 C++11 技术:
- 上一篇的 Optional
- std::bind
- std::function<T()>类型的赋值使用 lambda 包装
- std::result_of
测试代码:
1 void testLazy() 2 { 3 struct BigObj 4 { 5 BigObj() 6 { 7 std::cout << "created big obj.." << std::endl; 8 } 9 }; 10 11 struct MyStruct{ 12 MyStruct() 13 { 14 m_obj = lazy([]{ 15 return std::make_shared<BigObj>(); 16 }); 17 } 18 void Load() 19 { 20 m_obj.Value(); 21 } 22 Lazy<std::shared_ptr<BigObj>> m_obj; 23 }; 24 25 MyStruct ms; 26 ms.Load(); 27 28 }