指针进阶(二)(C语言)

🌞欢迎来到C语言的世界 
🌈博客主页:卿云阁

💌欢迎关注🎉点赞👍收藏⭐️留言📝

🌟本文由卿云阁原创!

🌠本阶段属于锻体阶段,希望各位仙友顺利完成突破

📆首发时间:🌹2021年1月17日🌹

✉️希望可以和大家一起完成进阶之路!

🙏作者水平很有限,如果发现错误,请留言轰炸哦!万分感谢!


目录

0️⃣指针作为函数参数

1️⃣返回指针值的函数

2️⃣指向函数的指针

3️⃣指向指针的指针

4️⃣void*指针

0️⃣✨✨✨指针作为函数参数✨✨✨ 


1.改变数组中元素的值

#include<stdio.h>
void print(int *b)
{  
  printf("%d\n",*b+1);
  *b=26;
}
void main(void)
{
int a[6]={1,2,3,4,5,6};
print(a);
printf("%d ",a[0]);
} 

 2.利用指针交换两个数的值

#include <stdio.h>
int main(void)
{
	void swap(int *x,int *y);
	int a=11,b=22;
	swap(&a,&b); 
	printf("%d,%d\n",a,b);
	return 0;
}
 //形参为指针变量,接收两个int型变量的地址。
void swap(int *x,int *y)
{  
	*x=*x+*y;
	*y=*x-*y;
	*x=*x-*y;
}


1️⃣✨✨✨返回指针值的函数✨✨✨

数据类型 *函数名(参数列表){...}

 例:int  *fun(int x, int y) {...}

引例;

int add(int a,int b)
{
return a+b;
}

此时返回的是基本类型

例.返回数组里最大值的地址

#include<stdio.h>
int *print(int *b)
{   int max=0;
    for(int i=0;i<6;i++)
    {
	  if(b[max]<b[i])
          max=i;
    }
    return b+max;
}
int main(void)
{
	int a[6]={18,29,13,4,75,36};
	int *p;
	p=print(a);
	printf("%d\n",*p);	
	
}


2️⃣✨✨✨指向函数的指针✨✨✨ 

 函数就是一系列指令的集合,在调用后,这些指令是存放在一个叫做代码区的内存中。函数名的值也不可更改,而且可以作为一个指针,其值为函数指令序列(代码区)的起始地址值,指向的数据类型称为函数类型。(这一点与数组类似)。 函数是数据类型的一种,在C语言中,函数返回类型、形参类型、个数和顺序完全相同的函数才是同一种类型的函数,只要有一个不同,就不是同一种数据类型。

引例1:

int a[5];
int *p;
*p=a;

引例1:指向一维数组的指针

char str[3][10]={"123","456","789"};
    char(*ch)[10];

指针变量指向一个函数要怎么定义?

一个函数指针变量的声明格式如下。

返回类型 (*变量名) (参数类型列表);

(1) int (*fun1)(double);  //形参为一个double型数据,返回一个int型数据

(2) void (*fun2)(char*);  //形参为指向char型数据的指针变量,不返回数据。

(3) double* (*fun3)(double *,int); //形参为一个指向double型数据的指针变量和一个int型变量,返回一个指向double数据的指针。

(4) int (*fun4)();  //没有形参,返回一个int型数据。

同一种类型的函数

1,返回类型

2.形参的个数,顺序。

3.每一个形参的类型

#include<stdio.h>
int add(int x, int y)
{
	return x + y;
}

int sub(int x, int y)
{
	return x - y;
}
int mul(int x, int y)
{
	return x * y;
}

int div1(int x, int y)
{
	return x / y;
}

int main()
{
	int (*p)(int,int);
	p=sub;                     //h函数名是地址 
	int b=p(6,8);
	printf("%d",b);
}

函数名的值也不可更改,而且可以作为一个指针,其值为函数指令序列(代码区)的起始地址值,指向的数据类型称为函数类型。

优化 

#include<stdio.h>
int add(int x, int y)
{
	return x + y;
}

int sub(int x, int y)
{
	return x - y;
}
int mul(int x, int y)
{
	return x * y;
}

int div1(int x, int y)
{
	return x / y;
}
int cal(int a,int b,int (*p)(int ,int ))
{
	return p(a,b);
}
int main()
{
    int a=10,b=40;
    b=cal(a,b,add);
	printf("%d",b);
}

 函数名的值也不可更改,而且可以作为一个指针,其值为函数指令序列(代码区)的起始地址值,指向的数据类型称为函数类型。


3️⃣✨✨✨指向指针的指针✨✨✨

数据类型 **变量名;

int **p; 此变量存放一个指针,这个指针指向另一个指针值(数据类型为指向一个int类型的指针)(p占8个字节)p的数据类型为指向一个int类型的指针。

int **p;
int *a;
int x=10;
a=&x;
p=&a;


 注意:

(1)

int a[3][6];
   int **p;
   p=a;
   return 0;//错误的


p的数据类型为指向一个int类型的指针。

a指向一维数组的指针。

(2)

int **p;
**p=5: //错误的


p:(装的是一个地址)此时是乱码的,假设为-1
*p:(装的是一个地址)该空间不一定可用

int *a;
int x;
*a=&x;
*a=5; //对的


例.1
给定5个字符串,把它们的首地址放在一个指向char型的一维数组中,char* songs[5]={ "I see", "How are you", " see me", "Thanks", "see you later"};写一个函数,把包含"see"的整个字符串改成"saw"输出

#include <stdio.h>
#include <string.h>
//把含"see"的串修改为"saw",其实就是把对应行的地址值改为串"saw" 
//所在的地址,并不是修改含有"see"的串。
void convertStr(char **buf,int size) //size接收数组songs的元素个数。
{
    char **tmp = buf;
 //遍历每一个字符串,如果包含"see",则修改为saw。
    while (buf < tmp + size)
{
        if(strstr(*buf,"see") != NULL) //判断是否包含"see"。
{
            *buf = "saw";  //把"saw"的首地址值赋给*buf。
        }
        buf++;   //buf指向指针类型数据,加1指向下一个指针数据。
    } 
}
void printString(char **s,int size) //输出字符串。
{
    char **start = s;
    for (;s < start + size;s++)
        printf("%s\n",*s); //输出首地址为s的串。
}
int main(void)
{
char* songs[5]={ "I see","How are you"," you see me", "Thanks","see you \
later"}; //指向char型的指针数组。
char **p = songs; // p是二级指针,与songs都指向指针类型数据,且
//这个指针数据都指向char型数据。可以赋值。
convertStr(p,5);  //调用修改串的函数。
printString(p,5);  //输出修改后的结果。
return 0;
}


 

 


4️⃣✨✨✨void*指针✨✨✨

void *指针变量名; 它与任意指针变量之间可以互相赋值

void *p(p可以接受任何类型的指针)

好处:

现实中有些数据类型不知道,可以通过这个方法改。

mn

                                        


拷贝内存

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void swap(void* a, void *b, int size)
{
    void *p = malloc(size); 
    memcpy(p, a, size);    
    memcpy(a, b, size);
    memcpy(b, p, size);
    free(p); 
    p=NULL;
}
int main(void)
{
    int m=6,n=12;
    short x=10,y=20;
    swap(&m,&n,sizeof(int));
    printf("m=%d,n=%d\n",m,n);
    swap(&x,&y,sizeof(short)); 
    printf("x=%hd,y=%hd\n",x,y);
    return 0;
}

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

卿云阁

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值