`
kuwoleft
  • 浏览: 1072511 次
文章分类
社区版块
存档分类
最新评论

DS计划C深入项目学习总结——变量的作用域

 
阅读更多

1.1 变量作用域

1.1.1 几种常见类型变量的作用域

作用域(scope)或者可见性是指变量在程序内的可见和可引用的范围。

比如:

1、 全局变量在所有的文件都可见,那他的作用域就是所有文件;

2、 static定义的全局变量,只在定义它的源文件中可见,那他的作用域就是其所在的源文件;

3、 函数内部的局部变量,只在其函数范围内可见;

4、 有些变量,只在某一块代码段内可见(花括号括起来的一段代码);

void test_fun()

{

int test_i = 0;

test_i = 10;

if (test_i != 0)

{

int test_count = 15;

test_i = test_count;

}

test_i = test_count;//这里会编译出错,因为test_count只在if条件的花括号中有效。

}

1.1.2 变量使用的高级话题

下面大部分内容来自《代码大全》。

1.1.2.1 使变量引用局部化

《代码大全》这本书介绍了攻击窗口的概念:介于同一个变量多个引用点之间的代码可成为攻击窗口,在这个窗口中新增代码,可能会不当的修改此变量。

一般而言,把对一个变量的引用局部化,即把引用点尽可能集中在一起总是一种很好的做法。主要的好处是提高程序的可读性和可维护性。如果变量的引用点都很集中,则阅读代码的时候,只要关注这一块代码就可以了,否则,阅读者的目光需要在代码中跳来跳去。

如何衡量变量引用的集中程度?《代码大全》提到了变量跨度的概念:对变量所有引用间相隔的代码行数。

void test_fun()

{

int test_i = 0;

int test_j = 0;

test_i = 10;//和第一次引用间隔1行代码

if (test_i != 0)//和第二次引用间隔0行代码

{

int test_count = 15;

test_i = test_count;//和第三次引用间隔1行代码

}

}

test_i的跨度总共是2。test_i的平均跨度是2/3。

1.1.2.2 缩短变量的存活时间

变量的存活时间—— 一个变量存在期间所跨越的语句总数。也就是从第一次引用,到最后一次引用之间跨越代码的行数。

跨度表明变量引用的集中程度,存活时间表明变量经历的语句。

如上图所示,test_i存活时间是6条语句。

低存活时间的好处:

1、减小攻击窗口,不易出错。

2、使你对代码有更准确的认识(提高可读性)

3、减少初始化错误。

最后,一个明显的好处是便于程序重构,如果一个程序拆分为多个小的程序,短的存活时间更有价值。

用跨度和生存时间来考察全局变量,会发现全局变量跨度和生存时间都很长——这是避免使用全局变量的好的理由之一。

1.1.2.3 减小作用域的一般原则

1、在循环开始之前再去初始化改循环里使用的循环变量,而不是在该循环所属的子程序的开始处初始化这些变量。

2、直到变量即将被使用时再为其赋值。把声明和定义放在使用之前。

3、把相关语句放在一起。减少变量的跨度和生存时间。

4、把相关的语句组提取成功单独的子程序。把一个长的子程序拆分为更小的、单独的子程序可以缩小变量的作用域。

5、开始时使用最严格的可见性,然后根据需要扩展变量的作用域。当对变量作用域犹豫不决时,应该倾向于选择该变量所能具有的最小的作用域:首先将变量限制于某个特定的循环,然后是局限于某个子程序,其次是类的private变量,protected变量,再其次对包()可见,最后不得已的情况下再把它作为全局变量。

关于对变量作用域的态度,取决于程序员如何看待“方便性”和“智力上的可管理性”。作用域越大,在写代码时越方便。但是写出的程序更难于理解、阅读、调试和维护。

1.1.3 结论

1、 全局变量在所有的文件都可见,那他的作用域就是所有文件。

2、 static定义的全局变量,只在定义它的源文件中可见,那他的作用域就是其所在的源文件。

3、 函数内部的局部变量,只在其函数范围内可见。

4、 有些变量,只在某一块代码段内可见(花括号括起来的一段代码)。

5、 尽量使变量的引用局部化。

6、 尽量缩短变量的存活时间。

7、 尽量减少变量的作用域。

1.1.4 扩展阅读

《代码大全》第10章《使用变量的一般事项》会教你如何更好的使用变量。

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics