当指针和函数、数组在一起了,那么可怕的事情就发生了!

函数与指针

函数指针变量定义的一般形式为:  类型说明符 (*指针变量名)(); 

例如:int (*pf)();表示一个pf指针是一个指向函数的指针变量,该函数的返回值是整型。(*p)的两边的括号不能少。

定义指针型函数的一般形式为: 类型说明符 *函数名(形参表)

                                                         {  …… /*函数体*/  }                  

例如:int  *p();说明p是一个指针型函数,其返回值是一个指向整型量的指针,*p两边没有括号。

思考

对于以下两个表达式:

1、int *(*(*fp)(int))[10]; :表示指针fp,指向一个函数,这个函数的参数是int型、返回值是一个指针,返回的这个指针又指向一个数组,数组里有10个元素,每个元素都是一个指针,每个指针都是int *型。

2、int *(*(*array[5])())();:表示array是一个数组,数组里有5个元素,每个元素都是一个指针,每个指针指向一个函数,函数的返回值是一个指针,返回的指针指向返回值为*的函数。

二位数组和指针

指针数组说明的一般形式为:     类型说明符 *数组名[数组长度]     

其中类型说明符为指针值所指向的变量的类型。     

例如: int *pa[3];       表示pa是一个指针数组,它有三个数组元素,每个元素值都是一个指针,指向整型变量。

指向二维数组的指针的几种表示

表示形式

含义

地址值

&a 

指向二维数组的指针

1000

a

二维数组名,指向一维数组a[0],即第0行首地址

1000

a[0] , *(a+0) , *a

0行第0列元素地址

1000

a+1 , &a[1]

1行首地址

1006

a[1] , *(a+1)

1行第0列元素地址

1006

a[1]+2 , *(a+1)+2 , &a[1][2]

1行第2列元素地址

1010

*(a[1]+2) , *(*(a+1)+2) , a[1][2]

1行第2列元素的值

元素值为11

例如:
main()
{   int a[3][4]={{1,2,3,4},{3,4,5,6},{5,6,7,8}};
    int i;
    int (*p)[4]=a,*q=a[0];
    for(i=0;i<3;i++)
    {   
        if(i==0)
            (*p)[i+i/2]=*q+1;
        else
            p++,++q;
    }
    for(i=0;i<3;i++)
    {
        printf("%d,",a[i][i]);
    }
    printf("%d,%d\n",*((int *)p),*q);

输出结果为:2,4,7,5,3

例:

#include <stdio.h>
 
int main()
{
    int i, j;
    int a[3][4] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12};
    int (*p)[4] = a;
 
    for(i = 0; i < 3; i++)
    {
        for(j = 0; j < 4; j++)
        {
            printf("%d ", a[i][j]);
            printf("%d ", *(*(p + i) + j));
            printf("%d ", p[i][j]);
            printf("%d ", (*(p + i))[j]);
        }
        printf("\n");
    }
    return 0;
}

其中 a[ i ] [ j ] === * ( * ( p + i) + j ) === ( * ( p + i ) ) [ j ] === p[ i ] [ j ]

指针的指针!

#include <stdio.h>
int main()
{
	char *name[]={"Follow me","BASIC","Great Wall","FORTRAN","Computer desighn"};
	char **p;
	int i;
	for(i=0;i<5;i++)  
	{
		p=name+i;
		printf("%s\n",*p);
	}
	
	return 0;	
}

输出结果:
Follow me
BASIC
Great Wall
FORTRAN
Computer desighn

利用代码思考二级指针的作用和使用方法。

main函数

main (int argc,char *argv[])  

1、argc(第一个形参)必须是整型变量,  argc参数表示了命令行中参数的个数(注意:文件名本身也算一个参数);

2、argv( 第二个形参)必须是指向字符串的指针数组。argv参数是字符串指针数组,其各元素值为命令行中各字符串(参数均按字符串处理)的首地址。 针数组的长度即为参数个数。

简单的例题:用变量a给出下面的定义。

1、一个整型数  int a

2、一个指向整型数的指针  int *a

3、资格指向指针的指针,它指向的指针是指向一个整型数     int *(*a)

4、一个有10个整型数的数组     int a[10]

5、一个有10个指针的数组,该指针是指向一个整型数的     int *a[10]

6、一个指向有10个整型数数组的指针     int (* a)[10]

7、一个指向函数的指针,该函数有一个整型参数并返回一个整型数     int (*a)(int)

8、一个有10个指针的数组,该指针指向一个函数,该函数有一个整型参数并返回一个整型数     int(*a[10])(int)

利用指针和命令行实现冒泡排序:

#include <stdio.h>
#include <string.h>
 
int greater(int x, int y)     
{
    return (x > y)? 1 : 0;
}
 
int less(int x, int y)
{
    return (x < y) ? 1 : 0;  
}
 
void sort(char *a[], int argc, int (*p)(int, int))
{
    int i, j;
    char *tmp;
    
    for(i = 1; i < argc; i++ )
    {
        for(j = 1; j < argc - i; j++)
        {
           /* if((strcmp(a[j], a[j + 1])) < 0)*/
            if(p(*a[j], *a[j + 1]))
           {
            tmp = a[j];
            a[j] = a[j+1];
            a[j+1] = tmp;
            }
        }
    }
}
 
void print(char *argv[], int argc)
{
    int i;
    for(i = 1; i < argc; i++)
    {
        printf("%s ", argv[i]);
    }
}
 
int main(int argc, char *argv[])
{
    int i = 0;
    sort(argv, argc, less);
    print(argv, argc);
    printf("\n");
    return 0;
}

猜你喜欢

转载自blog.csdn.net/wow66lfy/article/details/81253133