C 11新特性(一)

2021-10-03 20:02:10 字數 4885 閱讀 1306

【侯捷-c++11新特性-】

variadic templates

uniform initialization

initializer lists

alias template

用例

void

print()

template

<

typename t,

typename..

. types>

void

print

(const t& firstarg,

const types&..

. args)

void

main()

c++11之前,變數的初始化操作可以用小括號,大括號,或者是賦值操作。常常使人困惑。在c++11之後,提供統一的大括號初始化方式。

用例

void

main()

; vector<

int> v

; vector cities

; complex<

double

> c

;}

兩個注意點
int i;

// i 沒有被初始化

int j

;//j 被初始化為 0

int*p;

//p沒有被初始化

int*q

;//q被初始化為空指標

intx1(

5.3)

;//warning

int x2 =

5.3;

//warning

int x3

;//error, 收縮轉換報錯

int x4 =

;//error, 收縮轉換報錯

char c

;//ok

char c2

;//error

vector<

int> v1

;//ok

vector<

int> v2

;//error

用例

void

print

(initializer_list<

int> vals)

}void

main()

);}

原始碼
template

<

class

_elem

>

class

initializer_list

constexpr

initializer_list

(const _elem *_first_arg,

const _elem *_last_arg)

noexcept

:_first

(_first_arg)

,_last

(_last_arg)

_nodiscard constexpr

const _elem *

begin()

const

noexcept

_nodiscard constexpr

const _elem *

end(

)const

noexcept

_nodiscard constexpr size_t size()

const

noexcept

private

:const _elem *_first;

const _elem *_last;

};

initializer_list 在標準庫中的應用
template

<

class

_ty>

_nodiscard constexpr _ty (max)

(initializer_list<_ty> _ilist)

//vector 的 insert 方法之一

iterator insert

(const_iterator _where, initializer_list<_ty> _ilist)

用例

template

<

typename t>

class

myalloc

;template

<

typename t>

using vec = std::vector>

;

之後就可以直接使用:

vec<

int> vec;

注意點

不能為你自己寫的模板別名寫偏特化或者全特化。

使用 #define 無法達到該目的

#define vectemplatestd::vector>;
那麼 vecvec 等價於:

template

<

typename

int> std::vector<

int, myalloc<

int>>

;

顯然不對

使用 typedef 也無法達到目的,它不能實現模板別名,只能實現:

typedef std::vector<

int, myalloc<

int>> vec

應用

比如說我現在想實現這樣乙個目的:寫乙個函式,這個函式能夠對傳入的容器進行複製,返回乙個新的容器,傳入的容器可能是 vector,list等任何擁有 push_back成員函式的容器。

初步的想法可能是這樣子的,想通過模板類實現:

template

<

typename container,

typename t>

container

copycontainer

(container container, t item)

但是此時編譯器會報錯,說 模板引數 「container」 不能包含模板引數列表。因為編譯器無法判斷出模板引數container是模板,所以報錯。

那麼這個時候,我們可能又會想到使用模板的模板,把 container定義為乙個模板,同時又作為乙個模板引數。**如下:

template

<

typename t,

template

<

typename

>

typename container>

container

copycontainer

(container container)

這個時候能夠編譯通過,讓我們來使用試試:

vector<

int> v

;auto copy =

copycontainer

(v);

這個時候,編譯器又會報錯,說沒有與引數列表匹配的 函式模板 「copycontainer」 例項,這又是為什麼呢??

究其原因,其實是這樣的:傳入的引數是 vector容器,而vector容器的定義是這樣子的:

template

<

typename _ty,

typename _alloc = allocator<_ty>>

class

vector

;

它是需要兩個模板引數的,而我們在 copycontainer 函式中所定義的模板引數container只有乙個模板引數 t,而沒有相對應的 allocator,因此報錯。

我們或許可以這樣改:

template

<

typename t,

template

<

typename f,

typename _alloc = allocator>

typename container>

container

copycontainer

(container container)

但是這個時候,其實就可以使用 alias template 了:

template

<

typename t,

template

<

typename

>

typename container>

container

copycontainer

(container container)

template

<

typename t>

using vec = vector>

;int

main()

;auto copy = copycontainer<

int, vec>

(v);

return0;

}

注:

其實如果是想獲得容器中的元素型別,其實也可以用 iterator 的萃取機去獲得,**如下:

typedef

typename std::iterator_traits<

typename container::iterator>

::value_type valtype;

valtype 就是容器類的元素型別。

C 11新特性學習

lambda表示式用於建立匿名的函式物件,語法為 函式可訪問的的外部變數 函式引數 返回值型別 如 int a 1,b 2 int c b int x int b 表示函式中可以訪問外部變數b,而且引數b是按值傳遞,b 表示引數b是按引用傳遞,表示可以訪問所有外部變數,並且是用按值傳遞方式,類似,也...

C 11 新特性試用

在c 11之前,auto關鍵字用來指定儲存期。在新標準中,它的功能變為型別推斷。auto現在成了乙個型別的佔位符,通知編譯器去根據初始化 推斷所宣告變數的真實型別。各種作用域內宣告變數都可以用到它。例如,名空間中,程式塊中,或是for迴圈的初始化語句中。auto i 42 i is an int a...

C 11 新特性總結

vs2012以上版本支援 一.auto的使用 auto func less 自動表示函式指標 auto ite vector a.begin 自動表示stl的迭代器 auto p new foo 自動表示變數指標等變數 二.decltype int x 3 decltype x y x 從變數或表示...