数组指针
- int (*p)[10];数组指针;sizeof(p) = 8。
- int *p[10];指针数组;sizeof(p) = 80。
例如:int a[10] = {1,2,3,4,5,6,7,8,9,0};&a:指向长度为10的一维int数组的地址。
二维数组的应用(a[i][j] <===>*(*(a + i) + j) )
以二维数组a[3][4] 为例。
1.遍历
void printArray2D(int (*a)[4], int rows)
{
int i, j;
for(i = 0;i < rows;++i)
{
for(j = 0;j < 4;++j)
{
printf("%2d ",*(*(a +i) + j));
}
puts("");
}
}
2.元素求和
int sumOfTheArray2D(int (*a)[4], int rows)
{
int i, j;
int sum = 0;
for(i = 0; i < rows;++i)
{
for(j = 0; j < 4;++j)
{
sum += *(*(a + i) + j);
}
}
return sum;
}
3.求每行元素平均值(int result[rows];)
void advArray2D(int (*a)[4], int rows, int *result)
{
int i,j;
for(i = 0;i < rows;++i)
{
int sum = 0;
for(j = 0; j < 4; ++j)
{
sum += *(*(a + i) + j);
}
*(result + i) = sum / 4;
}
}
函数指针
一个函数在编译时被分配给一个入口地址,这个函数的入口地址就称为函数的指针。可以用一个指针变量指向函数,然后通过该指针变量调用此函数。
指向函数的指针变量的一般定义形式为:数据类型(*指针变量名)(函数参数 表列);
这里的“数据类型”是指函数返回值的类型。函数的调用可以通过函数名调用,也可以通过函数指针调用(指向函数的指针变量)
int(*p)(int, int); 表示定义一个指向函数的指针变量p,他不是固定指向哪一个函数的,只是表示定义了这样一个类型的变量,它是专门用来存放函数的入口地址的。
void printArray(int *a, int len, int (*pfn)(int))
{
int i;
for(i = 0;i < len;++i)
{
if(pfn (a[i]))
{
printf("%d\n",a[i]);
}
}
}
各类型快速排序
int doublecmp(const void *p1, const void *p2)
{
double *q1 = (double *)p1;
double *q2 = (double *)p2;//类型强制转换
if(*q1 > *q2)
{
return 1;
}
else if(*q1 < *q2)
{
return -1;
}
else
{
return 0;
}
}
int main(void)
{
double a[] = {1,2,3,4,5,6,7,8,9,0};
int len = sizeof(a) / sizeof (a[0]);
qsort(a, len, sizeof(a[0]), doublecmp);
int i;
for(i = 0;i < len;++i)
{
printf("%lf\n",a[i]);
}
return 0;
}
指向指针的指针
指的是一个指针变量,该变量的值为另一个指针的地址。
char * *p。char *为基类型,*为类型说明符,p为指针变量。
指针数组
一个数组,若其元素均为指针类型数据,称为指针数据,其每一个元素都相当于一个指针变量。
类型名 * 数组名[数组长度]; 如:int *p[4];
其形参为指针的指针。**s <===>*s[]。
void sortString(char **s, int len)
{
int i,j;
for(i = 0;i < len -1;++i)
{
for(j = i + 1;j < len;++j)
{
if(strcmp(*(s+i), *(s+j)) > 0)
{
swap(s+i,s + j);
}
}
}
}