C++ Primer学习 《Arrays》

来源:互联网 发布:git 安装使用centos 编辑:程序博客网 时间:2024/06/16 06:12

Arrays

array和vector类似,但是array性能更好,灵活性较差(trade-off between performance and flexibility)。

初始化array

const unsigned sz = 3;int ia1[sz] = {0,1,2};int a2[] = {0,1,2};int a3[5] = {0,1,2};//a3[] = {0,1,2,0,0};string a4[3] = {"hi","bye"};//a4[] = {"hi","bye",""};int a5[2] = {0,1,2};//error!
character array

一种和string有些类似的东西,叫做character array,虽然在C++语言中不常见,但有一些特殊用处,如声明的字符串中包含一些特殊字符时。

需要注意的是,character array必须以空字符('/0'))结尾,否则计算机无法知道该字符串终结处,而这个空字符是计入array大小中的(和std::string不同,string.size()是不包含空字符的,事实上std::string是一个类,因此根本就没有空字符!)

char a1[] = {'c','+','+'};//size = 4char a2[] = {'c','+','+','\0'};//size = 4char a3[] = "C++";//size = 4char a4[6] = "Daniel";//error! no space for the null!
no copy or assignment

array不能copy创造,也不能赋值。

int a2[] = a;//error! no copy!a2 = a;//error! no assignment!

我们知道,array本质是一个指针。然而,和指针的区别是,指针是可修改的左值,但array不是!

复杂的array声明

结合了指针(*)和引用(&)后,array的声明会有一些晦涩。

关键在于,从内往外看(inside out)!而不是从右往左看。

int (*parray)[10] = &arr;//parray是一个pointer,points to an array of ten intsint (&arrRef)[10] = arr;//arrRef是一个reference,refers to an array of ten ints
begin 和 end

C++ 11中为array也提供了begin和end,cbegin和cend函数哦!

int *pbeg = begin(a), *pend = end(a);for (; pbeg < pend; pbeg++){cout << *pbeg << endl;}


Multidimensional Array

初始化一个多维数组

int ia[3][4] = {    {0,1,2,3},    {4,5,6,7},    {8,9,10,11}};int ia[3][4] = {0,1,2,3,4,5,6,7,8,9,10,11};
上面两种初始化方法是等价的,但是第一种显然要清晰得多!

使用"{}",我们显式地把每一行(更准确的说是,每一个子数组)分开了。

int ia[3][4] = {{0},{4},{8}};int ia[3][4] = {0,3,6,9};
上面第一行表示:前四个都是0,然后四个都是4,然后四个都是8.

上面第二行,只对前四个赋值,剩下8个都是0.

range for 和 multidimensional array

当我们使用range for和multidimensional array时,有一个不容易察觉的致错因素。

<pre name="code" class="cpp">int ia[3][4] = {0};for(auto row:ia){    for(auto col:row){        ...    }}

上面这段代码看似没问题,我们先遍历ia的每一行,然后遍历ia每一行的每一个元素。但是,这是不能编译通过的!

这是因为,compiler会默认把array转换成pointer,所以这里row的类型是int*,而我们不能遍历一个int*数据。

正确的做法是:

int ia[3][4] = {0};for(auto & row:ia){    for(auto col:row){        ...    }}
注意区别就在于,多了一个"&"!!当我们这样做后,编译器就不会把array转换成pointer,因此,row也是一个array,其格式是int[4],所以可以再次遍历。

总结:当我们在range for中使用multidimensional array时,除了最里面一个for,其他所有的for都应该是reference!

Pointer和Multidimensional Arrays

除了用range for遍历multidimensional array,我们也可以用pointer来遍历,在C++ 11中,有以下两种较为简洁的遍历方法。

int ia[3][4] = { 0 };for (auto p = ia; p < ia+3; p++){for (auto q = *p; q < *p + 4; q++){cout << *q << endl;}}

int ia[3][4] = { 0 };for (auto p =begin(ia); p != end(ia); p++){for (auto q = begin(*p); q != end(*p); q++){cout << *q << endl;}}


type aliases和multidimensional array

如果利用type alias,我们也可以完成上述的类似功能。

using int_array = int[4];typedef int int_array[4];//这两个是等价的for(int_array *p = ia;p!=ia+3;++p){    for(int *q = *p;q!=*p+4;++q)        cout<<*q<<endl;}



0 0
原创粉丝点击