static和const关键字

static 关键字

static修饰局部变量

  • static用于修饰局部变量时,通常在某个函数体内,只能在此函数内调用。

    void test()
    {
        int i = 0;//  若i的数据类型为int
        i++;
        printf("%d ", i);
    }
    int main()
    {
        int i = 0;
        for (i = 0; i < 10; i++)
        {
            test();
        }
        return 0;
    }//因为 i 是局部变量,函数调用完之后,i的值被释放,当再次调用时,i为初值0
           打印结果:1 1 1 1 1 1 1 1 1 1
    void test()
    {
        static int i = 0;//若 i 的数据类型为static int
        i++;
        printf("%d ", i);
    }//static定义的变量,称为局部静态变量,存放在局部静态区,值不会因为随着函数调用的结束被释放,再次调用时,它的值是上一次调用结束后的值。
    ​
     打印结果:1 2 3 4 5 6 7 8 9 10

    修饰全局变量

  • static还可以修饰全局变量,该变量在某一个文件中,但不属于任何一个函数范围内,通常称为静态局部变量

1.

test.c
​
int a=2020;//在test文件中定义int类型的变量

创建了两个C文件,用extern声明外部符号

main.c
​
extern a;
int main()
{
print("%d",a);
return 0;
}
结果:2020

2.

test.c
​
static int a=2020;//在test文件中定义int类型的变量

创建了两个C文件,用extern声明外部符号

main.c
​
extern a;
int main()
{
print("%d",a);
return 0;
}
结果:fatal error :1个无法无法解析的外部命令     // 报错

解释:一个全局变量本来是有外部链接属性的,但是被static修饰后,外部链接属性就变成了内部链接属性,只能在自己所在的源文件内部使用,不能在其他文件内部使用。

static修饰函数

  • static还可以用于修饰一个函数,这样的函数称之为静态函数

1.

test.c
​
int add(int a,int b)
{
return a+b;
};          //在test文件中定义返回值为int类型的函数

创建了两个C文件,用extern声明外部符号

main.c
​
extern add(int a,int b);
int main()
{
int a=2;
int b=3;
int ret =add(a,b);
​
printf("%d",ret);
return 0;
}
结果: 5

2.

test.c
​
static int add(int a,int b)
{
return a+b;
};          //在test文件中定义返回值为static int类型的函数

创建了两个C文件,用extern声明外部符号

main.c
​
extern add(int a,int b);
int main()
{
int a=2;
int b=3;
int ret =add(a,b);
​
printf("%d",ret);
return 0;
}
结果:结果:fatal error :1个无法无法解析的外部命令     // 报错

解释·:定义一个静态函数就是在函数的返回类型前加上static关键字。静态函数的作用域仅限于本文件,不能被其他文件调用。

const 关键字

修饰变量

  • 变量前用const修饰,把变量声明为常量初始化后其值不能被修改

#include <stdio.h>
//错误案例
int main()
{
const int a = 200;   //const修饰成常量后a的值不能被修改  
//const int a,int const a,两者写法不同,意义相同
a = 50;              //错误,const修饰a为常量,常量a的值不能修改
​
printf("%d", a);
return 0;
}

修饰指针

  • 指针常量:const修饰p,表示p所指向的内存地址不可以改变,但可以改变p指向的变量的值

//错误案例
​
int a = 1;
int * const p = &a;
​
p++;//错误,const修饰指针p,p指向的变量的内存地址不能改变
printf("%d\n", *p);
//正确案例
​
int a = 1;
int * const p = &a;
​
*p = 2;//正确,const修饰指针p,p指向的变量的值可以改变
printf("%d\n", *p);
  • 常量指针:const修饰*p,表示p指针指向的变量的值不可以改变, 但可以改变p指向的内存地址

//错误案例
​
int a = 1;
int const * p = &a;
​
*p = 2;//错误,const修饰*p,*p的值不能被修改
printf("%d\n", *p);
//正确案例
int a = 1;
int const * p = &a;
printf("%p\n", p);
​
p++;//正确,p的指向的地址可以改变
printf("%p\n", p);
​
结果: 0x7fffc8f3780c
      0x7fffc8f37810     //指针偏移了4个字节,正好是一个int型变量占用的内存地址
  • const 修饰 ” * “ 与p,表示p指向的变量的值与p指向的地址都不能改变,” * “是解引用,用于获取指针p指向的变量的值,p是指针指向某段内存地

//错误案例
​
int a = 1;
const int * const p = &a;
​
*p = 2;//错误,p指向的变量的值不能改变
p++;//错误,p指向的地址也不能改变

修饰函数参数的指针形参

  • const char str作为函数参数:str被const修饰,它可以避免传递过来的值在函数体内部被错误修改

//错误案例
​
void printString(const char *str)
{
    *str = "hello";//错误,const修饰*str,*str指向的变量的值不能被修改
    printf("%s\n", str);
}
 
int main()
{
    char s[] = "hello world!";
    printString(s);
    printf("%s\n", s);
    return 0;
}

修饰函数返回值

正确案例
​
#include <stdio.h>
//const int getNum也可以写成int const getNum,两者意义相同
​
const int getNum(int x)
{
    return x = 5;
}//返回值类型是const int 即返回值不变,为5
 
int main()
{
    int a = 2;
    int ret = getNum(a);
    printf("ret = %d\n", ret);
    return 0;
}
结果: ret = 5                 //getNum函数的返回值并没有被传递过来的实参a修改,因此,函数的返回值被const修饰后,可以确保函数的返回值在使用的过程中不会被修改

总之,const靠近谁,谁就不能被修改

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值