VS2013 tuple 源碼分析

tuple這玩意實現方法就是遞歸方式展開函數包的完美示例。相關文章可以查看<深入應用C++11>3.2.1.1章節。

tuple的實現思想可以查看侯捷老師視頻:https://www.bilibili.com/video/BV1p4411v7Dh?p=20

假如我們現在有如下源碼:

tuple<int, double, char*> my_tuple = make_tuple(1,2.2,"love")

好吧來看 VS2013實現源碼:

	// CLASS tuple這裏是前置聲明
template<class... _Types>
	class tuple;

template<>//這裏是特化版本,爲了中止繼承
	class tuple<>
	{	
        //這裏沒有成員函數,什麼都不存
        }

//這裏是真正普通模板類
template<class _This,//_This 就對應我們上面例子中的1對應的 int 類型
	class... _Rest> //_Rest 就對應 double 和 char* 組成的一包
	class tuple<_This, _Rest...>
		: private tuple<_Rest...>//這裏繼承於自己,當然也不是自己,因爲模板參數不一樣
	{
public:
	typedef _This _This_type;
	typedef tuple<_This, _Rest...> _Myt;
	typedef tuple<_Rest...> _Mybase;
	static const size_t _Mysize = 1 + sizeof...(_Rest);

	_Tuple_val<_This> _Myfirst;	// the stored element//這裏存放第一個int類型的1
       }

 

	// CLASS tuple_element
template<size_t _Index,	class _Tuple>
	struct tuple_element;

template<class _This,class... _Rest>
	struct tuple_element<0, tuple<_This, _Rest...> >
	{	// select first element
	typedef _This type;
	typedef typename add_lvalue_reference<const _This>::type _Ctype;
	typedef typename add_lvalue_reference<_This>::type _Rtype;
	typedef typename add_rvalue_reference<_This>::type _RRtype;
	typedef tuple<_This, _Rest...> _Ttype;
	};

template<size_t _Index,	class _This,class... _Rest>
	struct tuple_element<_Index, tuple<_This, _Rest...> >//這裏tuple也會拆包,直到_Index爲0,此時我們想要取的值,爲此類型tuple的成員變量。
		: public tuple_element<_Index - 1, tuple<_Rest...> >//這裏_Index 會遞減,直到第一個模板參數爲0
	{	// recursive tuple_element definition
	};
	
// FUNCTION get
template<size_t _Index,	class... _Types> inline
	typename tuple_element<_Index, tuple<_Types...> >::_Rtype//這裏會根據_Types進行遞減
		get(tuple<_Types...>& _Tuple)//根據這裏的_Tuple能夠推導出tuple的一包參數_Types
	{	// get reference to _Index element of tuple
	typedef typename tuple_element<_Index, tuple<_Types...> >::_Ttype _Ttype;
	return (((_Ttype&)_Tuple)._Myfirst._Val);//_Ttype是存着我們那個值的基類,強轉即可
	}

編譯器編程可以運行期編程難多了。如果是運行期,可能會這樣:get(0),而編譯器是這樣get<0>()。妙哉妙哉。

	// CLASS _Ignore
class _Ignore
	{	// class that ignores assignments
public:
	_Ignore()
		{	// construct
		}

	template<class _Ty>//任何類型變量都可以賦值給此類型變量
		void operator=(const _Ty&) const
		{	// do nothing
		}
	};

const _Ignore ignore;
// FUNCTION tie
template<class... _Types> inline
	tuple<_Types&...>
		tie(_Types&... _Args) _NOEXCEPT
	{	// make tuple from elements
	typedef tuple<_Types&...> _Ttype;
	return (_Ttype(_Args...));//這裏很簡單就是把原tuple包賦值給現tuple包。
	}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章