提纲
- 数组类型
- 字符串类型
- 结构体、共用体
- 枚举
- 指针
- 动态数组
- 动态结构
- 自动存储、静态存储和动态存储
一、数组类型
数组的声明
- int yams[3];
- yams[0] = 7;
- yams[1] = 8;
- yams[2] = 6;
- int yamcosts[3] = {20,30,5};
感觉不好的是,在C++中不能以int[] yam[3]这种方式声明数组。
数组初始化的一些规则:
1.提供的值可以少于数组的长度
2.只有在定义数组时才能使用初始化。
像以这种方式声明数组在C++中却编译不通过,在java中这样写完全是可以的。
- int hand[] ={1,2,3,4};
- int card[] = hand;
二、字符串
字符串是存储在内存中连续字节的一系列字符。C++处理字符串有两种方式,一是字符数组,这是来源于C的处理方式;二是C++中的string类型。
1.以字符数组方式声明字符串
- char name1[] = {'s','u','n','y','y'};//不是字符串,长度为5
- char name2[] = {'s','u','n','y','y','/0'};//是字符串,因为有'/0'结尾,长度为6
- char name3[] = "sunny";
看两个简单的小例子
- #include <iostream>
- #include <cstring>
- int main()
- {
- using namespace std;
- const int SIZE = 15;
- char name1[SIZE];//空数组
- char name2[SIZE] = "C++owboy";//初始化的数组
- cout<<"Howdy!I'm "<<name2;
- cout<<"!What's your name?/n";
- cin>>name1;
- cout<<"Well,"<<name1<<",your name has ";
- cout<<strlen(name1)<<" letters and is stored/n";//要使用strlen()方法,需要使用cstring头文件
- cout<<"in an array of "<<sizeof(name1)<<" bytes./n";
- cout<<"Your initial is "<<name1[0]<<"./n";
- name2[3] = '/0';
- cout<<"Here are the first 4 characters of my name:";
- cout<<name2<<"/n";//这里输出C++,'/0'结束符作为第四个字符。
- return 0;
- }
- #include <iostream>
- int main()
- {
- using namespace std;
- const int SIZE = 20;
- char name[SIZE];
- char dessert[SIZE];
- cout<<"Enter your name:/n";
- cin>>name;//输入Sunny Peng
- cout<<"Enter your favorite dessert:/n";
- cin>>dessert;
- cout<<"I have some delicious "<<dessert;
- cout<<" for you,"<<name<<"./n";
- /*
- 我还未给dessert变量赋值,程序就已经输出结果了。
- 第一个cin读取的是Sunny,第二个cin读取的是Peng
- 这是因为cin以空白符来界定字符串的,它只能识别单个单词,而不能识别语句。
- */
- return 0;
- }
第二个例子存在一点点小问题,但是C++提供了getline(),get()函数来解决这个问题。这两个函数是用来读取行的,在前一节中我知道cin是istream类的一个对象,那么调用的方式就很简单的,cin.get()或cin.getline(char arr[],int len)。
- /************************************************************************/
- /* cin.getline()例子 */
- /************************************************************************/
- #include <iostream>
- int main()
- {
- using namespace std;
- const int SIZE = 20;
- char name[SIZE];
- char dessert[SIZE];
- cout<<"Enter your name:/n";
- cin.getline(name, SIZE);//读取行
- cout<<"Enter your favorite dessert:/n";
- cin.getline(dessert, SIZE);
- cout<<"I have some delicious "<< dessert;
- cout<<" for you,"<<name<<"./n";
- return 0;
- }
- /************************************************************************/
- /* cin.get()例子 */
- /************************************************************************/
- #include <iostream>
- int main()
- {
- using namespace std;
- const int SIZE = 20;
- char name[SIZE];
- char dessert[SIZE];
- cout<<"Enter your name:/n";
- //在读取行时,带参数的get函数并不丢弃换行符,但是不带参数的get()函数能通过读取一个字符来处理换行符。
- //同时这里也是函数重载的使用
- cin.get(name, SIZE).get();
- cout<<"Enter your favorite dessert:/n";
- cin.get(dessert,SIZE).get();
- cout<<"I have some delicious "<<dessert;
- cout<<" for you,"<<name<<"./n";
- return 0;
- }
2.string类
上面那种处理字符串的方式是C风格,用起来麻烦而且比较局限。
C++提供了string类来处理字符串,在使用时也不必像上面那种比较麻烦的方式,string类提供了一些处理字符串的函数,用起来直观而且方便。
string类在命名空间std中,使用string类,需要引入std::string命名空间。
- /************************************************************************/
- /* String例子 */
- /************************************************************************/
- #include <iostream>
- #include <string>
- #include <cstring>//C风格的字符串处理类
- int main()
- {
- using namespace std;
- char charr[20];
- string str;
- //在计算未初始化的字符数组长度时,空字符出现的位置是随机的,可能strlen()计算的结果比数组本身长度还要大。
- cout<<"Length of string in charr before input:"<<strlen(charr)<<endl;
- cout<<"Length of string in str before input:"<<str.size()<<endl;
- cout<<"Enter a line of text:/n";
- cin.getline(charr,20);
- cout<<"You entered:"<<charr<<endl;
- cout<<"Enter another line of text:/n";
- getline(cin,str);//把cin对象作为参数,并且不需要为输入的字符串指定长度。
- cout<<"Your entered:"<<str<<endl;
- cout<<"Length of string in charr after input:"<<strlen(charr)<<endl;
- cout<<"Length of string in str after input:"<<str.size()<<endl;
- }
三、结构体、共用体
1.结构体
一个结构体可以存储多种类型的数据,结构体中的成员很像在类中声明的字段,但是结构体没有方法,结构体是一种比较灵活的数据格式。
- /************************************************************************/
- /* 结构体例子 */
- /************************************************************************/
- #include <iostream>
- //声明结构体和声明类差不多,使用的时候直接为结构体赋值,而不需像类那样来new
- //结构体可以声明在函数内部或外部,就跟局部变量和全局变量一样,只是作用域不同。
- //关键字struct只是表明inflatable是结构体,而数据类型为inflatable;就好比声明 class Test,Test是一种数据类型一样
- struct inflatable
- {
- char name[20];
- float volume;
- double price;
- };
- int main()
- {
- using namespace std;
- inflatable guest =
- {
- "Glorious Gloria", //name
- 1.88, //volume
- 29.99 //price
- };
- inflatable pal =
- {
- "Audacious Arthur",
- 3.12,
- 32.99
- };
- cout<<"Expand your guest list with "<<guest.name;
- cout<<" and "<<pal.name<<"!/n";
- cout<<"You can have both for $";
- cout<<guest.price + pal.price <<"!/n";
- return 0;
- }
试想想,如果一个函数需要不同类型的多返回值如何实现?在一般情况下,可以通过在类中声明全局的字段来解决这个问题,但是这时候函数的返回类型为void。在学习了结构体以后,我可以在适当的情况下通过结构体来处理函数多返回值的问题,结构体还真是一种比较轻便灵活的数据类型。
2.共用体
共用体类似于结构体,它也能够存储多种数据格式,但是共用体只能同时存储一种数据类型。
例如声明了如下的一个共用体,有3个成员变量,但是在使用时只能使用其中一个,在代码段中,如果先后为int_val,long_val,double_val成员赋值,那么当前共用体中存储的是double_val的值,其他成员的值为0(因为是数值类型,所以为0)。共用体在内存中的空间为最大成员所占的空间。共用体有点多态的嫌疑,这个共用体既可以是int,也可以是long,还可以是double。共用体也是一种比较灵活的数据类型,在有些情况下可以使用它来做数据类型兼容。
- union one4all
- {
- int int_val;
- long long_val;
- double double_val;
- };
四、枚举
枚举可以用于创建一组符号常量,使用起来也极其方便,用枚举通过这些符号常量名我可以知道它所代表的含义。
- /************************************************************************/
- /* 枚举例子 */
- /************************************************************************/
- #include <iostream>
- enum week
- {
- Sunday,
- Monday,
- Tuesday,
- Wednesday,
- Thursday,
- Friday,
- Saturday
- };
- int main()
- {
- using namespace std;
- cout<<Sunday<<endl;
- return 0;
- }
如果在声明枚举时为枚举中的每个常量赋了值,那么在使用该枚举时,只能使用这几个值,超出这些值范围的使用将是不合法的。