一、全局变量

  1. 定义在函数外面的变量是全局变量
  2. 全局变量具有全局的生存期和作用域
  3. 它们与任何函数无关,在任何函数内部都可以使用它们
#include <stdio.h>

int f(void);

// 全局变量
int gALL = 12; int main(int argc, char const *argv[])
{
printf("in %s gALL=%d\n", __func__,gALL);
f(); printf("agn in %s gALL=%d\n", __func__,gALL); return 0;
} int f(void)
{
printf("in %s gALL=%d\n", __func__,gALL);
gALL += 8;
printf("agn in %s gALL=%d\n", __func__,gALL);
return gALL;
} // in main gALL=12
// in f gALL=12
// agn in f gALL=20
// agn in main gALL=20

二、全局变量初始化

  1. 没有做初始化的全局变量会得到0值
  2. 指针会得到NULL值
  3. 只能用编译时刻已知的值来初始化全局变量
  4. 它们的初始化发生在main函数之前

三、被隐藏的全局变量

如果函数内部存在与全局变量同名的变量,则全局变量被隐藏

#include <stdio.h>

int f(void);

// 全局变量
int gALL = 12; int main(int argc, char const *argv[])
{
printf("in %s gALL=%d\n", __func__,gALL);
f(); printf("agn in %s gALL=%d\n", __func__,gALL); return 0;
} int f(void)
{
// 这里定义一个名字相同的变量,那么全局的就被隐藏了
int gALL = 1;
printf("in %s gALL=%d\n", __func__,gALL);
gALL += 8;
printf("agn in %s gALL=%d\n", __func__,gALL);
return gALL;
}
// in main gALL=12
// in f gALL=1
// agn in f gALL=9
// agn in main gALL=12

四、静态本地变量

  1. 在本地变量定义时加上static修饰符就成为静态本地变量
  2. 当函数离开的时候,静态本地变量会继续存在并保持其值
  3. 静态本地变量的初始化只会在第一次进入这个函数时做,以后进入函数时会保持上次离开的值
#include <stdio.h>

int f(void);

int main(int argc, char const *argv[])
{
f();
f(); return 0;
} int f(void)
{
static int all = 1;
printf("in %s all=%d\n", __func__,all);
all += 9;
printf("agn in %s all=%d\n", __func__,all);
return all;
}
// in f all=1
// agn in f all=10
// in f all=10
// agn in f all=19

注意事项

  1. 静态本地变量实际上是特殊的全局变量
  2. 它们位于相同的内存区域
  3. 静态本地变量具有全局的生存期,函数内的局部作用域
  4. static在这里的意思就是局部作用域(本地可以访问)

五、后记:返回指针的函数

  1. 返回本地变量的地址是危险的
  2. 返回全局变量或静态本地变量的地址是安全的
  3. 返回在函数内malloc的内存是安全的,但是容易造成问题
  4. 最好的做法是返回传入的指针

下面的写法就是很危险的

#include <stdio.h>

int* f(void);
void g(void); int main(int argc, char const *argv[])
{
int *p = f();
printf("*p = %d\n", *p);
g();
printf("*p = %d\n", *p); return 0;
} int* f(void)
{
int i = 12; // 返回本地变量的地址是危险的
return &i;
} void g(void)
{
int k = 24;
printf("k = %d\n", k);
} // *p = 12
// k = 24
// *p = 24

tips

  1. 不要使用全局变量来在函数间传递参数和结果
  2. 尽量避免使用全局变量
  3. 使用全局变量和静态本地变量的函数是线程不安全的

C语言入门-全局变量的更多相关文章

  1. 《Ruby语言入门教程v1.0》学习笔记-01

    <Ruby语言入门教程v1.0> 编著:张开川 邮箱:kaichuan_zhang@126.com 想要学习ruby是因为公司的自动化测试使用到了ruby语言,但是公司关于ruby只给了一 ...

  2. c语言入门这一篇就够了-学习笔记(一万字)

    内容来自慕课网,个人学习笔记.加上了mtianyan标签标记知识点. C语言入门 -> Linux C语言编程基本原理与实践 -> Linux C语言指针与内存 -> Linux C ...

  3. Go 语言入门(一)基础语法

    写在前面 在学习 Go 语言之前,我自己是有一定的 Java 和 C++ 基础的,这篇文章主要是基于A tour of Go编写的,主要是希望记录一下自己的学习历程,加深自己的理解 Go 语言入门(一 ...

  4. 【Introduction】R语言入门关键小结

    写在前面:本博客为本人原创,严禁任何形式的转载!本博客只允许放在博客园(.cnblogs.com),如果您在其他网站看到这篇博文,请通过下面这个唯一的合法链接转到原文! 本博客全网唯一合法URL:ht ...

  5. C语言入门基础整理

    学习计算机技术,C语言可以说是必备的,他已经成为现在计算机行业人学习必备的,而且应用也是十分的广泛,今天就来看看拥有几年c语言工作经验的大神整理的C语言入门基础知识,没有学不会,只有不肯学. 结构化程 ...

  6. C/C++编程笔记:C语言入门知识点(三),请收藏C语言最全笔记!

    今天我们继续来学习C语言的入门知识点,第一课:C/C++编程笔记:C语言入门知识点(二),请收藏C语言最全笔记! 21. 输入 & 输出 当我们提到输入时,这意味着要向程序填充一些数据.输入可 ...

  7. 《JavaScript语言入门教程》记录整理:运算符、语法和标准库

    目录 运算符 算数运算符 比较运算符 布尔运算符 二进制位运算符 void和逗号运算符 运算顺序 语法 数据类型的转换 错误处理机制 编程风格 console对象和控制台 标准库 Object对象 属 ...

  8. 《JavaScript语言入门教程》记录整理:面向对象

    目录 面向对象编程 实例对象与 new 命令 this关键字 对象的继承 Object对象的方法 严格模式(strict mode) 本系列基于阮一峰老师的<JavaScrip语言入门教程> ...

  9. 踢爆IT劣书出版黑幕——由清华大学出版社之《C语言入门很简单》想到的(1)

    1.前言与作者 首先声明,我是由于非常偶然的机会获得<C语言入门很简单>这本书的,绝对不是买的.买这种书实在丢不起那人. 去年这书刚出版时,在CU论坛举行试读推广,我当时随口说了几句(没说 ...

随机推荐

  1. nbuoj 2080 洛谷p1025 数的划分

    链接:http://www.nbuoj.com/v8.83/Problems/Problem.php?pid=2820 链接:https://www.luogu.org/problem/P1025 题 ...

  2. 如何手动实现TryInsert和InsertOrUpdate

    在日常开发中,我们有时会需要对数据的插入操作进行定制.比如,如果表里已有某某记录就不写入新纪录,或者表里没该记录就插入,否则就更新.前者我们称为TryInsert,后者为InsertOrUpdate( ...

  3. css3(2)

    旋转: 2D:transform: rotate()——进行旋转,括号内部写旋转角度,默认顺时针旋转.允许负值,元素将进行逆时针旋转, translate()——从当前位置进行移动,括号内为x,y值. ...

  4. wxxcx_learn订单

    自动写入时间戳 protected $autoWriteTimestamp = true: 事务的使用 Db::startTrans();....... Db::commit();.. Db::rol ...

  5. 面试必问:JVM类加载机制详细解析

    前言 在Java面试中,简历上有写JVM(Java虚拟机)相关的东西,JVM的类加载机制基本是面试必问的知识点. 类的加载和卸载 JVM是虚拟机的一种,它的指令集语言是字节码,字节码构成的文件是cla ...

  6. Mybatis sql map 小于号配置

    Mybatis SQL map配置中出现小于号转义时,通过<![CDATA[查询条件]]>解决. EXCEMPLE: <select id="getComments&quo ...

  7. js重学

    js重学 数据类型 基本数据类型: Undefined.Null.Number.Boolean.String 复杂数据类型:Object Object:由一组无序键值对组成 typeof 未定义--u ...

  8. poj 1741 Tree (树的分治)

    Tree Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 30928   Accepted: 10351 Descriptio ...

  9. Python Weekly 422

    新闻 Python 采用12个月作为发布周期 链接: https://mail.python.org/archives/list/python-dev@python.org/thread/KE7OS4 ...

  10. 面试连环炮系列(二十三): StringBuffer与StringBuild的区别

    StringBuffer与StringBuild的区别 频繁修改字符串时,建议使用StringBuffer和StringBuilder类.StringBuilder相较于StringBuffer有速度 ...