C语言基础知识--变量

目录

一、C语言变量

1、局部变量

1)、什么是局部变量

2)、代码示例

3)、代码讲解

2、全局变量

1)、什么是全局变量

2)、代码示例

3)、代码讲解

3、静态变量

1)、全局静态变量

2)、局部静态变量

3)、代码示例

4)、代码讲解

4、const常量

1)、const变量

5、寄存器变量

1)、register变量

2)、代码示例

3)、代码讲解

二、总结


一、C语言变量

本文用到ARM汇编指令,请参考:

ARM常用汇编指令_BIN-XYB的博客-CSDN博客

本文用到编译器为在线编译器(ARM-GCC):

Compiler Explorer

1、局部变量

1)、什么是局部变量

局部变量,顾名思义,只在局部区域有效的变量。

局部变量的空间开辟在栈中,在程序运行过程中动态开辟,局部变量的生命周期随着函数调用的开始而开始,随着函数调用的结束而结束。

2)、代码示例
#include <stdio.h>

int test_func(int param0, int param1)
{
    int b = 4;
    return b;
}

int main()
{
    test_func(1, 3);
    return 0;
}

编译后汇编如下:

test_func:
        push    {r7}
        sub     sp, sp, #20
        add     r7, sp, #0
        str     r0, [r7, #4]
        str     r1, [r7]
        movs    r3, #4
        str     r3, [r7, #12]
        ldr     r3, [r7, #12]
        mov     r0, r3
        adds    r7, r7, #20
        mov     sp, r7
        ldr     r7, [sp], #4
        bx      lr
main:
        push    {r7, lr}
        add     r7, sp, #0
        movs    r1, #3
        movs    r0, #1
        bl      test_func
        movs    r3, #0
        mov     r0, r3
        pop     {r7, pc}
3)、代码讲解

在test_func函数中定义局部变量b,且初始化为4,分析test_func汇编代码,如下图圈住地方(对应c语言的语句 int b = 4;):

将立即数4写入寄存器R3中,然后将R3寄存器中值写入栈(R7+12Byte处)中。完成局部变量的空间开辟以及值初始化。

2、全局变量

1)、什么是全局变量

全局变量是在代码文件中定义的全局变量,在整个源文件中皆可访问。如果要在其他源文件中使用该变量,需要使用extern关键字引用。

全局变量的空间开辟在全局变量区,全局变量的生命周期同程序的生命周期相同。

2)、代码示例
#include <stdio.h>
int a = 3;
int test_func(int param0, int param1)
{
    int b = a;
    return b;
}

int main()
{
    test_func(1, 3);
    return 0;
}

编译后汇编如下:

a:
        .word   3
test_func:
        push    {r7}
        sub     sp, sp, #20
        add     r7, sp, #0
        str     r0, [r7, #4]
        str     r1, [r7]
        movw    r3, #:lower16:a
        movt    r3, #:upper16:a
        ldr     r3, [r3]
        str     r3, [r7, #12]
        ldr     r3, [r7, #12]
        mov     r0, r3
        adds    r7, r7, #20
        mov     sp, r7
        ldr     r7, [sp], #4
        bx      lr
main:
        push    {r7, lr}
        add     r7, sp, #0
        movs    r1, #3
        movs    r0, #1
        bl      test_func
        movs    r3, #0
        mov     r0, r3
        pop     {r7, pc}
3)、代码讲解

定义全局变量a,且初始化为3。在test_func函数中定义局部变量b且将全局变量a的值赋予局部变量b,分析汇编代码,如下图圈住地方(对应c语言的语句 int b = a;):

将全局变量a的地址写入寄存器R3中,然后将R3寄存器中所指向地址中的数据读取到R3寄存器中,然后将R3寄存器中值写入栈(R7+12Byte处)中。将局部变量b初始化成全局变量a的值。由以上分析可以看出全局变量并不像局部变量那样保存在栈上,而是定义在数据段上。

3、静态变量

1)、全局静态变量

全局静态变量是指定义在代码文件中的用static修饰的变量,静态全局变量存储在静态变量区,生命周期伴随程序的整个生命周期。只可在定义该变量的源文件中使用,不可在其他源文件中使用extern关键字引用该文件。

2)、局部静态变量

局部静态变量是指在函数内定义的使用static修饰的变量。局部全局变量存储在静态变量区,生命周期伴随程序的整个生命周期。尽可在定义该变量的函数内使用。

3)、代码示例
#include <stdio.h>
static int a = 5;
int test_func(int param0, int param1)
{
    static int b = 2;
    b++;
    a++;
    return b;
}

int main()
{
    int ret = test_func(1, 3);
    printf("b:%d\r\n", ret);
    ret = test_func(1, 3);
    printf("b:%d\r\n", ret);
    return 0;
}

编译后汇编如下:

a:
        .word   5
test_func:
        push    {r7}
        sub     sp, sp, #12
        add     r7, sp, #0
        str     r0, [r7, #4]
        str     r1, [r7]
        movw    r3, #:lower16:b.0
        movt    r3, #:upper16:b.0
        ldr     r3, [r3]
        adds    r2, r3, #1
        movw    r3, #:lower16:b.0
        movt    r3, #:upper16:b.0
        str     r2, [r3]
        movw    r3, #:lower16:b.0
        movt    r3, #:upper16:b.0
        ldr     r3, [r3]
        mov     r0, r3
        adds    r7, r7, #12
        mov     sp, r7
        ldr     r7, [sp], #4
        bx      lr
.LC0:
        .ascii  "b:%d\015\012\000"
main:
        push    {r7, lr}
        sub     sp, sp, #8
        add     r7, sp, #0
        movs    r1, #3
        movs    r0, #1
        bl      test_func
        str     r0, [r7, #4]
        ldr     r1, [r7, #4]
        movw    r0, #:lower16:.LC0
        movt    r0, #:upper16:.LC0
        bl      printf
        movs    r1, #3
        movs    r0, #1
        bl      test_func
        str     r0, [r7, #4]
        ldr     r1, [r7, #4]
        movw    r0, #:lower16:.LC0
        movt    r0, #:upper16:.LC0
        bl      printf
        movs    r3, #0
        mov     r0, r3
        adds    r7, r7, #8
        mov     sp, r7
        pop     {r7, pc}
4)、代码讲解

定义静态全局变量a,且初始化为5。在test_func函数中定义的静态局部变量b为,且初始化为2,分析汇编代码a++(绿框圈住)和b++(红框圈住)语句:

        movw    r3, #:lower16:b.0

        movt    r3, #:upper16:b.0 ; 将变量b的地址写入到R3寄存器

        ldr     r3, [r3];将b的值读取到寄存器R3中

        adds    r2, r3, #1;寄存器R3自增,结果保存到R2寄存器

        movw    r3, #:lower16:b.0

        movt    r3, #:upper16:b.0;将变量b的地址写入到R3寄存器

        str     r2, [r3];R2寄存器中运算结果写入R3寄存器中所指的地址中

变量a分析雷同。静态变量a与b的区别是a可以再整个源文件中访问,b只可以在函数test_func中访问。

4、const常量

1)、const变量

const变量,为只读变量,在编码过程中只可对该变量进行读,不可修改该变量的值。该变量会被存放在常量区,生命周期伴随程序的整个生命周期。

5、寄存器变量

1)、register变量

register变量,为寄存器变量,在编码过程中使用该变量修饰局部变量,告诉编译器将此变量尽量存储在寄存器中,编译器会根据现实情况,来尽可能的降该变量的存储空间开辟在CPU寄存器中,但不是绝对可以开辟在寄存器中。register关键字只可以用来修饰局部变量。

2)、代码示例
#include <stdio.h>

int test_func(int param0, int param1)
{
    register int a = 5;
    int b = a + 2;
    return b;
}

int main()
{
    test_func(1, 3);
    return 0;
}

编译后汇编如下:

test_func:
        push    {r4, r7}
        sub     sp, sp, #16
        add     r7, sp, #0
        str     r0, [r7, #4]
        str     r1, [r7]
        movs    r4, #5
        adds    r3, r4, #2
        str     r3, [r7, #12]
        ldr     r3, [r7, #12]
        mov     r0, r3
        adds    r7, r7, #16
        mov     sp, r7
        pop     {r4, r7}
        bx      lr
main:
        push    {r7, lr}
        add     r7, sp, #0
        movs    r1, #3
        movs    r0, #1
        bl      test_func
        movs    r3, #0
        mov     r0, r3
        pop     {r7, pc}
3)、代码讲解

在test_func函数中定义寄存器局变量a,且初始化为5。定义局部变量b,且初始化为a+2,分析汇编代码(register int a = 5; int b = a + 2;)语句:

        movs    r4, #5;将立即数5写到寄存器R4中

        adds    r3, r4, #2;将R4中的值与立即数2相加,结果保存在寄存器R3中

        str     r3, [r7, #12];,将R3中运算结果保存到栈中(R7+12Byte处)。

由上分析可知,变量a被保存在寄存器中,变量b被保存在栈中。

二、总结

如有问题请批评指出,感谢!

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: C语言基础知识入门PDF是一份C语言的教学材料,适合初学者学习和掌握C语言的基本语法、语义和编程方法。 C语言是一种高效、灵活、可移植、可扩展的编程语言,被广泛应用于操作系统、数据库系统、嵌入式系统等领域。学习C语言,需要掌握计算机基本原理、编程思想和算法设计等知识,而C语言基础知识入门PDF提供了一种快速入门、易于理解的学习途径。 C语言基础知识入门PDF包括了C语言的基本数据类型、运算符、流程控制语句、函数、指针、数组、结构体等内容,通过实例演示和练习题目的方式,帮助学生深入理解C语言的编程思想和技巧。 此外,C语言基础知识入门PDF还介绍了一些常用的C语言开发工具,如编辑器、编译器和调试器等,帮助学习者掌握基本的开发环境和技巧。 总之,C语言基础知识入门PDF是一本很好的C语言入门教材,通过细致详尽的篇章结构、浅显易懂的代码示范和解释,对于初学者学习C语言或复习C语言基础知识来说,都是一份很好的参考资料。 ### 回答2: 《C语言基础知识入门》是一本适合初学者入门的C语言教材,它由浅入深地介绍了C语言的基本语法、数据类型、控制结构、函数以及指针等内容。这本教材所包含的知识点非常基础和易懂,对于初学者来说非常友好,能够循序渐进地帮助他们逐步掌握C语言的基本概念和基础知识。 在学习过程中,这本教材还特别注重实践,提供了大量的实例代码以及习题和答案,帮助学生巩固所学知识,培养编程思维,提高编程能力。此外,这本教材还介绍了一些C语言的衍生语言和标准库,让学生在了解基础知识的同时,对C语言的发展和应用方向也有所了解。 总之,对于初学者来说,《C语言基础知识入门》是一本非常好的入门教材,它简单易懂、注重实践、知识面广泛、涵盖了C语言的基本知识点和实际应用场景,推荐给所有对于C语言感兴趣的初学者。 ### 回答3: 《C语言基础知识入门PDF》是一本适合初学者的C语言教程,它详细介绍了C语言的各个方面。该教程涵盖了C语言的基本语法、数据类型、运算符、流程控制、函数、指针、结构体、文件操作等重要内容。通过学习这本教程,初学者可以逐步掌握C语言基础知识,轻松理解编程思路。 该教程首先讲解了C语言的数据类型,包括整型、浮点型、字符型等,以及变量的定义和命名方法。接着介绍了运算符的使用方法,包括算术运算符、关系运算符和逻辑运算符。 在掌握了基础语法之后,该教程讲解了流程控制语句,如if语句、switch语句和循环语句等。这些语句非常重要,可以让程序根据不同的情况执行不同的操作。 接着,该教程介绍了函数的定义和调用方法。函数可以让程序模块化,使代码更具可读性。同时,它还讲解了指针的概念和使用方法,指针可以让程序更加灵活。 最后,该教程讲解了文件操作。文件是计算机存储数据的重要方式,学会文件操作可以让程序更好地处理数据。 总的来说,《C语言基础知识入门PDF》适合没有任何编程基础的初学者阅读。通过阅读该教程,初学者可以了解C语言的基本语法和编程思想,为以后深入学习打下基础。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值