//欲练此功必先自宫!!!
//第一天:C语言的基础
//进制
//2进制, 10进制, 8进制, 16进制
//注:8进制数前加0, 16进制数前加0x
//进制转换:
//10 -> n: 连除到取余
//n -> 10: 按权求和法(基数, 位权)
//n -> n: 1个8进制位 = 3个2进制位, 1个16进制位 = 4个2进制位
//字节
//1字节 = 8位2进制
//单行注释: //
//多行注释: /* */
//注:注释不参与程序编译, 可以出现在任何位置
//main函数: 是程序入口, 只能有一个
//数据类型
//基本类型: 1.整型: short int long 2.浮点型: float double 3.字符型: char
//构造类型: 1.数组[] 2.结构体struct 3.枚举enum
//指针类型: *
//空类型: void
//变量
//定义: 数据类型 变量名 = 初值
//注: 变量要先定义, 才能使用
//变量名的命名规范
//1.由数字, 字母, 下划线构成, 不能以数字开头
//2.在同一作用域内, 不能重名
//3.不能用系统的关键字(看颜色)
//4.见名知意(不用使用拼音, 汉字, 中英交叉)
//5.小驼峰法
//常量
//1, 19.9, 'c', "abc"
//运算符(单目, 双目, 三目)
//1.赋值运算符: =
//2.算术运算符: +, -, *, /, %, ++, --
//3.复合运算符: +=, -=, *=, /=, %=
//4.逻辑运算符: &&, ||, !
//5.关系运算符: >, >=, <, <=, ==, != (BOOL)
//6.条件运算符: ? :
//表达式 = 变量 + 常量 + 运算符
//语句: 程序执行的最小单元(见到;即语句)
//printf("Hi");
//printf("%d", a);
//格式化输出符
//char %c %d
//short %hd
//int %d
//long %ld
//float %f
//double %lf
//BOOL %d
//字符串 %s
//unsigned int %u
//unsigned long %lu
//八进制 %o
//十六进制 %x
//指针 %p
//以回车结束输入 %[^\n]
//%-10.2f:
//转义字符
//换行 \n
//tab \t
//% %%
//" \"
// \ \\
//scanf("%d", &a);
//注: ""内不能加\n, 后面写变量的地址
//第二天: 分支结构
//C语言的三大结构: 顺序结构, 分支结构, 循环结构
//if
//第一种形式
/*
if (<#condition#>) {
<#statements#>
}
*/
//第二种形式
/*
if (<#condition#>) {
<#statements#>
} else {
<#statements#>
}
*/
//第三种形式
/*
if (<#condition#>) {
<#statements#>
} else if (<#expression#>) {
<#statements#>
} else {
<#statements#>
}
*/
//注: 三种形式可以相互嵌套使用
//enum
enum 枚举名{
枚举值1,
枚举值2,
…
}
枚举值:枚举值默认从零开始,也可以指定数值;
枚举值常与switch合用
//switch
/*
switch (<#expression#>) {
case <#constant#>:
<#statements#>
break;
case <#constant#>:
<#statements#>
break;
default:
break;
}
*/
//注:1.switch后的表达式是整型表达式
//2.case后面的值是常量
//3.case和default中需要加break
//4.如果在case中定义变量, 需要case内部添加括号
/*
int a = 10;
switch (a) {
case 10:
{
int b = 100;
break;
}
default:
break;
}
*/
/*
//const用于修饰那一部分不能修改
//判断步骤
//1.去掉数据类型
//2.const后的就是不能修改的部分
int a = 10;
int b = 100;
const int *p1 = &a;//*p1不能修改
int const *p2 = &a;//*p2不能修改
int * const p3 = &a;//p3不能修改
const int * const p4 = &a;//p4和*p4不能修改
*/
/*
int max = 0, a = 5, b = 10;
max = a > b ? a : b;
if (a > b) {
max = a;
} else {
max = b;
}
*/
//第三天:循环结构
//for循环
/*
for (<#initialization#>; <#condition#>; <#increment#>) {
<#statements#>
}
*/
//while循环
/*
while (<#condition#>) {
<#statements#>
}
*/
//do...while循环
/*
do {
<#statements#>
} while (<#condition#>);
*/
//知道循环的次数, 使用for循环
//知道循环结束的条件, 使用while循环
//do...while循环使用比较少
//随机数公式[a, b]
//arc4random() % (b - a + 1) + a
//break: 跳出本层循环
//continue: 跳出本次循环, 加速循环的执行
//return: 跳出函数, 返回数值
//第四天:数组
//用于存储多个相同数据类型的有序队列
//数据类型 数组名[元素个数] = {};
//注: 元素个数可以省略, 由后面赋值来决定元素个数
//数值的使用
//1.数组不能够直接参与运算
//2.数组中的元素可以参与运算
//元素的访问
//1.通过下标访问数组元素
//2.下标从0开始, 到(元素个数 - 1)结束
//遍历数组
//遍历n维数组, 要嵌套n层for循环
//冒泡排序
/*
int array[5] = {12, 20, 3, 48, 5};
for (int i = 0; i < 5 - 1; i++) {
for (int j = 0; j < 5 - 1 - i; j++) {
if (array[j] > array[j + 1]) {
int temp = array[j];
array[j] = array[j + 1];
array[j + 1] = temp;
}
}
}
*/
//字符数组 = 字符串
//打印字符串: %s
//字符串函数
//strlen: 字符串长度
/*
char string[10] = "iPhone";
printf("%lu\n", strlen(string));//长度:6
printf("%lu\n", sizeof(string));//字节数:10
*/
//strcpy: 字符串拷贝
//strcat: 字符串拼接
//strcmp: 字符串比较
/*
int c = 5;
int array[c] = {};//数组定义时, 元素个数不能使用变量
*/
//第五天: 多维数组
//定义
//数据类型 数组名[维度1][维度2][...] = {};
//字符数组, 一维数组
//字符串, 一维数组
//字符串数组, 二维数组
/*
char string[5][20] = {"zhangsan", "lisi", "asan", "erhu", "guangtouqiang"};
//冒泡排序(a-z)
for (int i = 0; i < 5 - 1; i++) {
for (int j = 0; j < 5 - 1 - i; j++) {
if (strcmp(string[j], string[j + 1]) > 0) {
char temp[20] = {0};
strcpy(temp, string[j]);
strcpy(string[j], string[j + 1]);
strcpy(string[j + 1], temp);
}
}
}
*/
//第六天: 函数
//具有特定功能的代码段
//一个严格的函数包括
//1.函数声明
//2.函数定义
//3.函数调用
//函数定义
/*
返回值类型 函数名(参数类型 参数名, ...) {
}
*/
//注: 1.没有返回值, 使用void
//2.没有参数, 括号不能省略
//3.参数类型相同, 类型不能省略
//4.函数之间是并列的关系, 不能嵌套定义
//函数调用
//函数名(实参, ...)
//实参: 函数调用时的参数
//形参: 函数定义时的参数
//注: 函数调用时, 把实参的值拷贝给形参
//主调函数: 在函数a中调用了函数b, 函数a就称为函数b的主调函数
//局部变量: 定义在函数体内部的变量
//全局变量: 定义在函数体外部的变量
//注: 尽量不要使用全局变量
//函数可以嵌套调用
//递归函数, 一定要有出口
//*.h中写 函数声明
//*.m中写 函数定义
//如果在其他文件使用函数, 需要引入头文件
//数组作为函数的参数
//1.,数组名[],数组的元素个数省略
//2.多添加一个参数, 用于传递数组元素个数
//第七天: 结构体
//结构体是用户自定义的数据类型
//结构体声明
/*
struct <#struct name#> {
<#struct fields#>
};
*/
//注:1.结构体名字用小驼峰法
//2.每一个成员变量以分号结束
//3.结构体声明写在.h中
//结构体变量
//struct 结构体名 变量名 = 初值
//注: 1.结构体变量可以直接参与运算
//2. 结构体变量不能够直接打印
//结构体变量的成员变量
//使用点语法访问
//使用typedef对结构体重命名
//typedef 原结构体名 新结构体名
//注: 新结构体名要是大驼峰法
//结构体所占的字节数
//1.最大数据类型的倍数
//2.交换成员变量的位置, 会影响结构体所占的字节数
//char 1
//short 2
//int 4
//long 4或8
//float 4
//double 8
//指针 4或8
//结构体和数组相互嵌套使用
//1.结构体声明时, 成员变量是数组类型
//2.数组内存放的都是结构体类型的变量(结构体数组)
//第8天: 指针
//内存的地址编号
//&: 取地址运算符
//%p 打印地址
//指针变量: 用于存储地址
//数据类型 *变量名 = NULL
//注:1. 指针变量所占的字节数和数据类型无关, 只有操作系统的位数相关
//2.数据类型决定*p取内容时, 取多少个字节
//3.数据类型决定p + 1时, 跳转多少个字节
//*: 取值运算符
//指针变量被重新赋值, 意味着指针变量重定向
//指针的运用
//指针在数组中的运用
//数组的名字就是数组的首地址
// int a[5] = {1, 2, 3, 4, 5};
//*a a[0]
//*(a + 1) a[1]
//*(a + i) a[i]
// int *p = a;
//p 和 a 的区别
//1. 数组的名字a是一个常量指针, 不能重定向(修改)
//2. sizeof, p: 求指针所占的字节数; a: 求数组所占的字节数
//指针在字符串中的运用
// char string[] = "iOS";
// printf("%s\n", string);
// printf("%s\n", string + 1);
//
// char *q = string;
// printf("%s\n", q);
//第9天: 指针高级
//指针数组: 数组中元素类型是指针类型
int a = 10;
int b = 20;
int c = 30;
int *p[3] = {&a, &b, &c};
//p[0] &a *p
//p[1] &b *(p + 1)
//p[2] &c *(p + 2)
//*p[0] a *(*p)
//*p[1] b *(*(p + 1))
//*p[2] c *(*(p + 2))
//指针作为函数的参数
//作用: 在函数内部修改外部变量的值
//(int array[], int count)
//(int *array, int count)
//指针在结构体变量中的使用
//定义一个结构体指针变量 指向 结构体变量的首地址
//可以用->(指向操作符), 访问结构体的成员变量
//指针在结构体数组中的使用
struct student {
char name[20];
int age;
float score;
};
typedef struct student Student;
Student array[3] = {
{"zhangsan", 18, 59.9},
{"lisi", 20, 69},
{"wangmazi", 40, 30}
};
//array[0].name (*array).name
//array[1].name (*(array + 1)).name
//array[2].name (*(array + 2)).name
//array->name
//(array + 1)->name
//(array + 2)->name
//第10天: 动态内存分配
//内存的五大分区(地址编号由高到底)
//1.栈区(局部变量, 系统控制)
//2.堆区(由开发人员手动申请, 手动释放)
//申请 malloc
//释放 free p = NULL
//3.静态全局区(全局变量和static修饰的变量, 系统控制)
//static变量特点
//a. 存在静态全局区
//b. 只能被初始化一次
//c. 没有赋初值, 默认为0
//4.常量区(常量, 系统控制, 常量区的内容是只读的)
//5.代码区(函数,语句, 系统控制)
//第11天: 函数指针
//函数的名字就是函数的首地址
//函数指针类型确定的步骤
//1.把函数名换(*)
//2.去掉函数体和参数名
//int (*)(int, int)
/*
int printHello(int a, int b) {
}
*/
//函数指针变量
//int (*p)(int, int) = NULL
//注: 变量名写在*后面
//使用typedef重命名函数指针类型
//typedef int (*Type)(int, int)
//注: 新类型名, 写在*后面
//Type p = NULL
//指针指向函数的首地址
//p = printHello;
//printHello(3, 4)
//p(3, 4)
//回调函数: 使用函数指针变量调用函数
//函数指针变量作为函数的参数, 函数可以实现多种功能
//前提: 函数指针类型相同
//宏
//无参宏 只做简单地替换
//有参宏 #define kSum(A,B) ((A)+(B))
//表达式中的每一个参数加括号,整个表达式也要加括号
//条件编译
//三种条件编译
/*
#ifdef 标识符
代码段1
#else
代码段2
#endif
如果 标识符 被 #define 过 ,编译器编译代码段1,否则编译代码段2。
#ifndef 标识符
代码段1
#else
代码段2
#endif
如果 标识符 未被 #define 过 编译器编译代码段1,否则编译代码段2。
#if 常量表达式
代码段1
#else
代码段2
#endif
如果 常量表达式结果 非0 编译器编译代码段1,否则编译代码段2。
三种形式一样,以后主要用于版本控制;
*/
//经前人总结,若不自宫也能成功!!!
版权声明:本文为博主原创文章,未经博主允许不得转载。