第 5章 数组与指针
5.1 数组
5.2 指针
5.3 动态内存分配
5.4 指针作为函数的参数
5.5 指针数组与多级指针
5.1 数组数组:具有相同数据类型的若干变量按序进行存储的变量集合 。 数组有一维、二维和多维数组。
5.1.1 一维数组
1,一维数组的定义数据类型 数组名 [常量表达式 ];
如,int a[10];
说明:
(1) 数组名与变量名一样都是标识符,必须遵循标识符的命名规则。
(2),数据类型”是指数组元素的数据类型,可以是任一基本类型或构造类型,同一个数组的每个元素都具有相同的数据类型。
第 5章 数组与指针
5.1 数组
5.1.1 一维数组(续一)
(3),常量表达式”必须用方括号括起来,指的是数组的元素个数(又称数组长度),它是一个整型值,其中可以包含常数和符号常量,但不能包含变量。
(4) 数组元素的下标从 0开始,即数组中第一个元素的下标为
0。如上面定义的数组 a的第一个元素是 a[0]。
(5) 一个数组中的所有元素在内存中是连续存放的。
2,一维数组的引用引用格式,数组名 [下标 ]
其中下标可以为整型常量或表达式注意,引用数组元素时,不要使下标越界!
如上面的数组 a,其下标应为 0~9!
第 5章 数组与指针例 5.1 一维数组的引用
#include <iostream.h>
void main()
{
int i,a[10];
for(i=0; i<10; i++)
{
a[i] = i*10;
}
for(i=0; i<10; i++)
{
cout << a[i] << " ";
}
cout << endl;
} 程序运行结果为:
0 10 20 30 40 50 60 70 80 90
第 5章 数组与指针
5.1 数组
5.1.1 一维数组(续一)
3,一维数组的初始化在定义数组的同时为数组元素提供初始值,称为数组的初始化。一维数组初始化的一般格式为:
数据类型 数组名 [常量表达式 ] = {值 1,值 2,…,值 n};
例如:
(1) int a[5] = {1,2,3,4,5};
(2) int a[ ] = {1,2,3,4,5};
不指定数组长度,根据初值个数自动确定长度
(3) int a[5] = {1,2,3};
初值个数小于数组长度,后面元素值自动赋为 0
(4) int a[5] = {0};
初值只写出一个 0,则将所有元素都初始化为 0
第 5章 数组与指针
1 2 3 4 5
1 2 3 4 5
1 2 3 0 0
0 0 0 0 0
例 5.2 用一维数组处理 Fibonacci数列的前 40项
#include <iostream.h>
#include <iomanip.h>
void main()
{
int i;
int f[40]={1,1};
for(i=2; i<40; i++)
{
f[i] = f[i-1] + f[i-2];
}
for(i=0; i<40; i++)
{
cout << setw(12) << f[i];
if( (i+1)%5 == 0)
cout << endl;
}
cout << endl;
}
第 5章 数组与指针例 5.2(续)
程序运行结果:
第 5章 数组与指针例 5.3 用冒泡法对 10个整数按从小到大的顺序排序分析:冒泡法的基本思想是通过相邻两个数之间的比较和交换,
使较小的数逐渐从底部移向顶部,较大的数逐渐从顶部移向底部。以 5个整数排序为例,过程如图所示。
整个排序过程由两层循环完成,第一次外层循环通过相邻两个数的比较交换,将待排序数据中的最大数 8移到最后,此时最后一个数 8已经排好序。第二次外层循环再把剩下的 4个数两俩比较交换,将其中最大的数 5移到 a[3]的位置,此时最后两个数
5,8已经排好序。一直到最后将所有数据都排好序。
第 5章 数组与指针
a[0]
a[1]
a[2]
a[3]
a[4]
8
5
2
4
3
5
8
2
4
3
5
2
8
4
3
5
2
4
8
3
5
2
4
3
8
2
5
4
3
8
2
4
5
3
8
2
4
3
5
8
2
4
3
5
8
2
3
4
5
8
2
3
4
5
8
例 5.3(续一)
#include <iostream.h>
#include <iomanip.h>
void main()
{
int i,j,t,a[10];
cout << "请输入 10个整数,用空格分隔,";
for(i=0; i<10; i++)
cin >> a[i];
for(i=0; i<10-1; i++)
{
for(j=0; j < 10-1-i; j++)
{
第 5章 数组与指针例 5.3(续二)
if(a[j] > a[j+1])
{
t = a[j];
a[j] = a[j+1];
a[j+1]=t;
}
}
}
cout << "排序后的数据,";
for(i=0; i<10; i++)
cout << setw(5) << a[i];
}
第 5章 数组与指针程序运行结果为:
请输入 10个整数,用空格分隔,8 3 9 18 32 42 17 24 25 13
排序后的数据,3 8 9 13 17 18 24 25 32 42
5.1 数组
5.1.2 二维数组
1,二维数组的定义数据类型 数组名 [常量表达式 1][常量表达式 2];
如,int a[2][3];
二维数组在内存中按行存放。
2,二维数组的引用引用格式,数组名 [下标 1][下标 2]
其中下标可以为整型常量或表达式第 5章 数组与指针
a[0][0] a[0][1] a[0][2]
a[1][0] a[1][1] a[1][2]
例 5.4 二维数组的引用
#include <iostream.h>
void main()
{
int i,j,a[3][4];
for(i=0; i<3; i++)
{
for(j=0; j<4; j++)
{
a[i][j] = (i+1)*10+j;
}
}
for(i=0; i<3; i++)
{
for(j=0; j<4; j++)
{
cout << a[i][j] << " ";
}
cout << endl;
}
}
程序运行结果为:
10 11 12 13
20 21 22 23
30 31 32 33
第 5章 数组与指针
5.1 数组
5.1.2 二维数组(续)
3,二维数组的初始化
( 1) 分行初始化如,int a[3][4] = { {1,2,3,4},{5,6,7,8},{9,10,11,12} };
( 2)按二维数组在内存中的排列顺序给各元素赋初值如,int a[3][4] = {1,2,3,4,5,6,7,8,9,10,11,12 };
( 3)对部分数组元素初始化如,int a[3][4] = { {1,2,3},{4,5},{6,7,8} };
int a[3][4] = {1,2,3,4,5,6,7};
第 5章 数组与指针例 5.5 将两个 2*3的二维数组中的对应元素的值相加后存入第 3个数组中,并输出到屏幕。
#include <iostream.h>
#include <iomanip.h>
void main()
{
int i,j,c[2][3];
int a[2][3]={1,2,3,4,5,6};
int b[2][3]={7,8,9,10,11,12};
for(i=0; i<2; i++)
for(j=0; j<3; j++)
c[i][j]=a[i][j]+b[i][j];
for(i=0; i<2; i++)
{
for(j=0; j<3; j++)
cout << setw(4) << c[i][j];
cout << endl;
}
}
程序运行结果为:
8 10 12
14 16 18
第 5章 数组与指针例 5.6 找出 4*4二维数组中对角线上元素的最大值。
#include <iostream.h>
#include <iomanip.h>
void main()
{
int a[4][4] = {11,24,53,14,51,36,27,18,29,15,41,62,23,84,75,26};
int i,j,max;
for(i=0; i<4; i++)
{
for(j=0; j<4; j++)
cout << setw(4) << a[i][j];
cout << endl;
}
max = a[0][0];
for(i=1; i<4; i++)
{
if(a[i][i] > max)
max = a[i][i];
}
cout << "对角线的最大值是," << max;
}
程序运行结果为:
11 24 53 14
51 36 27 18
29 15 41 62
23 84 75 26
对角线的最大值是,41
第 5章 数组与指针
5.1 数组
5.1.3 字符数组
1,字符数组的定义
char 数组名 [常量表达式 ];
char 数组名 [常量表达式 1][常量表达式 2];
如,char a[10],b[3][4];
2,字符数组的初始化
char 数组名 [常量表达式 ] = {?字符 1?,?字符 2?,…,? 字符 n?};
如,char s[10]={?c?,,?p?,?r?,?o?,?g?,?r?,?a?,?m?};
注意,初值个数如大于数组长度会发生编译错误若初值个数小于数组长度,后面多余元素赋为?\0?
若初值个数与数组长度相同,定义数组时长度可以省略第 5章 数组与指针
c p r o g r a m \0
s[0] s[1] s[2] s[3] s[4] s[5] s[6] s[7] s[8] s[9]
5.1 数组
5.1.3 字符数组(续一)
用字符串常量初始化字符数组:
如,char s[10]={“c program”};
或 char s[10]=,c program”;
注意这种方式要保证 字符数组长度 ≥字符串的字符个数 +1
3,字符数组的引用
( 1) 单个数组元素的引用如输出上面的字符数组 s,可用以下语句,
for(int i = 0; i<10; i++ )
cout << s[i];
( 2) 字符数组的整体引用也可用以下方式输出字符数组 s,cout << s;
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续二)
4,字符串与字符串结束标志
C++使用字符数组存放字符串,为了测试字符串的实际长度,
在字符串结尾定义了一个结束标志 ——?\0?( ASCII码值为 0的字符 )
例 5.9 求一个字符串的实际长度
#include <iostream.h>
void main()
{
char s[20] =,C Program”; //后面的 11个元素都初始化为?\0?
int i,len=0;
for(i=0; s[i]!='\0'; i++)
len++;
cout << len << endl;
}
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续三)
5,常用的字符串处理函数对字符串进行比较、复制等操作的系统函数,使用前需包含头文件 string.h。
( 1) strcmp() 函数 —— 比较两个字符串的大小
strcmp(字符串 1,字符串 2)
函数返回值:
a.字符串 1与字符串 2相等,函数返回值等于 0;
b.字符串 1大于字符串 2,函数返回值等于 1;
c.字符串 1小于字符串 2,函数返回值等于 -1。
字符串比较规则:从两个字符串的第一个字符开始,每对相应字符按 ASCII码大小进行比较,直到对应字符不相同或达到串尾为止。
第 5章 数组与指针例 5.10 strcmp()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[10] = "Program";
char b[10] = "Programer";
char c[10] = "Problem";
int i,j,k,l;
i = strcmp(a,b);
j = strcmp(a,c);
k = strcmp(a,"Program");
l = strcmp(c,a);
cout << i <<" " << j << " " << k << " " << l << endl;
}
程序运行结果为:
-1 1 0 -1
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续四)
( 2) strcpy() 函数 —— 复制字符串
strcpy(字符数组,字符串 )
—— 函数执行后将字符串复制到字符数组中。
注意,
字符数组必须定义得足够大,以便容纳复制过来的字符串。复制时,连同结束标志?\0?一起复制。
不能用赋值运算符,=”将一个字符串直接赋值给一个字符数组,
必须用函数 strcpy()复制。
第 5章 数组与指针例 5.11 strcpy()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20];
char b[20] = "C++ Program";
strcpy(a,b);
strcpy(b,"C++");
cout << a << endl;
cout << b << endl;
}
程序运行结果为:
C++ Program
C++
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续五)
( 3) strcat() 函数 —— 连接字符串
strcat(字符数组,字符串 )
—— 函数执行后将字符串连接到字符数组后面。
注意,
字符数组必须定义得足够大,以便容纳连接后的目标字符串。
连接后,第二个参数字符串的内容保持不变。
第 5章 数组与指针例 5.12 strcat()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20] = "C++ ";
char b[20] = "Program";
strcat(a,b);
strcat(b," design");
cout << a << endl;
cout << b << endl;
}
程序运行结果为:
C++ Program
Program design
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续六)
( 4) strlen() 函数 —— 求字符串实际长度(不包括结束符)
strlen(字符串 )
( 5) strlwr() 函数 —— 将字符串中的大写字母转换成小写
strlwr(字符串 )
其中参数字符串是字符数组
( 6) strupr() 函数 —— 将字符串中的小写字母转换成大写
strupr(字符串 )
其中参数字符串是字符数组第 5章 数组与指针例 5.13 strlen()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20] = "C++";
int i = strlen(a);
int j = strlen("C++ Program");
cout << i << " " << j <<endl;
}
程序运行结果为:
3 11
第 5章 数组与指针例 5.14 strlwr()和 strupr()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20] = "C++ Program";
char b[20] = "C++ Program";
strlwr(a);
strupr(b);
cout << a << endl;
cout << b << endl;
}
程序运行结果为:
c++ program
C++ PROGRAM
第 5章 数组与指针返 回
5.2 指针
5.2.1 地址与指针的概念
1,内存地址计算机的内存储器被划分成一个个的 存储单元,这些存储单元按一定的规则 编号,这个 编号 就是存储单元的 地址 。
每个存储单元的大小为一个字节,每个单元有一个唯一的地址。
2,变量的地址在程序中定义的所有变量,都要分配相应的 存储单元,不同类型的数据所需要的存储空间的大小不同。
系统分配给变量的内存空间的起始单元地址 称为该变量的 地址。
如,int a;
则 0x3000为变量 a的地址第 5章 数组与指针
0x3000 0x3001 0x3002 0x3003
5.2 指针
5.2.1 地址与指针的概念(续)
3,指针与指针变量
( 1) 指针,一个变量的 地址 也称为该变量的 指针 。
( 2) 指针变量,用于存储其它变量的指针 (即地址 )的变量。
指针变量的定义:
数据类型 *指针变量名;
如,int *p1;
float *p2;
char *p3;
注意:指针变量所指向的变量类型不能改变指针变量必须指向具体内存地址才能引用,如:
int *p; *p=10;
( 3) 指针运算符 (*)与取地址运算符 (&)
第 5章 数组与指针
×
例 5.15 通过指针变量存取变量的值
#include <iostream.h>
void main()
{
int a,*p1;
double b,*p2;
char c,*p3;
p1 = &a;
p2 = &b;
p3 = &c;
*p1 = 10;
*p2 = 11.2;
*p3 = 'A';
cout << a << endl;
cout << b<< endl;
cout << c << endl;
} 程序运行结果为:10
11.2
A
第 5章 数组与指针
100x2000
ap1
11.20x2004
bp2
A0x200C
cp3
例 5.16 输入 a和 b两个数,按从小到大的顺序输出
#include <iostream.h>
void main()
{
int a,b;
int *p1,*p2,*p;
cout << "请输入两个整数,";
cin >> a >> b;
p1 = &a;
p2 = &b;
if( *p1 > *p2 )
{
p = p1;
p1 = p2;
p2 = p;
}
cout << "min=" << *p1 << " max=" << *p2 << endl;
}
程序运行结果为:
请输入两个整数,30 10
min = 10 max = 30
第 5章 数组与指针
&a
p1
&b
p2
p 30
a
10
b
&b
p1
&a
p2&a
p
30
a
10
b
5.2 指针
5.2.2 指针运算指针运算包括 算数运算,关系运算 与 赋值运算 。
指针可以与整数进行 加减运算,结果与指针所指向的数据类型有关。 p+n表示指针 p当前所指向位置后面第 n个同类型数据的地址,p-n表示指针 p当前所指向位置前面第 n个同类型数据的地址。
指向同一种数据类型的指针可以进行 关系运算 。如果两个相同类型的 指针相等,表示这两个指针指向同一个地址 。
指针也可以与 0进行比较运算,如果 p==0成立,我们称 p是一个 空指针,即指针 p还没有具体指向。
为了避免使用没有指向的指针,在定义指针变量时,可以将其 初始化为 0(也可以写成 NULL)。
第 5章 数组与指针例 5.17 指针与整数的加减运算
#include <iostream.h>
void main()
{
int a,*p1,*p2;
double b,*p3,*p4;
p1 = &a;
p3 = &b;
cout << p1 << " " << p3 << endl;
p2 = p1+1; //p1+1与 p3+1的含义不同,与指针数据类型有关
p4 = p3+1;
cout << p2 << " " << p4 << endl;
p2 = p1-1; //p1-1与 p3-1的含义不同,与指针数据类型有关
p4 = p3-1;
cout << p2 << " " << p4 << endl;
p2 = p1+5;
p4 = p3+5;
cout << p2 << " " << p4 << endl;
}
程序运行结果为:
0x0012FF7C 0x0012FF6C
0x0012FF80 0x0012FF74
0x0012FF78 0x0012FF64
0x0012FF90 0x0012FF94
第 5章 数组与指针例 5.18 使用空指针
#include <iostream.h>
void main()
{
int a,*p=NULL;
cout << p << endl;
if(p!=NULL)
{
*p=10;
cout << "将 10赋值给 p所指向的地址 " << endl;
}
else
cout << "p是空指针,不能使用! "<< endl;
p = &a;
cout << p << endl;
if(p!=NULL)
{
*p=10;
cout << "将 10赋值给 p所指向的地址 " << endl;
}
else
cout << "p是空指针,不能使用! "<< endl;
}
程序运行结果为:
0x00000000
p是空指针,不能使用!
0x0012FF7C
将 10赋值给 p所指向的地址第 5章 数组与指针
5.2 指针
5.2.3 用指针处理数组数组在内存中是 连续存放 的,数组名 就是数组的 首地址 ( 第一个元素的地址 ),指针可以与整数进行加减运算,利用这一性质可以方便地用指针处理数组 。
第 5章 数组与指针例 5.19 使用指针输出数组中的所有元素
#include <iostream.h>
void main()
{
int a[6] = {1,2,3,4,5,6};
int *p;
p = a;
for(int i=0; i<6; i++)
{
cout << *p << " ";
p++;
}
cout << endl;
}
程序运行结果为:
1 2 3 4 5 6
第 5章 数组与指针
1 2 3 4 5 6a
p
例 5.20 指向同一个数组的两个指针的减法运算
#include <iostream.h>
void main()
{
int a[10] = {1,2,3,4,5,6,7,8,9,10};
int *p1,*p2;
p1 = a;
p2 = &a[3];
cout << p2-p1 <<endl;
p1 = &a[2];
p2 = &a[7];
cout << p2-p1 <<endl;
}
程序运行结果为:
3
5
第 5章 数组与指针
a
p1
1 2 3 4 5 6 7 8 9 10
p2
a[0] a[1] a[2] a[3] a[4] a[5] a[6] a[7] a[8] a[9]
返 回
5.3 动态内存分配在程序运行过程中根据需要动态分配存储空间,不需要时还可以将空间释放,通过 new和 delete运算符实现。
1,动态分配一个数据的存储空间通过 new运算符实现动态分配内存,格式如下:
new 类型名(初值)
如,int *p1,*p2;
p1 = new int(10);
p2 = new int;
运算符 delete用来删除由运算符 new动态分配的存储空间。使用格式如下:
delete 指针名 ;
如,delete p1;
第 5章 数组与指针
5.3 动态内存分配
2,动态分配多个连续的数据存储空间通过 new运算符动态分配数组,格式如下:
new 类型名 [整型表达式 ]
如,int *p1;
p1 = new int[10];
用 delete删除动态数组时,要在指针前加,[]”。格式如下:
delete [] 指针名 ;
如,delete [ ] p1;
第 5章 数组与指针例 5.21 动态内存分配的使用
#include <iostream.h>
void main()
{
int *p1,*p2;
p1 = new int(10);
p2 = new int[10];
int i;
for(i=0; i<10; i++)
*(p2+i) = i;
cout << *p1 <<endl;
for(i=0; i<10; i++)
cout << *(p2+i) << " ";
cout << endl;
for(i=0; i<10; i++)
cout << p2[i] <<,,; // p2[i] 与 *(p2+i)所访问的数据相同
cout << endl;
delete p1;
delete [ ]p2;
}
程序运行结果为:
10
0 1 2 3 4 5 6 7 8 9
0 1 2 3 4 5 6 7 8 9
第 5章 数组与指针
p2
1 2 3 4 5 6 7 8 9 10
返 回
5.4 指针作为函数的参数
5.4.1 指针变量作为函数的参数指针作为函数的参数,实际上传递的是变量的地址,进行的是 地址传递 。
例 5.22 指针作为函数参数,被调函数中交换参数值第 5章 数组与指针
#include <iostream.h>
void swap(int *x,int *y);
void main()
{
int a,b;
a = 10;
b = 20;
swap(&a,&b);
cout << a << "," << b << endl;
}
void swap(int *x,int *y)
{
int temp;
temp = *x;
*x = *y;
*y = temp;
}
5.4 指针作为函数的参数
5.4.1 指针变量作为函数的参数(续)
例 5.22 程序运行过程中变量值的变化分析第 5章 数组与指针
yy
b10a
x
20 b
y &ax &b
10temp
20a
x
20 b
y
10temp
&a
a
x &b
b
10temp
&a &b
temp
10a 20
&a &b
20 10
(a) (b) (c) (d)
程序运行结果为:
20,10
5.4 指针作为函数的参数
5.4.2 数组作为函数的参数数组元素作为函数的参数,与普通变量作为函数的参数相同。
数组名作为函数的参数实际上传递的是数组的首地址,进行的是地址传递 。
例 5.23 编写一个函数,将数组中的元素按照相反的顺序存放分析:将数组名和元素个数作为函数的参数,可以通过地址访问数组中的所有元素。在函数中将数组的第一个元素与最后一个元素交换,第二个元素与倒数第二个元素交换,一直进行到中间,
即完成反序存放。
第 5章 数组与指针例 5.23 源程序
#include <iostream.h>
void inv(int x[],int n);
void main()
{
int i,a[10]={0,1,2,3,4,5,6,7,8,9};
cout << "原数组," << endl;
for(i=0;i<10;i++)
cout << a[i] << " ";
cout << endl;
inv(a,10);
cout << "交换后的数组," << endl;
for(i=0;i<10;i++)
cout << a[i] << " ";
cout << endl;
}
程序运行结果为:
原数组,0 1 2 3 4 5 6 7 8 9
交换后的数组,9 8 7 6 5 4 3 2 1 0
第 5章 数组与指针
void inv(int x[],int n)
{
int temp,i,j,m;
m=(n-1)/2;
for(i=0;i<=m;i++)
{
j=n-1-i;
temp=x[i];
x[i]=x[j];
x[j]=temp;
}
}
注意:由于传递的是数组地址,因此形参
x和实参 a指向相同的内存地址,因此在函数体中对 x的操作实际上就是对 a的操作例 5.23 (续)
第 5章 数组与指针返 回注意:数组名作为函数参数传递的是数组首地址,因此也可以直接将形参改为指针,当数组名作为实参时,同样能够传递数组首地址。将函数 inv()做以下修 改:
void inv(int *x,int n)
{
int *i,*j,temp,m;
m=(n-1)/2;
for(i=x,j=x+n-1; i<j; i++,j--)
{
temp=*i;
*i=*j;
*j=temp;
}
}
0 1 2 3 4 5 6 7 8 9
i
x
j
5.5 指针数组与多级指针
5.5.1 指针数组数组元素是指针的数组,称为 指针数组 。
定义格式:
类型名 *数组名 [常量表达式 ];
如:
int *p1[10];
double *p2[10];
第 5章 数组与指针例 5.24 用指针数组处理二维数组的元素
#include <iostream.h>
void main()
{
int line[3][3]={{1,0,0},{0,1,0},{0,0,1}};
int *p_line[3]; //声明整型指针数组
p_line[0]=line[0]; //初始化指针数组元素
p_line[1]=line[1];
p_line[2]=line[2];
cout<<"Matrix test:"<<endl; //输出单位矩阵
for(int i=0;i<3;i++) //对指针数组元素循环
{
for(int j=0;j<3;j++) //对矩阵每一行循环
{
cout<<p_line[i][j]<<" ";
}
cout<<endl;
}
}
程序运行结果为:
1 0 0
0 1 0
0 0 1
第 5章 数组与指针
1
p_line line
p_line[0]
p_line[1]
p_line[2]
1
1
0
0
00
0
0
5.5 指针数组与多级指针
5.5.2 多级指针如果一个指针变量保存的是另一个指针变量的地址,我们称之为 指向指针的指针,或 多级指针 。
定义格式:
类型名 **指针变量名 ;
如:
int **p1;
double **p2;
第 5章 数组与指针例 5.25 二级指针的应用
#include <iostream.h>
void main()
{
int a,*p1,**p2;
double b,*p3,**p4;
a=10;
b=22.3;
p1 = &a;
p3 = &b;
p2 = &p1;
p4 = &p3;
cout << a << " " << *p1 << " " << **p2 << endl;
cout << b << " " << *p3 << " " << **p4 << endl;
**p2 = 20;
**p4 = 45.8;
cout << a << " " << *p1 << " " << **p2 << endl;
cout << b << " " << *p3 << " " << **p4 << endl;
}
程序运行结果为:
10 10 10
22.3 22.3 22.3
20 20 20
45.8 45.8 45.8
第 5章 数组与指针
&p1 &a 10
p2 p1 a
&p3 &b 22.3
p4 p3 b
例 5.26 用二级指针指向指针数组
#include <iostream.h>
void main()
{
char *name[] = {"Basic","Fortran","C++","Pascal"};
char **p;
int i;
for(i=0; i<4; i++)
{
p = name+i;
cout << *p << endl;
}
}
程序运行结果为:
Basic
Fortran
C++
Pascal
第 5章 数组与指针
name[0]
name[1]
name[2]
name[3]
Basic
Fortran
C++
Pascal
p
分析:选择排序的基本思想是,每次从待排序序列中选择一个最小值,顺序排在已排好序序列的最后,直到全部排完。
#include <iostream.h>
void sort(int *x,int n);
void main()
{
int i,a[10];
cout << "请输入 10个整数,";
for(i=0;i<10;i++)
cin >> a[i];
cout << endl;
sort(a,10);
for(i=0; i<10; i++)
{
cout << a[i] << " ";
}
cout << endl;
}
例 5.27 编写一个函数,用选择法对数组中的元素按升序排序第 5章 数组与指针
void sort(int *p,int n)
{
int i,j,k,t;
for(i=0;i<n-1;i++)
{
k=i;
for(j=i+1;j<n;j++)
if(p[j]<p[k])
k=j;
if(k!=i)
{
t=p[i];
p[i]=p[k];
p[k]=t;
}
}
}
#include <iostream.h>
#include <string.h>
void stringcat(char *s1,char *s2);
void main()
{
char a[20] = "abcde";
char b[] = "fgh123";
cout << a << endl;
cout << b << endl;
stringcat(a,b);
cout << a << endl;
cout << b << endl;
}
例 5.28 编写一个函数,将两个字符串连接起来第 5章 数组与指针
void stringcat(char *s1,char *s2)
{
int i,len;
len = strlen(s1);
for(i=0; s2[i]!='\0'; i++)
{
s1[len+i] = s2[i];
}
s1[len+i] = '\0';
}
a b c d e ‘\0’ ……
s2 f g h 1 2 3 ‘\0’ ……
s1
返 回谢 谢!
5.1 数组
5.2 指针
5.3 动态内存分配
5.4 指针作为函数的参数
5.5 指针数组与多级指针
5.1 数组数组:具有相同数据类型的若干变量按序进行存储的变量集合 。 数组有一维、二维和多维数组。
5.1.1 一维数组
1,一维数组的定义数据类型 数组名 [常量表达式 ];
如,int a[10];
说明:
(1) 数组名与变量名一样都是标识符,必须遵循标识符的命名规则。
(2),数据类型”是指数组元素的数据类型,可以是任一基本类型或构造类型,同一个数组的每个元素都具有相同的数据类型。
第 5章 数组与指针
5.1 数组
5.1.1 一维数组(续一)
(3),常量表达式”必须用方括号括起来,指的是数组的元素个数(又称数组长度),它是一个整型值,其中可以包含常数和符号常量,但不能包含变量。
(4) 数组元素的下标从 0开始,即数组中第一个元素的下标为
0。如上面定义的数组 a的第一个元素是 a[0]。
(5) 一个数组中的所有元素在内存中是连续存放的。
2,一维数组的引用引用格式,数组名 [下标 ]
其中下标可以为整型常量或表达式注意,引用数组元素时,不要使下标越界!
如上面的数组 a,其下标应为 0~9!
第 5章 数组与指针例 5.1 一维数组的引用
#include <iostream.h>
void main()
{
int i,a[10];
for(i=0; i<10; i++)
{
a[i] = i*10;
}
for(i=0; i<10; i++)
{
cout << a[i] << " ";
}
cout << endl;
} 程序运行结果为:
0 10 20 30 40 50 60 70 80 90
第 5章 数组与指针
5.1 数组
5.1.1 一维数组(续一)
3,一维数组的初始化在定义数组的同时为数组元素提供初始值,称为数组的初始化。一维数组初始化的一般格式为:
数据类型 数组名 [常量表达式 ] = {值 1,值 2,…,值 n};
例如:
(1) int a[5] = {1,2,3,4,5};
(2) int a[ ] = {1,2,3,4,5};
不指定数组长度,根据初值个数自动确定长度
(3) int a[5] = {1,2,3};
初值个数小于数组长度,后面元素值自动赋为 0
(4) int a[5] = {0};
初值只写出一个 0,则将所有元素都初始化为 0
第 5章 数组与指针
1 2 3 4 5
1 2 3 4 5
1 2 3 0 0
0 0 0 0 0
例 5.2 用一维数组处理 Fibonacci数列的前 40项
#include <iostream.h>
#include <iomanip.h>
void main()
{
int i;
int f[40]={1,1};
for(i=2; i<40; i++)
{
f[i] = f[i-1] + f[i-2];
}
for(i=0; i<40; i++)
{
cout << setw(12) << f[i];
if( (i+1)%5 == 0)
cout << endl;
}
cout << endl;
}
第 5章 数组与指针例 5.2(续)
程序运行结果:
第 5章 数组与指针例 5.3 用冒泡法对 10个整数按从小到大的顺序排序分析:冒泡法的基本思想是通过相邻两个数之间的比较和交换,
使较小的数逐渐从底部移向顶部,较大的数逐渐从顶部移向底部。以 5个整数排序为例,过程如图所示。
整个排序过程由两层循环完成,第一次外层循环通过相邻两个数的比较交换,将待排序数据中的最大数 8移到最后,此时最后一个数 8已经排好序。第二次外层循环再把剩下的 4个数两俩比较交换,将其中最大的数 5移到 a[3]的位置,此时最后两个数
5,8已经排好序。一直到最后将所有数据都排好序。
第 5章 数组与指针
a[0]
a[1]
a[2]
a[3]
a[4]
8
5
2
4
3
5
8
2
4
3
5
2
8
4
3
5
2
4
8
3
5
2
4
3
8
2
5
4
3
8
2
4
5
3
8
2
4
3
5
8
2
4
3
5
8
2
3
4
5
8
2
3
4
5
8
例 5.3(续一)
#include <iostream.h>
#include <iomanip.h>
void main()
{
int i,j,t,a[10];
cout << "请输入 10个整数,用空格分隔,";
for(i=0; i<10; i++)
cin >> a[i];
for(i=0; i<10-1; i++)
{
for(j=0; j < 10-1-i; j++)
{
第 5章 数组与指针例 5.3(续二)
if(a[j] > a[j+1])
{
t = a[j];
a[j] = a[j+1];
a[j+1]=t;
}
}
}
cout << "排序后的数据,";
for(i=0; i<10; i++)
cout << setw(5) << a[i];
}
第 5章 数组与指针程序运行结果为:
请输入 10个整数,用空格分隔,8 3 9 18 32 42 17 24 25 13
排序后的数据,3 8 9 13 17 18 24 25 32 42
5.1 数组
5.1.2 二维数组
1,二维数组的定义数据类型 数组名 [常量表达式 1][常量表达式 2];
如,int a[2][3];
二维数组在内存中按行存放。
2,二维数组的引用引用格式,数组名 [下标 1][下标 2]
其中下标可以为整型常量或表达式第 5章 数组与指针
a[0][0] a[0][1] a[0][2]
a[1][0] a[1][1] a[1][2]
例 5.4 二维数组的引用
#include <iostream.h>
void main()
{
int i,j,a[3][4];
for(i=0; i<3; i++)
{
for(j=0; j<4; j++)
{
a[i][j] = (i+1)*10+j;
}
}
for(i=0; i<3; i++)
{
for(j=0; j<4; j++)
{
cout << a[i][j] << " ";
}
cout << endl;
}
}
程序运行结果为:
10 11 12 13
20 21 22 23
30 31 32 33
第 5章 数组与指针
5.1 数组
5.1.2 二维数组(续)
3,二维数组的初始化
( 1) 分行初始化如,int a[3][4] = { {1,2,3,4},{5,6,7,8},{9,10,11,12} };
( 2)按二维数组在内存中的排列顺序给各元素赋初值如,int a[3][4] = {1,2,3,4,5,6,7,8,9,10,11,12 };
( 3)对部分数组元素初始化如,int a[3][4] = { {1,2,3},{4,5},{6,7,8} };
int a[3][4] = {1,2,3,4,5,6,7};
第 5章 数组与指针例 5.5 将两个 2*3的二维数组中的对应元素的值相加后存入第 3个数组中,并输出到屏幕。
#include <iostream.h>
#include <iomanip.h>
void main()
{
int i,j,c[2][3];
int a[2][3]={1,2,3,4,5,6};
int b[2][3]={7,8,9,10,11,12};
for(i=0; i<2; i++)
for(j=0; j<3; j++)
c[i][j]=a[i][j]+b[i][j];
for(i=0; i<2; i++)
{
for(j=0; j<3; j++)
cout << setw(4) << c[i][j];
cout << endl;
}
}
程序运行结果为:
8 10 12
14 16 18
第 5章 数组与指针例 5.6 找出 4*4二维数组中对角线上元素的最大值。
#include <iostream.h>
#include <iomanip.h>
void main()
{
int a[4][4] = {11,24,53,14,51,36,27,18,29,15,41,62,23,84,75,26};
int i,j,max;
for(i=0; i<4; i++)
{
for(j=0; j<4; j++)
cout << setw(4) << a[i][j];
cout << endl;
}
max = a[0][0];
for(i=1; i<4; i++)
{
if(a[i][i] > max)
max = a[i][i];
}
cout << "对角线的最大值是," << max;
}
程序运行结果为:
11 24 53 14
51 36 27 18
29 15 41 62
23 84 75 26
对角线的最大值是,41
第 5章 数组与指针
5.1 数组
5.1.3 字符数组
1,字符数组的定义
char 数组名 [常量表达式 ];
char 数组名 [常量表达式 1][常量表达式 2];
如,char a[10],b[3][4];
2,字符数组的初始化
char 数组名 [常量表达式 ] = {?字符 1?,?字符 2?,…,? 字符 n?};
如,char s[10]={?c?,,?p?,?r?,?o?,?g?,?r?,?a?,?m?};
注意,初值个数如大于数组长度会发生编译错误若初值个数小于数组长度,后面多余元素赋为?\0?
若初值个数与数组长度相同,定义数组时长度可以省略第 5章 数组与指针
c p r o g r a m \0
s[0] s[1] s[2] s[3] s[4] s[5] s[6] s[7] s[8] s[9]
5.1 数组
5.1.3 字符数组(续一)
用字符串常量初始化字符数组:
如,char s[10]={“c program”};
或 char s[10]=,c program”;
注意这种方式要保证 字符数组长度 ≥字符串的字符个数 +1
3,字符数组的引用
( 1) 单个数组元素的引用如输出上面的字符数组 s,可用以下语句,
for(int i = 0; i<10; i++ )
cout << s[i];
( 2) 字符数组的整体引用也可用以下方式输出字符数组 s,cout << s;
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续二)
4,字符串与字符串结束标志
C++使用字符数组存放字符串,为了测试字符串的实际长度,
在字符串结尾定义了一个结束标志 ——?\0?( ASCII码值为 0的字符 )
例 5.9 求一个字符串的实际长度
#include <iostream.h>
void main()
{
char s[20] =,C Program”; //后面的 11个元素都初始化为?\0?
int i,len=0;
for(i=0; s[i]!='\0'; i++)
len++;
cout << len << endl;
}
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续三)
5,常用的字符串处理函数对字符串进行比较、复制等操作的系统函数,使用前需包含头文件 string.h。
( 1) strcmp() 函数 —— 比较两个字符串的大小
strcmp(字符串 1,字符串 2)
函数返回值:
a.字符串 1与字符串 2相等,函数返回值等于 0;
b.字符串 1大于字符串 2,函数返回值等于 1;
c.字符串 1小于字符串 2,函数返回值等于 -1。
字符串比较规则:从两个字符串的第一个字符开始,每对相应字符按 ASCII码大小进行比较,直到对应字符不相同或达到串尾为止。
第 5章 数组与指针例 5.10 strcmp()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[10] = "Program";
char b[10] = "Programer";
char c[10] = "Problem";
int i,j,k,l;
i = strcmp(a,b);
j = strcmp(a,c);
k = strcmp(a,"Program");
l = strcmp(c,a);
cout << i <<" " << j << " " << k << " " << l << endl;
}
程序运行结果为:
-1 1 0 -1
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续四)
( 2) strcpy() 函数 —— 复制字符串
strcpy(字符数组,字符串 )
—— 函数执行后将字符串复制到字符数组中。
注意,
字符数组必须定义得足够大,以便容纳复制过来的字符串。复制时,连同结束标志?\0?一起复制。
不能用赋值运算符,=”将一个字符串直接赋值给一个字符数组,
必须用函数 strcpy()复制。
第 5章 数组与指针例 5.11 strcpy()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20];
char b[20] = "C++ Program";
strcpy(a,b);
strcpy(b,"C++");
cout << a << endl;
cout << b << endl;
}
程序运行结果为:
C++ Program
C++
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续五)
( 3) strcat() 函数 —— 连接字符串
strcat(字符数组,字符串 )
—— 函数执行后将字符串连接到字符数组后面。
注意,
字符数组必须定义得足够大,以便容纳连接后的目标字符串。
连接后,第二个参数字符串的内容保持不变。
第 5章 数组与指针例 5.12 strcat()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20] = "C++ ";
char b[20] = "Program";
strcat(a,b);
strcat(b," design");
cout << a << endl;
cout << b << endl;
}
程序运行结果为:
C++ Program
Program design
第 5章 数组与指针
5.1 数组
5.1.3 字符数组(续六)
( 4) strlen() 函数 —— 求字符串实际长度(不包括结束符)
strlen(字符串 )
( 5) strlwr() 函数 —— 将字符串中的大写字母转换成小写
strlwr(字符串 )
其中参数字符串是字符数组
( 6) strupr() 函数 —— 将字符串中的小写字母转换成大写
strupr(字符串 )
其中参数字符串是字符数组第 5章 数组与指针例 5.13 strlen()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20] = "C++";
int i = strlen(a);
int j = strlen("C++ Program");
cout << i << " " << j <<endl;
}
程序运行结果为:
3 11
第 5章 数组与指针例 5.14 strlwr()和 strupr()函数的应用
#include <iostream.h>
#include <string.h>
void main()
{
char a[20] = "C++ Program";
char b[20] = "C++ Program";
strlwr(a);
strupr(b);
cout << a << endl;
cout << b << endl;
}
程序运行结果为:
c++ program
C++ PROGRAM
第 5章 数组与指针返 回
5.2 指针
5.2.1 地址与指针的概念
1,内存地址计算机的内存储器被划分成一个个的 存储单元,这些存储单元按一定的规则 编号,这个 编号 就是存储单元的 地址 。
每个存储单元的大小为一个字节,每个单元有一个唯一的地址。
2,变量的地址在程序中定义的所有变量,都要分配相应的 存储单元,不同类型的数据所需要的存储空间的大小不同。
系统分配给变量的内存空间的起始单元地址 称为该变量的 地址。
如,int a;
则 0x3000为变量 a的地址第 5章 数组与指针
0x3000 0x3001 0x3002 0x3003
5.2 指针
5.2.1 地址与指针的概念(续)
3,指针与指针变量
( 1) 指针,一个变量的 地址 也称为该变量的 指针 。
( 2) 指针变量,用于存储其它变量的指针 (即地址 )的变量。
指针变量的定义:
数据类型 *指针变量名;
如,int *p1;
float *p2;
char *p3;
注意:指针变量所指向的变量类型不能改变指针变量必须指向具体内存地址才能引用,如:
int *p; *p=10;
( 3) 指针运算符 (*)与取地址运算符 (&)
第 5章 数组与指针
×
例 5.15 通过指针变量存取变量的值
#include <iostream.h>
void main()
{
int a,*p1;
double b,*p2;
char c,*p3;
p1 = &a;
p2 = &b;
p3 = &c;
*p1 = 10;
*p2 = 11.2;
*p3 = 'A';
cout << a << endl;
cout << b<< endl;
cout << c << endl;
} 程序运行结果为:10
11.2
A
第 5章 数组与指针
100x2000
ap1
11.20x2004
bp2
A0x200C
cp3
例 5.16 输入 a和 b两个数,按从小到大的顺序输出
#include <iostream.h>
void main()
{
int a,b;
int *p1,*p2,*p;
cout << "请输入两个整数,";
cin >> a >> b;
p1 = &a;
p2 = &b;
if( *p1 > *p2 )
{
p = p1;
p1 = p2;
p2 = p;
}
cout << "min=" << *p1 << " max=" << *p2 << endl;
}
程序运行结果为:
请输入两个整数,30 10
min = 10 max = 30
第 5章 数组与指针
&a
p1
&b
p2
p 30
a
10
b
&b
p1
&a
p2&a
p
30
a
10
b
5.2 指针
5.2.2 指针运算指针运算包括 算数运算,关系运算 与 赋值运算 。
指针可以与整数进行 加减运算,结果与指针所指向的数据类型有关。 p+n表示指针 p当前所指向位置后面第 n个同类型数据的地址,p-n表示指针 p当前所指向位置前面第 n个同类型数据的地址。
指向同一种数据类型的指针可以进行 关系运算 。如果两个相同类型的 指针相等,表示这两个指针指向同一个地址 。
指针也可以与 0进行比较运算,如果 p==0成立,我们称 p是一个 空指针,即指针 p还没有具体指向。
为了避免使用没有指向的指针,在定义指针变量时,可以将其 初始化为 0(也可以写成 NULL)。
第 5章 数组与指针例 5.17 指针与整数的加减运算
#include <iostream.h>
void main()
{
int a,*p1,*p2;
double b,*p3,*p4;
p1 = &a;
p3 = &b;
cout << p1 << " " << p3 << endl;
p2 = p1+1; //p1+1与 p3+1的含义不同,与指针数据类型有关
p4 = p3+1;
cout << p2 << " " << p4 << endl;
p2 = p1-1; //p1-1与 p3-1的含义不同,与指针数据类型有关
p4 = p3-1;
cout << p2 << " " << p4 << endl;
p2 = p1+5;
p4 = p3+5;
cout << p2 << " " << p4 << endl;
}
程序运行结果为:
0x0012FF7C 0x0012FF6C
0x0012FF80 0x0012FF74
0x0012FF78 0x0012FF64
0x0012FF90 0x0012FF94
第 5章 数组与指针例 5.18 使用空指针
#include <iostream.h>
void main()
{
int a,*p=NULL;
cout << p << endl;
if(p!=NULL)
{
*p=10;
cout << "将 10赋值给 p所指向的地址 " << endl;
}
else
cout << "p是空指针,不能使用! "<< endl;
p = &a;
cout << p << endl;
if(p!=NULL)
{
*p=10;
cout << "将 10赋值给 p所指向的地址 " << endl;
}
else
cout << "p是空指针,不能使用! "<< endl;
}
程序运行结果为:
0x00000000
p是空指针,不能使用!
0x0012FF7C
将 10赋值给 p所指向的地址第 5章 数组与指针
5.2 指针
5.2.3 用指针处理数组数组在内存中是 连续存放 的,数组名 就是数组的 首地址 ( 第一个元素的地址 ),指针可以与整数进行加减运算,利用这一性质可以方便地用指针处理数组 。
第 5章 数组与指针例 5.19 使用指针输出数组中的所有元素
#include <iostream.h>
void main()
{
int a[6] = {1,2,3,4,5,6};
int *p;
p = a;
for(int i=0; i<6; i++)
{
cout << *p << " ";
p++;
}
cout << endl;
}
程序运行结果为:
1 2 3 4 5 6
第 5章 数组与指针
1 2 3 4 5 6a
p
例 5.20 指向同一个数组的两个指针的减法运算
#include <iostream.h>
void main()
{
int a[10] = {1,2,3,4,5,6,7,8,9,10};
int *p1,*p2;
p1 = a;
p2 = &a[3];
cout << p2-p1 <<endl;
p1 = &a[2];
p2 = &a[7];
cout << p2-p1 <<endl;
}
程序运行结果为:
3
5
第 5章 数组与指针
a
p1
1 2 3 4 5 6 7 8 9 10
p2
a[0] a[1] a[2] a[3] a[4] a[5] a[6] a[7] a[8] a[9]
返 回
5.3 动态内存分配在程序运行过程中根据需要动态分配存储空间,不需要时还可以将空间释放,通过 new和 delete运算符实现。
1,动态分配一个数据的存储空间通过 new运算符实现动态分配内存,格式如下:
new 类型名(初值)
如,int *p1,*p2;
p1 = new int(10);
p2 = new int;
运算符 delete用来删除由运算符 new动态分配的存储空间。使用格式如下:
delete 指针名 ;
如,delete p1;
第 5章 数组与指针
5.3 动态内存分配
2,动态分配多个连续的数据存储空间通过 new运算符动态分配数组,格式如下:
new 类型名 [整型表达式 ]
如,int *p1;
p1 = new int[10];
用 delete删除动态数组时,要在指针前加,[]”。格式如下:
delete [] 指针名 ;
如,delete [ ] p1;
第 5章 数组与指针例 5.21 动态内存分配的使用
#include <iostream.h>
void main()
{
int *p1,*p2;
p1 = new int(10);
p2 = new int[10];
int i;
for(i=0; i<10; i++)
*(p2+i) = i;
cout << *p1 <<endl;
for(i=0; i<10; i++)
cout << *(p2+i) << " ";
cout << endl;
for(i=0; i<10; i++)
cout << p2[i] <<,,; // p2[i] 与 *(p2+i)所访问的数据相同
cout << endl;
delete p1;
delete [ ]p2;
}
程序运行结果为:
10
0 1 2 3 4 5 6 7 8 9
0 1 2 3 4 5 6 7 8 9
第 5章 数组与指针
p2
1 2 3 4 5 6 7 8 9 10
返 回
5.4 指针作为函数的参数
5.4.1 指针变量作为函数的参数指针作为函数的参数,实际上传递的是变量的地址,进行的是 地址传递 。
例 5.22 指针作为函数参数,被调函数中交换参数值第 5章 数组与指针
#include <iostream.h>
void swap(int *x,int *y);
void main()
{
int a,b;
a = 10;
b = 20;
swap(&a,&b);
cout << a << "," << b << endl;
}
void swap(int *x,int *y)
{
int temp;
temp = *x;
*x = *y;
*y = temp;
}
5.4 指针作为函数的参数
5.4.1 指针变量作为函数的参数(续)
例 5.22 程序运行过程中变量值的变化分析第 5章 数组与指针
yy
b10a
x
20 b
y &ax &b
10temp
20a
x
20 b
y
10temp
&a
a
x &b
b
10temp
&a &b
temp
10a 20
&a &b
20 10
(a) (b) (c) (d)
程序运行结果为:
20,10
5.4 指针作为函数的参数
5.4.2 数组作为函数的参数数组元素作为函数的参数,与普通变量作为函数的参数相同。
数组名作为函数的参数实际上传递的是数组的首地址,进行的是地址传递 。
例 5.23 编写一个函数,将数组中的元素按照相反的顺序存放分析:将数组名和元素个数作为函数的参数,可以通过地址访问数组中的所有元素。在函数中将数组的第一个元素与最后一个元素交换,第二个元素与倒数第二个元素交换,一直进行到中间,
即完成反序存放。
第 5章 数组与指针例 5.23 源程序
#include <iostream.h>
void inv(int x[],int n);
void main()
{
int i,a[10]={0,1,2,3,4,5,6,7,8,9};
cout << "原数组," << endl;
for(i=0;i<10;i++)
cout << a[i] << " ";
cout << endl;
inv(a,10);
cout << "交换后的数组," << endl;
for(i=0;i<10;i++)
cout << a[i] << " ";
cout << endl;
}
程序运行结果为:
原数组,0 1 2 3 4 5 6 7 8 9
交换后的数组,9 8 7 6 5 4 3 2 1 0
第 5章 数组与指针
void inv(int x[],int n)
{
int temp,i,j,m;
m=(n-1)/2;
for(i=0;i<=m;i++)
{
j=n-1-i;
temp=x[i];
x[i]=x[j];
x[j]=temp;
}
}
注意:由于传递的是数组地址,因此形参
x和实参 a指向相同的内存地址,因此在函数体中对 x的操作实际上就是对 a的操作例 5.23 (续)
第 5章 数组与指针返 回注意:数组名作为函数参数传递的是数组首地址,因此也可以直接将形参改为指针,当数组名作为实参时,同样能够传递数组首地址。将函数 inv()做以下修 改:
void inv(int *x,int n)
{
int *i,*j,temp,m;
m=(n-1)/2;
for(i=x,j=x+n-1; i<j; i++,j--)
{
temp=*i;
*i=*j;
*j=temp;
}
}
0 1 2 3 4 5 6 7 8 9
i
x
j
5.5 指针数组与多级指针
5.5.1 指针数组数组元素是指针的数组,称为 指针数组 。
定义格式:
类型名 *数组名 [常量表达式 ];
如:
int *p1[10];
double *p2[10];
第 5章 数组与指针例 5.24 用指针数组处理二维数组的元素
#include <iostream.h>
void main()
{
int line[3][3]={{1,0,0},{0,1,0},{0,0,1}};
int *p_line[3]; //声明整型指针数组
p_line[0]=line[0]; //初始化指针数组元素
p_line[1]=line[1];
p_line[2]=line[2];
cout<<"Matrix test:"<<endl; //输出单位矩阵
for(int i=0;i<3;i++) //对指针数组元素循环
{
for(int j=0;j<3;j++) //对矩阵每一行循环
{
cout<<p_line[i][j]<<" ";
}
cout<<endl;
}
}
程序运行结果为:
1 0 0
0 1 0
0 0 1
第 5章 数组与指针
1
p_line line
p_line[0]
p_line[1]
p_line[2]
1
1
0
0
00
0
0
5.5 指针数组与多级指针
5.5.2 多级指针如果一个指针变量保存的是另一个指针变量的地址,我们称之为 指向指针的指针,或 多级指针 。
定义格式:
类型名 **指针变量名 ;
如:
int **p1;
double **p2;
第 5章 数组与指针例 5.25 二级指针的应用
#include <iostream.h>
void main()
{
int a,*p1,**p2;
double b,*p3,**p4;
a=10;
b=22.3;
p1 = &a;
p3 = &b;
p2 = &p1;
p4 = &p3;
cout << a << " " << *p1 << " " << **p2 << endl;
cout << b << " " << *p3 << " " << **p4 << endl;
**p2 = 20;
**p4 = 45.8;
cout << a << " " << *p1 << " " << **p2 << endl;
cout << b << " " << *p3 << " " << **p4 << endl;
}
程序运行结果为:
10 10 10
22.3 22.3 22.3
20 20 20
45.8 45.8 45.8
第 5章 数组与指针
&p1 &a 10
p2 p1 a
&p3 &b 22.3
p4 p3 b
例 5.26 用二级指针指向指针数组
#include <iostream.h>
void main()
{
char *name[] = {"Basic","Fortran","C++","Pascal"};
char **p;
int i;
for(i=0; i<4; i++)
{
p = name+i;
cout << *p << endl;
}
}
程序运行结果为:
Basic
Fortran
C++
Pascal
第 5章 数组与指针
name[0]
name[1]
name[2]
name[3]
Basic
Fortran
C++
Pascal
p
分析:选择排序的基本思想是,每次从待排序序列中选择一个最小值,顺序排在已排好序序列的最后,直到全部排完。
#include <iostream.h>
void sort(int *x,int n);
void main()
{
int i,a[10];
cout << "请输入 10个整数,";
for(i=0;i<10;i++)
cin >> a[i];
cout << endl;
sort(a,10);
for(i=0; i<10; i++)
{
cout << a[i] << " ";
}
cout << endl;
}
例 5.27 编写一个函数,用选择法对数组中的元素按升序排序第 5章 数组与指针
void sort(int *p,int n)
{
int i,j,k,t;
for(i=0;i<n-1;i++)
{
k=i;
for(j=i+1;j<n;j++)
if(p[j]<p[k])
k=j;
if(k!=i)
{
t=p[i];
p[i]=p[k];
p[k]=t;
}
}
}
#include <iostream.h>
#include <string.h>
void stringcat(char *s1,char *s2);
void main()
{
char a[20] = "abcde";
char b[] = "fgh123";
cout << a << endl;
cout << b << endl;
stringcat(a,b);
cout << a << endl;
cout << b << endl;
}
例 5.28 编写一个函数,将两个字符串连接起来第 5章 数组与指针
void stringcat(char *s1,char *s2)
{
int i,len;
len = strlen(s1);
for(i=0; s2[i]!='\0'; i++)
{
s1[len+i] = s2[i];
}
s1[len+i] = '\0';
}
a b c d e ‘\0’ ……
s2 f g h 1 2 3 ‘\0’ ……
s1
返 回谢 谢!