C notebook

C语言基础

ubuntu编译C与C++文件环境配置

sudo apt install gcc
sudo apt install g++

验证环境

cd /usr/bin
ls gcc*
ls g++*

通过gcc编译C文件

gcc [address/]filename.c [-o [address/]file]
ubuntu -> a.out [file]
windows -> a.exe [file.exe]

分步编译过程

//预处理:宏定义展开、头文件展开、条件编译等,删除注释,不检查语法
gcc -E filename.c -o file.i 
//编译:检查语法,生成汇编代码文件
gcc -S filename.i -o file.s 
//汇编:生成二进制文件(目标文件)
gcc -c filename.s -o file.o 
//链接:链接动态库(.DLL),生成可执行文件
gcc    filename.o -o file 
.c //C文件
.i //预处理后的C文件
.s //编译后的汇编文件
.o //汇编过后的二进制文件

运行编译后的文件

ubuntu -> [address/] ./(add now)filename
windows -> [address/] filename

C标准框架

//使用库函数包含相应的头文件
#include <stdio.h> 

//行注释:// ...
//块注释:/* ... */

//C代码由函数组成,有且只有一个主函数main()
//程序自动调用mian()开始运行
int main() 
{
    //mian()语句体
    printf("Hello world\n"); 
    //返回值,返回0表示程序正常结束
    return 0; 
}

system函数启动外部程序或命令

#include <stdio.h>
#include <stdlib.h>

int main()
{
    printf("before system");
    //ubuntu显示程序所在目录文件
    system("ls -alh");
    //ubuntu调用外部程序
    system("[address/] ./(add now)filename")
    //windows调用计算器
    system("calc");
    //windows调用外部程序
    system("[address/] filename")
    printf("after system");
    return 0;
}

操作系统编码

ubuntu -> uft-8(unicode)
windows -> gbk, gb2312, ANSI

数据类型

编译器预算变量(对象)分配的内存空间大小
C notebook

关键字

C关键字共有32个

  • 数据类型关键字(12个)

    char, short, int, long, float, double,

    unsigned, signed

    struct, union, enum,

    void

  • 控制语句关键字(12个)

    if, else, switch, case, default,

    for, do, while, break, continue, goto, return

  • 存储类关键字(5个)

    auto, extern, register, static, const

  • 其他(3个)

    sizeof, typedef, volatile

常量与变量

  • 常量:在程序运行过程中,其值不会改变

  • 变量:在程序运行过程中,其值可以改变

    1. 在使用前必须先定义,必须指定其数据类型

    2. 标识符命名规则

      • 标识符不能为保留关键字
      • 标识符由字母、数字、下划线组成
      • 只能以字母或下划线开头
      • 标识符区别大小写
    3. 变量初始化:定义的同时赋初值

    4. 变量特点

      • 变量在编译时分配相应的内存空间
      • 可以通过其变量名或者地址访问相应的内存空间
    5. 声明和定义的区别

      • 声明变量不需要建立存储空间,eg:extern int a;

      • 定义变量需要建立存储空间,eg:int a;

        #include <stdio.h>
        
        int mian()
        {
            //extern 只做声明,不能做任何定义
            //声明变量a,没有建立存储空间
            extern int a;
            a = 10; //error:undefined reference to `a',没有空间无法赋值
            //const修饰一个变量为只读,相当于常量
            const int b = 10;
            b  =20; //error: assignment of read-only variable ‘b’
            int c = b; //ok
            return 0;
        }
        
  • eg:

    #include <stdio.h>
    #define PI 3.14
    
    int main()
    {
        float r, s;
        printf("Please input r:");
     	scanf("%f", &r);
        s = PI*r*r;
        printf("this square is %.2f\n", s);
        return 0;
    }
    

进制

  • 右边是低位,左边是高位

    进制(逢x进1,接1当x) 表示
    二进制 0, 1
    十进制 0, 1, 2, 3, 4 ,5, 6, 7
    八进制 0, 1, 2, 3, 4, 5, 6, 7, 8, 9
    十六进制 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F
  • 8421法
    1111=231+221+211+201=81+41+21+11=15=F 1 1 1 1 = 2^3*1 + 2^2*1 + 2^1*1 + 2^0*1 =8*1 + 4*1 + 2*1 + 1*1 =15 =F

  • 进制转换

    • 1位八进制数 = 3位二进制数
    • 1位十六进制数 = 4位二进制数
    • 八进制转十六进制,先转换为二进制数
  • C语言中进制表示

    进制 表示
    二进制 C语言不能直接写二进制数
    八进制 以数字0开头,0~7
    十进制 以数字1-9开头,0~9
    十六进制 以0x / 0X开头,09和AF
  • eg:

    #include <stdio.h>
    
    int main()
    {
        int a, b, c;
        a = 123;
        b = 0123;
        c = 0x123;
        printf("[10]%d\n[8]%o\n[16]%x\n", a, b, c);
        return 0;
    }
    

原反补码

  • 数据在计算机中主要以补码形式存储
术语 含义
bit(比特,位) 一个二进制数(0/1)表示一位,数据传输以“位”为单位
Byte(字节) 一个字节为8个二进制数(8位),计算机中存储最小单位位字节,数据存储习惯以“字节”为单位
WORD(双字节,字) 2个字节,16位
DWORD 两个WORD,4个字节,32位
1 b 1 bit,1位
1 B 1 Byte,1字节,8位
1 k,1 K 1024
1 M(1兆) 1024 k,1024*1024
1 G 1024 M
1 T 1024 G
1 Kb(千位) 1024 bit,1024位
1 KB(千字节) 1024 Byte,1024字节
1 Mb(兆位) 1024 Kb = 1024*1024 bit
1 MB(兆字节) 1024 KB = 1024*1024 Byte
  • 存储1字节(8位)大小的数字(char)

    • 原码(用户角度):原始的二进制
      • 用户的数字分正负数,利用符号位
      • 最高位(左起第一位)为符号数:0代表正数,1代表负数
      • 导致的问题
        1. 0有两种存储方式
        2. 正数和负数相加,结果不正确(计算机只会加法运算)
    • 反码(为了算补码)
      • 规定:正数的原码和反码一致,负数符号位不变,其他位取反(01互换)
      • 导致的问题
        1. 0有两种存储方式
    • 补码(为了存储负数)
      • 规定:正数的原码、反码和补码一致,负数为其补码+1
      • 解决的问题
        1. 统一0的存储编码
        2. 符号位和其他位统一处理
        3. 减法运算转变为加法运算
        4. 两个用补码表示的数相加,最高位(符号位)有进位则被舍去
    • 补码求原码:
      • 正数补码等于其原码
      • 负数符号位不变,其他按位取反,结果+1
  • eg:

    数字 原码 反码 补码
    + 1 0 000 0001 0 000 0001 0 000 0001
    - 1 1 000 0001 1 111 1110 1 111 1111
    + 0 0 000 0000 0 000 0000 0 000 0000
    - 0 1 000 0000 1 111 1111 1 0 000 0000(最高位丢弃)
    1 - 1 = 1 + -1 1 000 0010 = -2 1 111 1111 = -0 1 0 000 0000 = -0 = 0

有符号和无符号的区别

  • 有符号数,最高位是符号位,1代表负数,0代表整数

  • 无符号数,最高位不是符号位,是数的一部分,不包含负数

  • -0当作2^x使用(最高位舍去)

    数据类型 占用空间 取值范围
    char 1字节 -128127(-2^72^7-1)
    short 2字节 -3276832767(-2^152^15-1)
    int 4字节 -21474836482147483647(-2^312^31-1)
    long 4字节 -21474836482147483647(-2^312^31-1)
    unsigned char 1字节 0255(02^8-1)
    unsigned short 2字节 065535(02^16-1)
    unsigned int 4字节 04294967295(02^32-1)
    unsigned long 4字节 04294967295(02^32-1)
  • eg:

    #include <stdio.h>
    
    int main()
    {
    	char a = 0xff; //[signed] char
        unsigned char b = 0xff;
        //原:1 111 1111 反:1 000 0000 补:1 000 0001
        printf("signed char:%d\n", a); //-1
        //原:1 111 1111 反:1 111 1111 补:1 111 1111
        printf("unsigned char:%u\n", b); //255,输出结果以格式控制符为准
        return 0;
    }