C语言基础知识梳理

  • 零、概述
  • 一、变量和基本类型
    • (一)基本类型
      • 1、有符号常见类型大小及其范围
      • 2、浮点数范围来由及其有效数字
      • 3、字面值常量
        • (1)十进制字面值
        • (2)浮点数字面值
        • (3)指定字面值类型
      • 4、字符和字符串常量
      • 5、总结
    • (二)变量
      • 1、定义变量
      • 2、常用特殊前缀
      • 3、数组与初始化变量
      • 4、变量作用域
        • (1)局部变量与全局变量的差别
    • (三)字符串
    • (四) 自定类型——结构体
  • 二、表达式
  • 三、语句
    • (一)条件语句
      • 1、if语句
      • 2、switch语句
    • (二)迭代语句
      • 1、while语句
      • 2、do while语句
      • 3、for语句
    • (三)跳转语句
  • 四、函数
    • (一)函数一般格式
    • (二)函数声明
      • (三)结构体中的函数
  • 五、指针
    • (一)定义
    • (二)结构体与指针
    • (三)数组与指针
  • 六、文件读取
    • (一)文本文件
    • (二)二进制文件
  • 七、编译预处理指令与.h文件
    • (一)编译预处理指令
      • 1、# include < stdio.h >
      • 2、#define 名称 操作(宏定义)
      • 3、(补充)inline内联函数
    • (二).h文件
    • (三)一些常用宏
  • 八、常用函数
    • (一)常用函数
    • (二)scanf和printf


零、概述


写此篇博客的目的主要是为了梳理一下c语言基础知识,因为不会像c语言教程那样有很多例子,或者按照初学c语言的顺序,所以不推荐刚学习c语言的人阅读。(期末复习可以看看)

本篇文章有什么:

  1. 对c语言系统的梳理
  2. 对一些使用的细节进行梳理
  3. 解答对使用c语言时产生的一些疑惑
  4. 本篇内容基于“C语言程序设计-浙江大学-翁恺”、“C++ Primer”部分内容以及个人理解进行梳理,不充分之处欢迎指出


一、变量和基本类型


(一)基本类型

1、有符号常见类型大小及其范围

1byte(字节)=8bit(位);每个bit就是一个0或者1,byte是c语言里面数据的最小单位

常用2的次方:
27=128
28=256
215=32,768
216=65,536
231=2,147,483,648‬
232=4,294,967,296
263=9,223,372,036,854,775,808‬
264=18,446,744,073,709,551,616

类型 含义 32位编译器中大小(一般) 64位编译器中大小(一般) 最小值(32位) 最大值(32位)
bool(stdbool.h) 布尔类型 1byte 1byte false true
char 单个字符 1byte 1byte -27 27-1
short 短整形 2byte 2byte -215 215-1
int 整形 4byte 4byte -231 231-1
long 长整形 4byte 8byte -231 231-1
long long 长整形 8byte 8byte -263 263-1
float 单精度浮点数 4byte 4byte -2127 2128
double 双精度浮点数 8byte 8byte -21023 21024
long double 扩展精度浮点数 12byte 16byte -216383 216384
char* 字符常量或字符串常量 4byte 8byte 无意义 无意义

2、浮点数范围来由及其有效数字

这里单独讨论一下浮点数的取值范围,浮点数都遵循IEEE754标准,所以:
4*8=32位的float的第1位是符号位,第2~9位有8位是指数位,第10~32位有23位是尾数位

那么可以很容易看到float的范围是[-1*2127≈1.7*1038, 1*2128≈3.4*1038]

因为转换成IEEE754都要进行标准化,也就是将原来的整数点整数的形式转化成二进制点二进制的形式,然后将点的位置移动到左边第一个1(2)之后,产生指数位。规定点之后的数填在尾数位上,所以31位前暗含了1(2),所以上面的范围会先乘个1。
32位的指数位 = 移位数(左移一位+1,右移一位-1)+ 127得出。所以负数只有127(127-127=0),而正数有128(127+128=255)


8*8=64位的double的第1位是符号位,第2~12位有11位是指数位,第13~64位有52位是尾数位
那么可以很容易看到float的范围是[-1*21023≈8.988*10307, 1*21024≈1.797693*10308]

12*8=96或16*8=128位的long double的第1位是符号位,第2~16位有15位是指数位,在32位系统中第17~96位有80位是尾数位,在64位系统中第17~128位有112位是尾数位,那么范围是[-1*216383≈5.9*104931, 1*216384≈1.1897*104932](与尾数大小无关)。

其实float的范围就已经非常非常大了,那为什么还会有double甚至long double呢,这是因为浮点数能准确记录量级,但是无法准确记录太长的数字,数字的有效位数值取决于尾数位的长度,我们可以总结成下表:

类型 有效位数计算 有效位数
float 223+1=16,777,216 8-1=7
double 252+1=9,007,199,254,740,992‬ 16-1=15
long double 280+1=2.4*10 24 / 2112+1=1.038*1034 25-1=24 / 35-1=34

3、字面值常量

(1)十进制字面值

对于一个20(10)=24(8)=14(16),在c语言中对应表达为20(10进制)、024(8进制)、0x14(16进制)。
默认情况下,十进制字面值的类型是int,如果int装不下就是long,再装不下就是long long。

(2)浮点数字面值

对于一个浮点数可以表示为314.159(10)也可以表示为3.14159e+2(科学记数法)。
默认情况下,浮点数字面值是一个double

(3)指定字面值类型

整形字面值
后缀 最小匹配类型 例子
u / U unsigned 20u / 20U
l / L long 20l / 20L
ll / LL long long 20ll / 20LL
浮点形字面值
f / F float 20.0f / 20.0F
l / L long double 20.0l / 20.0L

4、字符和字符串常量

形如’a’、"HelloWorld"都可以看作是常量,特别说明当例如char* s1="HelloWorld";char* s2="HelloWorld";时,s1和s2所指的都是内存中代码段的常量,可读不可写且地址相同,类似于const char* s1;

字符是以单引号’括住的单个字符,只占一个char(一个byte)
字符串以双引号"括住一系列字符,最后隐含了’\0’,所以占n+1个char(n为字符串有意义的长度)

特殊的常量:无穷,每个编译器的表示都不一样,可以使用如下代码输出:

printf("%f\n", 1/0.0);  // 无穷大。我的电脑上为:1.#INF00
printf("%f\n", -1/0.0);  // 无穷小。我的电脑上为:1.#INF00
printf("%f\n", 0.0/0.0);  // 空。我的电脑上为:-1.#IND00

5、总结

有符号的类型(除浮点数)的范围都是由[-2n-1, 2n-1-1](n为类型所占bit)
无符号的类型(除浮点数)的范围都是由[0, 2n-1](n为类型所占bit)
浮点数的范围与其指数位大小有关,为[-2{[2^(m-1)]-1}, 2[2^(m-1)]](m为指数位位数)


(二)变量

1、定义变量

变量由一个类型声明符加一个或多个变量名组成的列表(c99及以后可以在函数内任意位置定义变量),例如:

int a;  // a是int类型的变量
double b=1.0;  //b是double类型的变量,赋1.0为初值
char c, d;  // c, d是char类型的变量

2、常用特殊前缀

extern int a;  // 声明一个int类型的变量a,一般用在.h文件中声明项目全局变量
const int b=1;  // 定义一个不可变的变量b,使用const关键字都要赋初值
static int c=1;  // 在函数中使用,只在第一次使用时初始化,相当于作用域在函数内的全局变量
typedef long long int;  // 把long long当作int使用

3、数组与初始化变量

int a=1;  // 给a初始化为1
// 以下为C99加入的特性
int b[10] = {1};  // 第一个元素初始化为1,其他9个元素初始化为0
int c[10] = {0};  // 全部初始化为0,常用初始化手段
int d[10] = {[1]=1, 2, [4]=4};  // 0 1 2 0 4 0 0 0 0 0

4、变量作用域

变量有两种类型:局部变量全局变量,变量作用域即变量可使用的范围。

对于局部变量可以简单理解为大括号{}内即为一个作用域,变量在哪个大括号内,作用域就在哪。

对于全局变量的作用域就是在当前的.c文件中,在.h文件声明后可以在整个项目内使用。

对于同名变量,小作用域的变量会在其作用域中覆盖大作用域的变量。

(1)局部变量与全局变量的差别

差别因素 局部变量 全局变量
初始值 初始值取决于内存里的数(随机) 一般为0,指针为null
作用域 仅限于大括号内 .c文件甚至项目


(三)字符串

字符串在c语言中有两种形式char*和char[],这里简单分辨下两者之间的不同。
char* c1="HelloWorld!"中,c1指向代码段中的常量,只读不写,且常量相同,指向的地址也相同。
char c2[]="HelloWorld!"中,c2指向堆栈段中的数据,可读可写,相当于把代码端的数据拷贝了出来。


(四) 自定类型——结构体

结构体可以看作是一种个基础类型复合的类型。

// 声明如下:
struct DATE{int year, month, day;
};// 几种定义方式如下:
struct DATE date1;  // 不赋初值
struct DATE date2={2020, 4, 5};  // 根据结构体中的顺序赋初值,这里是年月日
struct DATE date3 = {.year=2020, .day=5};  // 给单独变量赋初值
struct DATE *date4 = &date3;  // 用指针取date3地址(指针后面会单独说)// 几种赋值方式如下:
date3 = (struct DATE){.year=1999};  // 将数据强制转换成struct DATE类型赋值
date3 = date2;  // 自动赋值
date3.year=2010;  // 对变量中单一元素赋值
date4->year=2010;  // 对指针所指变量中的单一元素赋值// 常用声明
typedef struct DATE2{int year, month, day;
} D;
D date5;  // 这样就可以不用写struct DATE2这么一长串,取而代之用D来表示

扩展:union
union作为关键字与struct类似,但是struct中每个成员都是单独的内存,而union只占最大成员变量的大小,通常用与二进制与十进制的转换。

union DATE{int year;int month;int day;
};  /* 一个union DATE只有一个int大小 */

扩展:enum枚举,枚举类似#define,但是有体系些(c语言的枚举不好用)

// 声明枚举, 默认下标RED:0, YELLOW:1, GREEN:2
enum COLOR1 {RED1, YELLOW1, GREEN1};
// 自定下标
enum COLOR2 {RED2=1, YELLOW2, GREEN2=5};



二、表达式


这里给出运算符优先级

优先级 运算符 名称或含义 使用形式 结合方向 说明
1 [] 数组下标 数组名[整型表达式] 左到右
() 圆括号 (表达式)/函数名(形参表)
. 成员选择(对象) 对象.成员名
-> 成员选择(指针) 对象指针->成员
2 - 负号运算符 -算术类型表达式 右到左 单目运算符
(type) 强制类型转换 (纯量数据类型)纯量表达式
++ 自增运算符 ++纯量类型可修改左值表达式 单目运算符
-- 自减运算符 --纯量类型可修改左值表达式 单目运算符
* 取值运算符 *指针类型表达式 单目运算符
& 取地址运算符 &表达式 单目运算符
! 逻辑非运算符 !纯量类型表达式 单目运算符
~ 按位取反运算符 ~整型表达式 单目运算符
sizeof 长度运算符 sizeof 表达式 / sizeof(类型)
3 / 表达式/表达式 左到右 双目运算符
* 表达式*表达式 双目运算符
% 余数(取模) 整型表达式%整型表达式 双目运算符
4 + 表达式+表达式 左到右 双目运算符
- 表达式-表达式 双目运算符
5 << 左移 整型表达式<<整型表达式 左到右 双目运算符
>> 右移 整型表达式>>整型表达式 双目运算符
6 > 大于 表达式>表达式 左到右 双目运算符
>= 大于等于 表达式>=表达式 双目运算符
< 小于 表达式<表达式 双目运算符
<= 小于等于 表达式<=表达式 双目运算符
7 == 等于 表达式==表达式 左到右 双目运算符
!= 不等于 表达式!= 表达式 双目运算符
8 & 按位与 整型表达式&整型表达式 左到右 双目运算符
9 ^ 按位异或 整型表达式^整型表达式 左到右 双目运算符
10 | 按位或 整型表达式|整型表达式 左到右 双目运算符
11 && 逻辑与 表达式&&表达式 左到右 双目运算符
12 || 逻辑或 表达式||表达式 左到右 双目运算符
13 ?: 条件运算符 表达式1? 表达式2: 表达式3 右到左 三目运算符
14 = 赋值运算符 可修改左值表达式=表达式 右到左
/= 除后赋值 可修改左值表达式/=表达式
*= 乘后赋值 可修改左值表达式*=表达式
%= 取模后赋值 可修改左值表达式%=表达式
+= 加后赋值 可修改左值表达式+=表达式
-= 减后赋值 可修改左值表达式-=表达式
<<= 左移后赋值 可修改左值表达式<<=表达式
>>= 右移后赋值 可修改左值表达式>>=表达式
&= 按位与后赋值 可修改左值表达式&=表达式
^= 按位异或后赋值 可修改左值表达式^=表达式
|= 按位或后赋值 可修改左值表达式|=表达式
15 , 逗号运算符 表达式,表达式,… 左到右 从左向右顺序结合

总结优先度: 特殊运算符(括号、地址类) > 单目运算符 > 算数运算符(乘除>加减) > (移位运算) > 判断运算符(比较>相等) > (位运算) > 逻辑运算符(&&>||) > 三目运算符 > 赋值运算符 > 逗号运算符

针对十进制字面值
<<:左移数据,相当于乘2(右边填0)
>>:右移数据,相当于除2(unsigned左填0,signed左边填原来的最高位(因为负数移位还要是负数))



三、语句


简单语句:;,只有一个分号的空语句。
复合语句:由{}大括号嵌套起来的语句,空块(括号里什么都没用)等于空语句。

(一)条件语句

1、if语句

if语句一般格式:if…else if…else(翻译为如果…否则如果…否则)

if (age>18) {  // 如果年龄大于18岁
} else if(age<18) {  // 如果年龄小于18岁
} else {  // 上面的都不满足
}

可用搭配:
if...
if...else if...
if...eles...
if...else if...else if...else...

tips:
(1)if依据后面的条件语句的结果进行判断,非0为真,0为假
(2)else不需要接条件
(3)if语句后面不要接;

2、switch语句

switch语句一般格式:

switch(ch){  // switch是传入整数并判断整数进行判断case 'a':...break;case 'b':...break;default:...
}

tips:
(1)case只是入口,所以每个case都要用break;跳出
(2)default类型if语句中的else,即上面的case都不满足时进入
(3)switch只能传入整数进行判断,上面的例子就是将char类型的ch转换成了ASCII码进行比较
(4)switch后面不要接;


(二)迭代语句

1、while语句

while语句的一般格式:

while(条件){语句
}

tips:
(1)while适用于不知道次数的循环
(2)while后面不要接;

2、do while语句

do while语句的一般格式:

do{语句
}while(条件);

tips:
(1)do while适用于不知道次数且要先做一遍的循环
(2)do while后面要接;
(3)do while后面要接;
(4)do while后面要接;

3、for语句

for语句的一般格式:

for (初始化变量; 条件; 变量操作) {语句
}int n=10;  // 定义循环次数
// 例子1,循环n次
for (int i=0; i<n; i++) {;
}
等价于
int i=0;
while(i<n){;  // 语句i++;
}// 例子2,多参数
for (int i=0, j=10; i<n; i++, j--) {;
}
等价于
int i=0, j=10;
while(i<n){;  // 语句i++;j--;
}

tips:
(1)for适用于知道次数的循环
(2)for后面不要接;
(3)for可以压缩行数,简化部分使用while的情况


(三)跳转语句

break;直接跳出当前条件语句或迭代语句,能且只能 跳出 当前一个 语句。

continue;在 条件语句 中表示什么都不做(替代空语句);在 迭代语句 中表示 直接进入下一轮循环,不执行完当前循环

goto;跳转到指定位置(该位置必须有声明),例子:

start:  // goto声明...  // 语句...  // 语句...  // 语句goto start;  //跳转到start声明位置

!!!注意,goto仅推荐用于跳出多重循环,例如:

for (int i=0; i<n; i++) {for (int j=0; j<m; j++) {for (int k=0; k<o; k++) {if (跳出条件) {goto end;}}}
}
end:



四、函数


(一)函数一般格式

返回值类型 函数名(形参列表) {...语句...return 返回值;
}
// 例子,main函数
int main(){return 0;
}

tips:
(1)特殊的返回值类型void(什么都不返回),此时return 返回值;写为return;。
(2)形参列表为空时,表明不需要传入函数。


(二)函数声明

函数声明一般写在程序开头。尽管部分c语言编译器没有要求在调用函数时,就要知道函数格式。但是让编译器提前知道格式,就可以在编译时进行检查,防止我们错误使用了函数。

有一函数定义如下:

int f(int a){return a;
}

那么函数的声明可以写成:

int f(int a);
或者
int f(int);

特殊的对于返回值和参数都是void的函数,声明可以写成:

void f(void);


(三)结构体中的函数

如果能在结构体中写函数,那么结构体就更接近一个类了,例子如下:

struct SHOWDATE{void (*show)(int year, int month, int day);
};static void show(int year, int month, int day){printf("%d-%d-%d", year, month, day);
}static SHOWDATE showDate={.show=show};int main(){showDate.show(2020, 1, 1);return 0;
}



五、指针


(一)定义

int a=10;
int *p=&a;  // (1)(2)
*p = 12;  // (3)
int * const p1;  // (4)
const int * p2;  // (5)
int const * p3;

(1)*代表这是一个指针类型。具体到例子中就一个int*类型,代表p存放一个指向int类型的地址

(2)&代表取地址。在例子中就是取int类型变量的地址,即变量a的地址

(3)*p代表一个变量,这个变量就是p所指地址里面的变量

(4)int * const p1;不能修改p里的地址

(5)const int * p2;和int const * p3;不能修改p里地址对应的值


(二)结构体与指针

typedef strcut stDATE{int year, month, day;
} DATE;int main(){DATE date1={2020, 1, 1};DATE* date2=&date1;date1.year=2019;date2->month=2;printf("%d-%d-%d", date1.year, date1.month, date1.day);return 0;
}

(1)结构体变量访问结构体成员使用.,结构体指针变量访问结构体成员使用->。


(三)数组与指针

int a[10] = {0}  // (1)、(2)int *p = a;  // (3)void *q = (void*)p;  // (4)int *new = (int*)malloc(10*sizeof(int));  // (5)
free(new);

(1)int a[10]里面的a实际上是数组第一个变量的地址,所以可以int *p = a;。
(2)*(p+n)与a[n]等价。
(3)int*指针变量加上一个数n,代表指针变量的数值加上n*32(int的bit)得到偏移。
(4)q表示未定的类型(类似char*但不一样)。
(5)使用int*指针变量来创建数组,使用完要free(程序关闭会自动释放,如果程序长时间使用则会造成内存泄露)。

其他:
char c[][]错误;
char c[][10]正确且限制大小;
char *c[]正确,c[n]是一个char*的字符或字符串
char **c正确,一个指向指针的指针



六、文件读取


(一)文本文件

函数定义:

FILE* fopen(const char* restrict path, const char* restrict mode);  // 打开文件。参数:路径,模式
int fclose(FILE* stream);  // 关闭文件
fscanf(FILE*, ...);  // 文件读取(类似scanf,只是加了第一个参数,具体在八)
fprintf(FILE*, ...);  // 文件输出(类似printf,只是加了第一个参数,具体在八)

fopen的mode选项:
r:只读
r+:读写,从文件头开始
w:只写,清空或新建
w+:读写,清空或新建
a:追加,追加或新建
…x:只新建,若存在则不能打开(wx、ax等)

例子:

FILE* p=fopen("file", "r");
if(fp) {...fclose(fp);
}


(二)二进制文件

函数定义(打开文件和关闭文件与文本文件一致):

// ptr:读入字符串存放的变量、size*nmemb:读多少字符、stream:文件句柄
size_t fread(void* ptr, size_t size, size_t nmemb, FILE* stream);
size_t fwrite(const void* ptr, size_t size, size_t nmemb, FILE* stream);

二进制文件读写主要是读写结构体,现在不常用,因为可移植性不好,不如读写文件



七、编译预处理指令与.h文件


(一)编译预处理指令

在c语言中,所有#开头的语句都是编译预处理指令。
c语言编译经过
.c——处理编译预处理指令——》
.i——c编译器编译成汇编文件——》
.s——生成目标代码文件——》
.o——生成可执行文件——》
#.out / .exe
四步得到可执行文件,第一步就是处理编译预处理指令。

1、# include < stdio.h >

# include <stdio.h>就是将stdio.h文件里面的内容复制到代码里面去

2、#define 名称 操作(宏定义)

# define被称为宏定义,格式为# define 名称 操作
例子:

#define PI 3.14159
#define cube(x) (x*x*x)int main(){cube(3);return 0;
}

可以用宏定义定义一个变量PI或一个方法cube。

宏定义定义方法看起来很方便,但十分不推荐初学者使用,因为宏定义的方法是没有类型的,而且运算顺序也不好理解(看上面 二、表达式 15个运算等级的表,就知道多复杂了)。

如果确实想用类似宏定义的方式来定义函数,可以使用下面的方法。

3、(补充)inline内联函数

inline char *dbtest(int a)
{return (a % 2 > 0 ? "奇" : "偶");
}


(二).h文件

.h文件主要用来声明对应.c文件里面的变量或函数,把.c文件里面的声明放到.h文件就可以了(全局变量需要加上extern前缀)。

导入标准库时推荐使用<>,如# include <stdio.h>
导入自定声明时推荐使用"",如# include "train.h"


(三)一些常用宏

printf("%d", __LINE__);  // 输出当前语句行号
printf("%s", __FILE__);  // 输出当前文件名
printf("%s", __DATE__);  // 输出编译日期
printf("%s", __TIME__);  // 输出编译时间
printf("%d", __STDC__);  // 当要求程序严格遵循ANSIC标准时该标识符被赋值为1
printf("%s", __FUNC__);  // 输出当前函数名



八、常用函数


(一)常用函数

size_t = unsigned int

库名 函数定义 解释
默认 size_t sizeof(type_name) 返回byte
string.h size_t strlen(const char *s) 返回s的字符串长度(不包括最后的\0)
string.h int strcmp(const char *s1, const char *s2) 比较两个字符串,返回0:相等; 1:s1>s2; -1:s1<s2
string.h int strncmp(const char *s1, const char *s2, size_t n) 安全版本比较前n个字符的大小,其他同上
string.h char* strcpy(char *restrict dst, const char *restrict src) 把src的字符串拷贝到dst,restrict表示不重叠
string.h char* strncpy(char *restrict dst, const char *restrict src, size_t n) 安全版本,拷贝n个字符,其他同上
string.h char* strcat(char *restrict s1, const char *restrict s2) 把s2拷贝到s1后面,s1要足够大
string.h char* strncat(char *restrict s1, const char *restrict s2, size_t n) 安全版本,追加n个字符,其他同上
string.h char* strchr(const char *s, int c) 在s串中找到c第一次出现的位置,返回指针,没有为null
string.h char* strrchr(const char *s, int c) 在s串中从右边找到c第一次出现的位置,返回指针,没有为nulltring.h
string.h char* strstr(const char *s1, const char *s2) 在字符串s1中不忽略大小写寻找字符串s2
string.h char* strcasestr(const char *s1, const char *s2) 在字符串s1中忽略大小写寻找字符串s2
string.h void *memset(void *s, int c, unsigned long n) 将指针变量s所指向的前n字节的内存单元用一个“整数”c替换
string.h void *memcpy(void *dest, const void *src, size_t n) 从src的开始位置拷贝n个字节的数据到dest。如果dest存在数据,将会被覆盖。
stdlib.h system(“pause”) 暂停程序,按任意键继续


(二)scanf和printf

scanf(stdio.h)函数声明:int scanf(const char *format, …)
format格式:%[flag]type

printf(stdio.h)函数声明:int printf(const char *format, …)
format格式:%[flags][width][.prec][hlL]type

flag 含义
- 跟width一起用,左对齐(%-9d)
+ 正数强制输出正号(%+9d) 可以%±9d/%-+9d
正常输出
0 数字前填充0(%09d) 不可以%-09d(因为负号已经是左对齐了)

width / prec 含义
number 最小字符数
.number 小数点后位数。%9.2f:一共9位,小数点后2位(正数部分7位)
* 将number放到后面作为参数使用(%*d, number, int)
.* 将.number放到后面作为参数使用(%.*d, .number, int)

hlL 含义
hh 单个字节(char 1byte)
h short(2byte)
l long(4byte)
ll long long(8byte)
L long double(16byte)

type 用于 含义
i / d int 接受整数值并将它表示为有符号的十进制整数,i是老式写法
u unsigned int 无符号10进制整数
o unsigned int 无符号8进制整数(不输出前缀0)
x / X unsigned int 无符号16进制整数,x对应的是abcdef,X对应的是ABCDEF(不输出前缀0x)
f / F / lf double 单精度浮点数和双精度浮点数用f(lf 在C99开始加入标准,意思和 f 相同)
e / E double 科学计数法表示的数,此处"e"的大小写代表在输出时用的“e”的大小写
g / G double 有效位数,如:%.8g表示单精度浮点数保留8位有效数字。
c char 字符型。可以把输入的数字按照ASCII码相应转换为对应的字符
s / char * / wchar_t * 字符串。输出字符串中的字符直至字符串中的空字符(字符串以’\0‘结尾,这个’\0’即空字符
p 指针(void *) 以16进制形式输出指针
n 读入/写出的个数(int *) 到此字符之前为止,一共输出的字符个数,不输出文本
% 不进行转换,输出字符‘%’(百分号)本身
m 打印errno值对应的出错内容,(例: printf("%m\n"); )

【C语言】c语言基础知识梳理(超全)相关推荐

  1. 编程入门:C语言基础知识全网超全不用到处找了!

    你背或者不背,干货就在那里,不悲不喜 你学或者不学,编程就在那里,不来不去 听到这话的你是否略感扎心? 01基础知识 计算机系统的主要技术指标与系统配置. 计算机系统.硬件.软件及其相互关系. 微机硬 ...

  2. c语言 异或_编程入门:C语言基础知识全网超全不用到处找了!(文末附清单)

    你背或者不背,干货就在那里,不悲不喜 你学或者不学,编程就在那里,不来不去 听到这话的你是否略感扎心? 01基础知识 1. 计算机系统的主要技术指标与系统配置. 2. 计算机系统.硬件.软件及其相互关 ...

  3. 无源元件之——电阻器基础知识(超全)

    电阻.电容.电感是常见且重要的无源器件,本系列文章将分为三篇分别介绍这三种元件的详细的基础知识.本文的电阻介绍将会从电阻的型号命名.分类.主要特性参数.电阻器阻值标示方法.常用电阻器. 导电体对电流的 ...

  4. c语言需要哪些英语基础,学习C语言的必备基础知识(国外英语资料).doc

    学习C语言的必备基础知识(国外英语资料) 满卧裹瑟莉筑部获搪肪棱惺杀摄械圭旬敷豹休登悬邱雀报台盼拈毒鹰进怀却恩登雄旁二宇谊婆叔陌嘎扇体歌嫉蹿久题篡憨琵夹涌芦鸣褐颂诅讳拴狸果液梦绸亥氯确杯牌憨耗终贼况榔 ...

  5. R语言可视化绘图基础知识详解

    R语言可视化绘图基础知识详解 图形参数:字体.坐标.颜色.标签等: 图像符号和线条: 文本属性: 图像尺寸及边界: 坐标轴.图例自定义等: 图像的组合: #install.packages(c(&qu ...

  6. c语言二级程序设计题难吗,c语言二级公共基础知识试题特点

    二级C一直以来是整个二级考试中试题最多.难度最大.报考人数也最多的考试,以下是由学习啦小编整理关于c语言二级公共基础知识试题特点的内容,希望大家喜欢! 从2008年4月份开始笔试由原来120分钟减少到 ...

  7. Java编程语言学习:Java语言编程的基础知识之Java的变量与数据类型、符号、运算符、数组Array总结之详细攻略

    Java编程语言学习:Java语言编程的基础知识之Java的变量与数据类型.符号.运算符.数组Array总结之详细攻略 目录 Java语言编程的基础知识之Java的变量与数据类型.符号.运算符.数组总 ...

  8. C语言中重要基础知识的概述

    本章主要对于C语言中的基础知识进行一个大致的描述,适合有C语言基础但长久没接触C语言开发的人员进行快速回忆.在总体回忆基础知识之前,先来创建一个C程序.笔者的编译器是visual stduio2013 ...

  9. python入门题目及答案_Python基础自测题答案和基础知识梳理

    Python基础自测题答案和基础知识梳理 1.关于Python中的lambda表达式的函数体自能是单独一条语句,所以答案选择C. 例如:>>>g = lambda x: 2*x+1 ...

  10. python理论知识选择题_Python基础自测题答案和基础知识梳理

    Python基础自测题答案和基础知识梳理 1.关于Python中的lambda表达式的函数体自能是单独一条语句,所以答案选择C. 例如:>>>g = lambda x: 2*x+1 ...

最新文章

  1. SpringBoot返回枚举对象中的指定属性
  2. 中小型企业开展网站关键词优化,怎样才能达到理想优化效果?
  3. visibility和display隐藏元素的区别
  4. 非程序员如何使用 Git——版本控制你的生活
  5. 【深度学习的数学】单层感知机是什么?
  6. SAP CRM HANA report里 默认filter 的工作机制分析
  7. 基于Matlab的模拟通信实验平台设计,【通信原理仿真实验】通信原理虚拟实验仿真平台的设计和实现_玛雅作文网...
  8. c语言数字字体的格式,c语言—— 格式控制符—— 数据类型——相对应的字节数...
  9. 如何跨服务器复制表中数据
  10. 测试工具之RobotFramework界面基本功能使用
  11. 苏宁入局区块链;山东用阿里的AI抓违建;印度拟让苹果退网 | 极客头条
  12. 关于渐变属 gradient:
  13. IDEA中添加Tomcat配置,Run/Debug Configurations中没有Tomcat选项
  14. C++ 多态与虚函数面试题
  15. 同样的事情,小孩叫逆反,大人叫抬杠
  16. java共享汽车租赁系统
  17. python counter函数_Python中的魔法函数——Counter
  18. rand()函数的用法
  19. M1 Pro 和 M1 Max MacBook Pro,我们该选择哪款MacBook
  20. 自学python能成功吗_自学Python之路一

热门文章

  1. Tomcat 下载、安装、配置图文教程
  2. 微信小程序下载文件到本地
  3. asp.net门诊收费管理系统
  4. ASP.net 探针
  5. 计算机数值分析为什么那么难,数值分析方法
  6. 英伟达显卡不同架构_求历代英伟达显卡架构名称
  7. 让我们准备祭奠小米帝国
  8. 教你一键式下载iOS旧版APP(2021年有效)
  9. 如何在doc下运行java程序及打包成.jar格式的Java程序
  10. 在xp IIS上搭建动易论坛注意事项