我所忽略的c 语言标准

1.表达式中有无符号数和有符号数混用的时候

 

先看一个例子:

int main(void)

{

unsigned int a = 6;

int                 b = -20

return (a+b) > 0 ? 1 : 0;

 

}

 

echo $ 的结果是 1。

首先这两个数在内存中都是以补码形式存储的,

 

以上面的例子分别为0xffffffec  , 0x6。相加后的值也很明显等于fffffff2

可以看一下gcc中反汇编:

 

 

但是关键对a+b这个add操作后,编译器对结果的解释 ,在这里很不幸,被解释成unsigned int。因为在c语言中,当有符号数

和无符号数在同一个表达式的时候,有符号数被解释成无符号数。而且a+b > 0这个操作(当然0是无符号的(默认))。

所以这种写法很不好的。最好避免有同一个表达式中同时出现有符号数和无符号数。

表达式求值:

 

隐式类型转换

c的整型算术运算总是至少以整型类型的精度来进行的。为了获得这个精度,表达式中的字符型和短整型操作数在使用之前被转换为普通整型,这种转换称为“整型提升”。

 

算术转换

当两个操作数属于不同的类型,那么除非其中一个操作数转换为另外一个操作数的类型,否则操作无法进行。

下面的层次体系----称为寻常算术转换

long double 

double

float 

unsigned long int

long int

unsigned int

int

如果操作数的类型在上面这个列表中排名较低,那么它首先将转换为另外一个操作数的类型然后执行操作。(自己的理解,排名是根据类型表示的数据的个数(范围的大小)来决定的。

 

 

 

2.标准c的标记化初始化语法

 

在linux设备驱动程序看到的一种标准:
 struct file_operations scull_fops ={

.owner = THIS_MODULE,

.llseek  =  scull_read,

.write   = scull_write,

.ioctl    = scull_ioctl,

.open   =  scull_open,

.release = scull_release

};

 

这种写法是很值得采用的,因为它使驱动程序在结构的定义发生变化时更具可移植性,并且使得代码更加紧凑且易读。而且标记化的初始化方法允许对结构成员进行重新排列。

当然是Iso c99的标准。

比起传统的初始化办法:scull_fops= {THIS_MODULE, scull_read, scull_write, scull_iotcl, scull_open, scull_release};有很明显的好处。

 

3-14日

 

sig_atomic_t类型,由 iso c标准定义的变量类型,在写这种类型的变量时,不会被中断(不会有缺页中断发生)。它意味着在具有虚拟存储器的系统上这种变量不会跨越页边界,可以用一条机器指令对其进行访问。

而且在使用的时候,前面加上volatile

 

如 volatile sig_atomic_t quitflag;

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值