1. const指针
const关键字,常量(只读)
const int *p;
int const *p;
int *const p;
const int *const p;
int const *const p;
1和2是等价的:const修饰p,指针变量p的值可以改变, 但不能利用指针修改指向空间中的值
3:const修饰p,指针变量p的值不能改变,但可以利用指针变量p修改指向空间中的值(一定要对指针初始化)
4和5是等价的:const修饰p和*p,指针变量p的值不能改变,也不能利用*p改变直系那个空间中的值(一定要初始化)
2. void
//高精度
int *p;
double *p;
char *p;
//低精度
void *p //p保存内存地址
int * 、double * 、char * 转换为void * 需要强制类型转换
void *转换为int * 、double * 、char * 不需要强制类型转换
strcpy拷贝字符串
memcpy拷贝一段内存空间
3. 函数指针和指针函数
指针函数:是函数,函数的返回值类型是指针类型
函数指针:是指针,指针指向了函数
1. 指针函数:
局部变量的地址不能返回,因为局部变量会随函数作用域结束被回收,虽然能获得返回的地址,但地址对应的空间已经被回收过了
将函数的返回值作为下一个函数的参数
2. 函数指针:
int (*Fun)(int a, int b) = NULL;
定义函数指针变量Fun,占8个字节空间,指向int返回值2个int参数的函数
练习:
1. 定义一个指针函数,实现字符串数组用来拷贝的strcpy函数
#include <stdio.h>
char *Mystrcpy(char *pdst, char *psrc)
{
char *pret = pdst;
while(*psrc != '\0')
{
*pdst = *psrc;
psrc++;
pdst++;
}
*pdst = '\0';
return pret;
}
int main(void)
{
char str[32] = {0};
char dst[32] = {0};
Mystrcpy(dst, Mystrcpy(str, "hello world"));
printf("str = %s\n",str);
printf("dst = %s\n",dst);
}
2. 利用函数指针,实现数组的排序(升序、降序、绝对值升序、绝对值降序)
#include <stdio.h>
#include <stdlib.h>
int InputArray(int *parray, int len)
{
int i = 0;
for(i = 0; i < len; i++)
{
scanf("%d",&parray[i]);
}
return 0;
}
int SortArray(int *parray, int len, int (*pcompay)(int, int))
{
int i = 0;
int j = 0;
int tmp = 0;
for(j = 0; j < len-1; j++)
{
for(i = 0; i < len-1-j; i++)
{
if(pcompay(parray[i], parray[i+1]))
{
tmp = parray[i];
parray[i] = parray[i+1];
parray[i+1] = tmp;
}
}
}
return 0;
}
int OutputArray(int *parray, int len)
{
int i = 0;
for(i = 0; i < len; i++)
{
printf("%d ",parray[i]);
}
printf("\n");
return 0;
}
int AscCompare(int num1, int num2)
{
if(num1 > num2)
{
return 1;
}
return 0;
}
int DescCompare(int num1, int num2)
{
if(num1 < num2)
{
return 1;
}
return 0;
}
int AbsAscCompare(int num1, int num2)
{
if(abs(num1) > abs(num2))
{
return 1;
}
return 0;
}
int AbsDeascCompare(int num1, int num2)
{
if(abs(num1) < abs(num2))
{
return 1;
}
return 0;
}
int main(void)
{
int a[5] = {0};
InputArray(a, 5);
SortArray(a, 5, AscCompare);
printf("升序: ");
OutputArray(a, 5);
SortArray(a, 5, DescCompare);
printf("降序: ");
OutputArray(a, 5);
SortArray(a, 5, AbsAscCompare);
printf("绝对值升序: ");
OutputArray(a, 5);
SortArray(a, 5, AbsDeascCompare);
printf("绝对值降序: ");
OutputArray(a, 5);
return 0;
}
4. C语言中二级指针使用场景:
1. 指针数组传参时:
char *str[5];
int Fun(char **ppstr, int len);
2. 函数体内想修改函数体外指针变量值的时候,要传递指针变量的地址即二级指针
char *p = NULL;
int Fun(char **pp);
5. 构造数据类型:
数据类型:
1. 基本数据类型:
int、double、 char
2. 构造数据类型:
1. struct 结构体
2.union 共用体
3. enum 枚举
1. 结构体:
1. 结构体类型的定义
struct 结构体名
{
数据类型1 成员变量1;
数据类型2 成员变量2;
数据类型3 成员变量3;
......
};
2. 结构体变量的定义
数据类型 变量名;
数据类型 *指针变量名;
3. 结构体变量的初始化
1. 全部初始化:
struct students = {"zhangsan", 'm', 19, 100};
2. 局部初始化:
struct student stu = {
.name = "lisi",
.score = 90,
};
4. 结构体成员变量的访问:
. :结构体变量类型访问成员变量使用 .
->:结构体指针类型访问成员变量使用 ->
整体类型由成员变量类型决定
作业:
1. 定义一个结构体包含年-月-日三个成员,从终端接收年月日信息存放到结构体中,计算该年为第几天?计算该年剩余多少天?打印年月日信息
#include <stdio.h>
#include <string.h>
struct data
{
int year;
int mon;
int day;
};
int IsLeepYear(int Year)
{
if(Year % 400 == 0)
{
return 1;
}
else if(Year % 4 ==0 && Year % 100 != 0)
{
return 1;
}
else
{
return 0;
}
}
int GetDayOfYear(int Year, int Mon, int Day)
{
int i = 0;
int NowDay = 0;
for(i = 0; i < Mon; i++)
{
if(i==1 || i==3 || i==5 || i==7 || i==8 || i==10 || i==12)
{
NowDay += 31;
}
else if(i == 4 || i ==6 || i == 9 || i==11)
{
NowDay += 30;
}
else if(i == 2)
{
if(IsLeepYear(Year))
{
NowDay += 29;
}
else
{
NowDay += 28;
}
}
}
NowDay += Day;
return NowDay;
}
int GetLeftDayOfYear(int Year,int Mon,int Day)
{
int RemDay = 0;
if(IsLeepYear(Year))
{
RemDay = 366 - GetDayOfYear(Year, Mon, Day);
}
else
{
RemDay = 365 - GetDayOfYear(Year, Mon, Day);
}
return RemDay;
}
int main(void)
{
struct data d;
int NowDay = 0;
int RemDay = 0;
memset(&d, 0, sizeof(d));
scanf("%d%d%d", &d.year, &d.mon, &d.day);
NowDay = GetDayOfYear(d.year, d.mon, d.day);
RemDay = GetLeftDayOfYear(d.year, d.mon, d.day);
printf("%d-%d-%d是此年的第%d天,还剩余%d天\n", d.year, d.mon, d.day,
NowDay, RemDay);
return 0;
}
2. 封装一个函数,给定一个数字字符串转换成其对应的整型数
如:“123456” 得到123456
#include <stdio.h>
#include <string.h>
int MyAtoi(char *pstr)
{
int sum = 0;
while(*pstr != '\0')
{
sum *= 10;
sum += (*pstr-'0');
pstr++;
}
return sum;
}
int main(void)
{
char num[32] = {0};
int sum = 0;
gets(num);
sum = MyAtoi(num);
printf("%d\n",sum);
return 0;
}