第5章 常量--变量C++/C 编程指南,v 1.0

news/2024/7/3 13:20:40 标签: c++, 编程, 语言, 编译器, class, float
class="baidu_pl">
class="article_content clearfix">
class="htmledit_views">
第5章常量
    常量是一种标识符,它的值在运行期间恒定不变。 Cclass="tags" href="/tags/YuYan.html" title=语言>语言用 #define来定义常量(称为宏常量)。C++ class="tags" href="/tags/YuYan.html" title=语言>语言除了 #define外还可以用const来定义常量(称为const常量)。
5.1为什么需要常量
如果不使用常量,直接在程序中填写数字或字符串,将会有什么麻烦?
(1)       程序的可读性(可理解性)变差。程序员自己会忘记那些数字或字符串是什么意思,用户则更加不知它们从何处来、表示什么。
(2)       在程序的很多地方输入同样的数字或字符串,难保不发生书写错误。
(3)       如果要修改数字或字符串,则会在很多地方改动,既麻烦又容易出错。
 
l         【规则5-1-1】 尽量使用含义直观的常量来表示那些将在程序中多次出现的数字或字符串。
例如:
    #define         MAX   100       /*  Cclass="tags" href="/tags/YuYan.html" title=语言>语言的宏常量   */
const int       MAX = 100;      //  C++ class="tags" href="/tags/YuYan.html" title=语言>语言的 const常量
const float     PI = 3.14159;   //  C++ class="tags" href="/tags/YuYan.html" title=语言>语言的 const常量
5.2 const与 #define的比较
    C++ class="tags" href="/tags/YuYan.html" title=语言>语言可以用 const来定义常量,也可以用 #define来定义常量。但是前者比后者有更多的优点:
(1)       const常量有数据类型,而宏常量没有数据类型。class="tags" href="/tags/BianYiQi.html" title=编译器>编译器可以对前者进行类型安全检查。而对后者只进行字符替换,没有类型安全检查,并且在字符替换可能会产生意料不到的错误(边际效应)。
(2)       有些集成化的调试工具可以对 const常量进行调试,但是不能对宏常量进行调试。
 
l         【规则5-2-1】在 C++ 程序中只使用const常量而不使用宏常量,即const常量完全取代宏常量。
5.3常量定义规则
l         【规则5-3-1】需要对外公开的常量放在头文件中,不需要对外公开的常量放在定义文件的头部。为便于管理,可以把不同模块的常量集中存放在一个公共的头文件中。
l         【规则5-3-2】如果某一常量与其它常量密切相关,应在定义中包含这种关系,而不应给出一些孤立的值。
例如:
const float    RADIUS = 100;
const float    DIAMETER = RADIUS * 2;
5.4类中的常量
有时我们希望某些常量只在类中有效。由于 #define定义的宏常量是全局的,不能达到目的,于是想当然地觉得应该用const修饰数据成员来实现。const数据成员的确是存在的,但其含义却不是我们所期望的。const数据成员只在某个对象生存期内是常量,而对于整个类而言却是可变的,因为类可以创建多个对象,不同的对象其const数据成员的值可以不同。
    不能在类声明中初始化 const数据成员。以下用法是错误的,因为类的对象未被创建时,class="tags" href="/tags/BianYiQi.html" title=编译器>编译器不知道SIZE的值是什么。
    class A
    {…
        const int SIZE = 100;  // 错误,企图在类声明中初始化 const数据成员
        int array[SIZE];        // 错误,未知的 SIZE
    };
 
const数据成员的初始化只能在类构造函数的初始化表中进行,例如
    class A
    {…
        A(int size);        // 构造函数
        const int SIZE ;   
    };
    A::A(int size) : SIZE(size) // 构造函数的初始化表
    {
     …
    }
    A a(100); // 对象 a 的SIZE值为100
    A b(200); // 对象 b 的SIZE值为200
 
    怎样才能建立在整个类中都恒定的常量呢?别指望 const数据成员了,应该用类中的枚举常量来实现。例如
    class A
    {…
        enum { SIZE1 = 100, SIZE2 = 200}; // 枚举常量
        int array1[SIZE1]; 
        int array2[SIZE2];
    };
    枚举常量不会占用对象的存储空间,它们在编译时被全部求值。枚举常量的缺点是:它的隐含数据类型是整数,其最大值有限,且不能表示浮点数(如 PI=3.14159)。
来源:http://www.eefocus.com/andysun001/blog/10-06/192028_29dc5.html#articletop

http://www.niftyadmin.cn/n/1736433.html

相关文章

链表之循环链表、双向链表

一、循环链表 循环链表是与单链表一样,是一种链式的存储结构,所不同的是,循环链表的最后一个结点的指针是指向该循环链表的第一个结点或者表头结点,从而构成一个环形的链。 循环链表的运算与单链表的运算基本一致。所不同的有以下…

C语言宏定义使用技巧

C语言宏定义使用技巧 写好C语言,漂亮的宏定义很重要,使用宏定义可以防止出错,提高可移植性,可读性,方便性 等等。下面列举一些成熟软件中常用得宏定义……1,防止一个头文件被重复包含 #ifndef COMDEF_H #de…

经典c 教程(ch7 指针和内存分配---下)

7.15 数组的大小可以在程序运行时定义吗? 不。在数组的定义中,数组的大小必须是编译时可知的,不能是在程序运行时才可知的。例如,假设i是一个变量,你就不能用i去定义一个数组的大小: char arr…

彻底了解指针数组,数组指针,以及函数指针,以及堆中的分配规则

指针数组和数组指针 下面就简单说说这两个概念: 一:指针数组,顾名思义,就是说的首先是一个数组吧,然后数组的元素是指针而已。 说明形式为:type *pointer_array[constant1][constant2]...[constantn]; 例如…

linux板级设备的初始化过程

start_kernel() -> setup_arch(&command_line) -> mdesc setup_machine(machine_arch_type) -> list lookup_machine_type(nr) -> return struct machine_desc. 内核在启动的时候就是最先运行start_kernel() , 然后她就会调用体系结构相关的setup_arch(&…

第一讲:2410的初始化流程(设备初始化)

第一讲:2410的初始化流程(设备初始化)1 在mach-smdk2410.c中先通过MACHINE_START()定义了machine_desc的变量,其中注册了smdk2410_map_io(), s3c2410_init_irq(), smdk2410_init()这3个回调函数. 这3个回调函数会在系统起来的时候setup_arch(…

Lcd帧缓冲设备

帧缓冲(framebuffer)是Linux为显示设备提供的一个接口,是把显存抽象后的一种设备,它允许上层应用程序在图形模式下直接对显示缓冲区进行读写操作,这种操作是抽象的,统一的。用户不必关心物理显存的位置,换页机制等等具…

Frame Buffer

Linux的帧缓冲(Frame Buffer)之一:原理及控制参数 大家都知道Unix/Linux系统是由命令驱动的。X-Window-System是Unix/Linux上的图形系统,它是通过X-Server来控制硬件的。但有一些Linux的发行版在…