【C】C语言数组与字符串(包括:字符串与字符数组) 您所在的位置:网站首页 在c语言中如何定义字符串的长度单位 【C】C语言数组与字符串(包括:字符串与字符数组)

【C】C语言数组与字符串(包括:字符串与字符数组)

2024-07-12 17:21| 来源: 网络整理| 查看: 265

在程序设计中,为了方便处理,通常把具有相同类型的若干变量按有序的形式组织起来。这些按序排列的同类数据元素的集合称为数组。在C语言中,数组属于构造数据结构。一个数组可以分解成多个数组元素,这些数组元素可以是基本数据类型或是构造类型。因此按照数组元素的类型不同,数组又可分为数值数组、字符数组、指针数组、结构数组等各种类别。

本文主要介绍一维数组、二维数组和字符数组,其余的数组将会在以后的文章中介绍到。

 

数组概述

数组就是用来存储和处理一组相同类型的数据的。

数组在C语言中有着特殊的地位,它有很多的特性,比如它的存储是连续的、数组的名称是数组的地址等。

一维数组

一维数组是使用同一个数组名存储一组数据类型相同的数据,用索引或下标区别数组中的不同元素。

一维数组的定义方式为: 类型说明符 数组名[常量表达式]

在定义数组时,应该注意以下几点:

数组使用的方括号[],不是小括号;常量表达式表示数据元素的个数,必须是一个正的整数值,不能含有变量,但是可以是符号常量或者常量表达式;数组定义后,其长度不可更改。 一维数组的数据元素的一般形式为: 数组名[下标]

在引用数组元素时,应该注意以下几点:

一位数组元素的下标从0开始,最大下标为n-1;在C语言中只能逐个地使用数组元素,而不能一次引用整个数组。 一维数组的初始化:除了用赋值语句对数组元素逐个赋值外,还可采用初始化赋值和动态赋值的方法。

初始化赋值的一般形式为:

类型说明符 数组名[常量表达式] = {初始值表}; int a[5]={1,2,3,4,5};

在初始化赋值时,应该注意以下几点:

数组定义时初始化可以整体赋初值,但是除了定义初始化之外,不能整体赋值!当初始值表给出全部元素值时,可以不给出数组元素的个数;可以只给部分数组中的部分元素赋初始值(没有赋值的位将补0)。也就是说可以这样: int a[]={1,2,3,4,5}; int b[5]={1,2,3}; 二维数组 二维数组定义的一般形式为: 类型说明符 数组名[常量表达式1][常量表达式2];

二维数组被定义后,编译系统将为该数组在内存中分配一片连续的存储空间,按行的顺序连续存储数组的各个元素。即先顺序存储第一行元素,再存储第二行元素……直到存储最后一行元素。数组名代表着数组的起始地址。

二维数组元素引用的基本语法格式为: 数组名[下标][下标] 初始化赋值的一般形式为: 类型说明符 数组名[常量表达式1][常量表达式2] = {初始值表}; int a[3][4] = { { 1,2,3,4 },{ 5,6,7,8 },{ 9,0,1,2 } };

由于二维数组在内存中是按照线性顺序存储的,所以内存括号可以省去,不会产生影响。也就是说可以这样:

int a[3][4] = { 1,2,3,4,5,6,7,8,9,0,1,2 };

在初始化赋值时,应该注意以下几点:

当初始值表给出全部元素值时,可以不给出二维数组的常量表达式1(但常量表达式2必须给);可以只给部分数组中的部分元素赋初始值(没有赋值的位将补0)。也就是说可以这样: int a[][4] = { { 1,2,3,4 },{ 5,6,7,8 },{ 9,0,1,2 } }; int a[][4] = { 1,2,3,4,5,6,7,8,9,0,1,2 }; int b[3][4] = { { 1 },{ 5 },{ 9 } };

在这里,省去3是可以的,但是4不能省去的。编译器会根据所附的数值的个数以及数组的列数,自动计算出数组的行数。

数组是一种构造类型的数据。二维数组可以看作是由一维数组的嵌套而构成的。设一维数组的每个元素都是一个数组,就组成了二维数组。当然前提是各元素的类型必须相同。根据这样的分析,一个二维数组也可以分解成多个一维数组。C语言允许这样的分解。如二维数组a[3][4],可以分解成3个一维数组,a[0]、a[1]、a[2]。

数组与链表的区别:

从逻辑结构上来看,数组必须实现定义固定的长度,不能适应数据动态增减的情况。当数据增加时,可能会造成空间的不够;当数据减少时,可能造成空间浪费。而链表动态地进行存储分配,可以适应数据动态增减的情况,方便插入和删除;从内存储存上来看,数组从栈中分配空间,方便快捷,但自由度小。而链表从堆中分配空间,自由度大,但申请管理比较麻烦。

 

字符数组与字符串 字符数组的说明与初始化

用于存放字符的数组称为字符数组,它是数组的一种特殊类型,字符数组的每个元素存放一个字符。

字符数组的定义的一般形式为: char 数组名[常量表达式]; char 数组名[常量表达式1][常量表达式2]; 字符数组的初始化:除了数组的基本初始化方式外,字符数组还可以使用字符串常量初始化。 char a[5]={'a','b','c','d','e'}; char a[]={'a','b','c','d','e'};

把一个字符串存入一个数组时,也会将结束符'\0'存入数组,并以此作为该字符串是否结束的标志。有了'\0'标志后,就不必再用字符数组的长度来判断字符串的长度了。

用字符串方式赋值比用字符逐个赋值要多占1个字节,用于存放字符串结束标志'\0'。以下三种初始化的效果是一样的:

char b[]={"How are you"}; char b[]="How are you"; char b[]={'H','o','w',' ','a','r','e',' ','y','o','u','\0'};

同时,需要注意:字符数组可以使用在定义初始化的时候用字符串初始化,但是不能使用赋值语句整体赋值:

char c[11] = "How are you";            /* 正确 */ char c[11]; c = "How are you";            /* 错误 */

为了证实'\0'的存在,例如:

#include int main() { int i; char c[] = "How are you!"; for (i = 0;; i++) { if (c[i] == '\0') break; } printf("%d\n", i); return 0; }

最终结果输出12,代表字符数组下标为12的字符是'\0',这与我们的理论是一致的。

字符串和字符数组

C语言中没有专门的字符串变量,如果要将一个字符串存放到某一个变量中,必须使用字符数组,即用一个字符数组来存放一个字符串,数组中每个元素存放一个字符。

字符串:必须以'\0'结尾;字符数组:可以包含多个'\0',也可以不包含'\0'。 字符串的处理函数

在采用字符串方式后,字符数组的输入/输出变得更加简单方便。除了可以使用字符串对字符数组赋初值的方法外,还可以用printf()函数和scanf_s()函数一次性输入/输出一个字符数组的所有字符,而不必利用循环单个操作。

C语言提供了大量的字符串处理函数,大致可以分为字符串的输入、输出、合并、修改、比较、转换、复制、搜索几类。

在使用输入/输出的字符串函数之前,需要包含头文件stdio.h;使用其他字符串函数之前,需要包含头文件string.h;

由于没有字符串变量这个说法,所以对任何字符串的操作都是将它放在字符数组里。

字符串输入函数gets()

从键盘上输入一个字符串(包括空格),赋予从字符数组起始的存储单元,直到读入一个回车符为止。回车符读入后,不作为字符串的内容,系统将自动用'\0'替换,作为字符串结束的标志。

char c[20]; gets(c); 字符串输出函数puts()

将字符数组起始地址开始的第一个字符串(以'\0'结束的字符序列)输出到显示器,并将字符串结束标志'\0'自动转换成'\n'。

char c[]="Hello!"; puts(c);

区分printf()与puts()、scanf_s()与gets()函数的区别:

puts()函数在遇到'\0'时,会自动转换成'\n'。而printf()函数则不输出'\0',同时也不输出'\n';gets()函数接受字符串,读入换行符才停止。而scanf_s()函数则读入到空格或者换行符就停止。 字符串长度函数strlen()

测试字符数组起始地址开始的字符串(以'\0'结束的字符序列)有效长度,此长度不包括'\0'在内。

char c[]="Hello"; printf("%d",strlen(c)); 字符串连接函数strcat() strcat(字符数组1,字符数组2);

将字符数组2连接到字符数组1之后,函数值为字符数组1的起始地址。连接字符数组1和字符数组2的尾部都有一个'\0',连接时将字符数组1后的'\0'自动取消,字符数组2后的'\0'一并连接到字符数组1后。

这里还有一个注意点:

#include int main() { char c1[20] = "Hello ";        /* 这里必须要指定足够的长度,否则会报错! */ char c2[] = "World!"; printf("%s", strcat(c1, c2)); return 0; }

字符数组1必须要足够长度,以便在其有效字符后能够容纳字符数组2的字符串。

字符串复制函数strcpy() strcpy(字符数组1,字符数组2);

将字符数组2复制到字符数组1中去,函数值为字符数组1的起始地址。字符数组1的长度能够容纳字符数组2的长度;将字符数组2的字符串结束标志'\0'一起复制到字符数组1中去了;同时,strcpy()函数能够将字符数组2前面若干个字符复制到字符数组1中,例如:

strcpy(字符数组1,字符数组2,长度); 字符串比较函数strcmp() strcmp(字符数组1,字符数组2);

将两个字符数组自左向右对应的字符逐个进行比较(按照ASCII码值大小比较),直到出现不同的字符或者遇到'\0'字符为止,函数值为一个整型。具体返回的情况如下表所示:

strcmp函数返回值 字符串大小情况返回值字符串1等于字符串20字符串1大于字符串21字符串1小于字符串2-1

 

关于数组的小例子

1、杨辉三角形:

#include int main() { int a[10][10],i,j; for (i = 0; i < 10; i++) { a[i][0] = 1; a[i][i] = 1; } for (i = 2; i < 10; i++) { for (j = 1; j < i; j++) { a[i][j] = a[i - 1][j - 1] + a[i - 1][j]; } } for (i = 0; i < 10; i++) { for (j = 0; j < i+1; j++) { printf("%d ", a[i][j]); } printf("\n"); } return 0; }

这段程序的运行结果为:

1 1 1 1 2 1 1 3 3 1 1 4 6 4 1 1 5 10 10 5 1 1 6 15 20 15 6 1 1 7 21 35 35 21 7 1 1 8 28 56 70 56 28 8 1 1 9 36 84 126 126 84 36 9 1 请按任意键继续. . .

2、找出下面程序中的错误:

#include int main() { unsigned char a[256], i; for (i = 0; i < 256; i++) { a[i] = i; } return 0; }

unsigned char的取值范围为0-255,当i最大为255的时候,下次循环i++,i就变成了0,造成无限循环。

 



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有