首页 > 编程学习 > C 语言-8 简单进阶

C 语言-8 简单进阶

发布时间:2022/8/22 13:20:45

8.1 枚举类型

  • 在实际问题中,有些变量的取值被限定在一个有限的范围内。例如,一个星期内只有七天,一年只有十二个月。为此,C语言提供了一种称为“枚举”的类型。枚举类型比整型或者字符型更为准确、合适

  • 在“枚举”类型 的定义中列举出所有可能的取值,被说明为该“枚举”类型的变量取值不能超过定义的范围

    • 即凡被说明为枚举类型,变量的取值只能是范围中的某值
  • 枚举类型是一种基本数据类型,而不是一种构造类型,因为它不能再分解为任何基本类型

  • 定义:

    • 一般形式:

      enum 枚举名{枚举值表};
      

      枚举值表中罗列出所有可用值。这些值也称为枚举元素

  • 说明:

    1. 先定义,后说明

      enum weekday{ sun,mou,tue,wed,thu,fri,sat };
      enum weekday a,b,c;
      
    2. 同时定义说明

      enum weekday{ sun,mou,tue,wed,thu,fri,sat }a,b,c;
      
    3. 直接说明

      enum { sun,mou,tue,wed,thu,fri,sat }a,b,c;
      
  • 赋值:

    • 枚举类型是常量,不能再使用赋值语句中赋值

    • 枚举元素本身由系统定义了一个序号的数值,从 0 开始顺序为 0,1,2,……

    • 只能把枚举值赋予枚举变量,不能把元素的数值直接赋予枚举变量

      • 示例:

        enum weekday
        { sun,mon,tue,wed,thu,fri,sat } a,b,c;
        a=sun;
        b=mon;
        
      • 如一定要把数值赋予枚举变量,则必须用强制类型转换

        a=(enum weekday)2;
        

        意义是将顺序号为 2 的枚举元素赋予枚举变量 a

    • 枚举元素不是字符常量也不是字符串常量,使用时不要加单、双引号

8.2 类型定义符 typedef

  • C语言不仅提供了丰富的数据类型,而且还允许由用户自己定义类型说明符,允许由用户为数据类型取“别名”

  • 使用类型定义符 typedef 即可用来完成此功能

    • 一般定义形式:

      typedef 原类型名 新类型名
      

      原类型名中含有定义部分

      新类型名一般用大写表示,以便于区别

  • 例如:有整型变量 a,b,说明为 int a,b;,可把整型说明符用 typedef 定义为:typedef int INTEGER。这以后就可用 INTEGER 来代替 int 作整型变量的类型说明了:INTEGER a,b;

  • 意义:用 typedef 定义数组、指针、结构等类型带来很大的方便,不仅使程序书写简单而且使意义更为明确,因而增强了可读性

    typedef char NAME[20];
    NAME a1,a2,a3;		//等效为 char a1[20],a2[20],s1[20],s2[20]
    
    typedef struct stu
    { char name[20];
     int age;
     char sex;
    } STU;
    STU body1,body2;
    
  • 有时也可用宏定义来代替 typedef 的功能,后者更为灵活方便

    • 宏定义是由预处理完成的
    • typedef 则是在编译时完成的

8.3 位运算

  • 前面介绍的各种运算都是以字节作为最基本位进行的。但在很多系统程序中常要求在位(bit)级进行运算或处理

  • C语言提供了位运算的功能,这使得 C语言也能像汇编语言一样用来编写系统程序

  • 六种位运算符:

    运算符 说明 描述
    & 按位与 参与运算的两数各对应的二进位相与。只有对应的两个二进位均为 1 时,结果位才为 1,否则为 0。参与运算的数以补码方式出现
    | 按位或 参与运算的两数各对应的二进位相或。只要对应的二个二进位有一个为 1 时,结果位就为 1。参与运算的两个数均以补码出现
    ^ 按位异或 参与运算的两数各对应的二进位相异或,当两对应的二进位相异时,结果为 1。参与运算数仍以补码出现
    ~ 取反 对参与运算的数的各二进位按位求反
    << 左移 把“<<”左边的运算数的各二进位全部左移若干位,由“<<”右边的数指定移动的位数,高位丢弃,低位补 0
    >> 右移 把“>>”左边的运算数的各二进位全部右移若 干位,“>>”右边的数指定移动的位数
    对于有符号数,在右移时,符号位将随同移动。当为正数时,最高位补 0,而为负数时,符号位为 1,最高位是补 0 或是补 1 取决于编译系统的规定
    • 除了取反运算符是单目运算符外,其他均为双目运算符
  • 位域(位段)

    • 是指把一个字节中的二进位划分为几个不同的区域,并说明每个区域的位数。每个域有一个域名,允许在程序中按域名进行操作。这样就可以把几个不同的对象用一个字节的二进制位域来表示。例如在存放一个开关量时,只有 0 和 1 两种状态,用一位二进位即可

    • 定义:位域定义与结构定义相仿

      struct 位域结构名
      {位域列表};
      
      • 位域列表:

        类型说明符 位域名:域名长度
        
      • 示例:

        struct bs
        {
            int a:8;
            int b:2;
        }
        
    • 定义说明:

      1. 一个位域必须存储在同一个字节中,不能跨两个字节。如一个字节所剩空间不够存放另一位域时,应从下一单元起存放该位域。也可以有意使某位域从下一单元开始

        struct bs
        {
            unsigned a:4;
            unsigned :0; /*空域*/
            unsigned b:4; /*从下一单元开始存放*/
            unsigned c:4;
        }
        

        a 占第一字节的 4 位,后 4 位填 0 表示不使用,b 从第二字节 开始,占用 4 位,c 占用 4 位

      2. 位域不允许跨两个字节,因此位域的长度不能大于一个字节的长度,也就是说不能超过 8 位二进位

      3. 位域可以无位域名,这时它只用来作填充或调整位置。无名的位域是不能使用的

        struct k
        {
            int a:1;
            int :2; /*该 2 位不能使用*/
            int b:3;
            int c:2;
        };
        
    • 位域变量的说明与结构变量说明的方式相同,此处略

    • 使用:

      位域变量名·位域名
      
    • 位域在本质上就是一种结构类型,不过其成员是按二进位分配的。

    • 位域使得可在高级语言中实现数据的压缩,节省存储空间,同时也提高了程序的效率

Copyright © 2010-2022 mfbz.cn 版权所有 |关于我们| 联系方式|豫ICP备15888888号