1.即使本程序中虽然不改变这种类型的值,但别的比如中断程序可能会改变这个值,加上volatile,编译器不优化,每次都重新访问这个值做判断

2.如

unsigned char flag = 1;

int main(int argc, char **argv) {
    reg_intr(XXX, intr_func);
    while(flag) {
        printf("hello\n");
    }
    return 0;
}

void intr_func(void)//中断函数

{
    flag = 0;
}

3.“const”含义是“请做为常量使用”,而并非“放心吧,那肯定是个常量”。
“volatile”的含义是“请不要做没谱的优化,这个值可能变掉的”,而并非“你可以修改这个值”。

4.这个人说的一看就懂

另外一个例子在嵌入式系统中比较常见。很多嵌入式系统允许我们访问外部寄存器,该寄存器的地址可能是0x0018,该寄存器的最低位可能表示设备状态,1为忙碌,0为空闲。

C/C++ code
#define GET_REG_VALUE(reg)              (*reg)       /* get register value */
const unsigned char *STATUS_REG   = 0x0018;    /* status register */
const unsigned char  STATUS_BUSY = 0x01;        /* busy bit */
while (GET_REG_VALUE(STATUS_REG) & STATUS_BUSY); /* wait until free */
// do something to operate the device
...
 

这段代码很可能会死循环。因为编译器强奸民意的将地址0x0018处的值缓存起来,然后每次while的时候都从缓存中读取。虽然STATUS_REG的值是const unsigned char *,但这仅仅表示STATUS_REG寄存器是个只读寄存器,我们不能够在代码中去写这个寄存器,但并不表示这个寄存器是不能够改变的。硬件完成了它的任务之后,就会把状态设置成空闲,因此该寄存器的最后一位在我们循环的时候很可能已经发生了变化。因此在这样的地方,我们要禁止编译器自作聪明的优化,方法如下:

C/C++ code

 const volatile unsigned char *STATUS_REG   = 0x0018;    /* status register */

5.

只读表示编译器不允许代码修改变量。但并不表示这个变量在其它地方不能够被修改(不能被修改岂不就成了常量?)。比如:

C/C++ code

 

?

1
2
3
4
void f(const char *str)
{
...
}

在上面的程序中,str所指向的内存区域就是只读的,但这个只读性只在函数f内部,出了f,这块内存完全有可能是能够被修改的。

 
 
C/C++ code

 

?

1
2
3
4
5
6
void g(void)
{
    char name[] = "Jim King";
    f(name);
...
}

volatile举列说明const的更多相关文章

  1. C语言中volatile、register、const、static、extern、 auto关键字的作用

    一.volatile详解 volatile的本意是"易变的" 因为访问寄存器要比访问内存单元快的多,所以编译器一般都会作减少存取内存的优化,但有可能会读脏数据.当要求使用volat ...

  2. C++的类型转换:static_cast、dynamic_cast、reinterpret_cast和const_cast(dynamic_cast还支持交叉转换,const_cast将一个类的const、volatile以及__unaligned属性去掉)

    在C++中,存在类型转换,通常意味着存在缺陷(并非绝对).所以,对于类型转换,有如下几个原则:(1)尽量避免类型转换,包括隐式的类型转换(2)如果需要类型转换,尽量使用显式的类型转换,在编译期间转换( ...

  3. c++中的const和volatile知识自我总结

    学习了下c++中的const关键字,总结如下. 1.const限制一个变量不能修改其内容,如果强行修改的话,如下面代码这样子,编译就会报错,“表达式必须是可修改的左值”. int main() { c ...

  4. 多线程中volatile关键字的作用

    原文链接:https://blog.csdn.net/xuwentao37x/article/details/27804169 多线程的程序是出了名的难编写.难验证.难调试.难维护,这通常是件苦差事. ...

  5. C++中const的全面总结

    C++中的const关键字的用法非常灵活,而使用const将大大改善程序的健壮性,本人根据各方面查到的资料进行总结如下,期望对朋友们有所帮助. Const 是C++中常用的类型修饰符,常类型是指使用类 ...

  6. volatile关键字及编译器指令乱序总结

    本文简单介绍volatile关键字的使用,进而引出编译期间内存乱序的问题,并介绍了有效防止编译器内存乱序所带来的问题的解决方法,文中简单提了下CPU指令乱序的现象,但并没有深入讨论. 以下是我搭建的博 ...

  7. C++ const

    在程序中经常遇到const,但是对他还不是非常了解,今天看到一篇文章讲挺好的,所以复制过来了.... 原文链接:http://blog.csdn.net/Eric_Jo/article/details ...

  8. 提交form表单不刷新页面案列

    提交form表单不刷新页面其实很简单的,这里拿上传图片来举列,大家有什么其它的方法也欢迎留言告知与我 <form action="" method="post&qu ...

  9. const in C++

    const关键字是C++中常用的类型修饰符,用法非常灵活,使用const将大大改善程序的健壮性. const的作用 1.  定义const常量: 比如: const int Max = 100; 2. ...

随机推荐

  1. Windows server 2012 各版本 激活方法

    Windows server 2012 激活教程 本文包括以下两种版本的激活过程:(注意RC版的是不能激活的!) 1.Windows server 2012 试用版本激活 2.Windows serv ...

  2. MySQL flush tables with read lock

    mysql> flush tables with read lock; flush tables with read lock 会去关闭已经打开的所有文件,它要做这个操作就先要拿到锁:当发起这个 ...

  3. UI控件自定义tableView的分割线的样式

    - (void)drawRect:(CGRect)rect { CGContextRef context = UIGraphicsGetCurrentContext(); CGContextSetFi ...

  4. zlog使用手册,小靠谱啊

    http://hardysimpson.github.io/zlog/UsersGuide-CN.html Chapter 1 zlog是什么? zlog是一个高可靠性.高性能.线程安全.灵活.概念清 ...

  5. hadoop集群的故障概率估算

    hadoop集群的机器数业界(国内)最大的在5000左右,是什么限制了集群的规模呢?有好几个原因. 1. namenode的内存大小限制 2. 机器故障概率随着机器数目增大而增大,通常一份数据存储在h ...

  6. Codeforces 538E Demiurges Play Again(博弈DP)

    http://codeforces.com/problemset/problem/538/E 题目大意: 给出一棵树,叶子节点上都有一个值,从1-m.有两个人交替从根选择道路,先手希望到达的叶子节点尽 ...

  7. JVM基础和调优(六)

    JVM设置过程中的一般的规范 在JVM的设置中,年轻代的设置比较的重要,因为年轻代存储空间分配的比较的块,可以说触发GC的机会比较的大. 默认的情况下:-XX:NewRatio  默认为2 说明:年轻 ...

  8. debug openStack

    ERROR neutron.agent.l3.agent [-] An interface driver must be specified No valid host was found. Ther ...

  9. (poj 1475) Pushing Boxes

    Imagine you are standing inside a two-dimensional maze composed of square cells which may or may not ...

  10. PHP数据结构:栈、队列、堆、固定数组

    数据结构:栈 队列: 堆: 固定尺寸的数组: