01 起源
编程范式(Programming Paradigm)指从事软件工程的一类典型的编程风格。通过了解编程语言的范式,能加深对编程语言的认识,提高自己的编程技能,写出更好的代码。
C 语言
- 静态弱类型语言,使用变量时需要声明变量类型,但类型间可以有隐式转换;
- 不同的变量类型可以用结构体(struct)组合在一起,声明新的数据类型;
- 可以用 typedef 关键字定义类型的别名,达到变量类型的抽象;
- 有结构化程序设计、具有变量作用域以及递归功能的过程式语言;
- 传递参数一般是以值传递,也可以传递指针;
- 通过指针可以容易地对内存进行低级控制,同时也加大了编程复杂度;
- 编译预处理让语言的编译更具有弹性(跨平台)。
程序员可以在微观层面写出非常精细和精确的编程操作,可以在底层和系统细节上非常自由、灵活和精准地控制代码。但在代码组织和功能编程上不占优势。
void swap(int* x, int* y)
{
int tmp = *x;
*x = *y;
*y = tmp;
}
要达到调用完函数后,实参内容的交换,必须要把实参的地址(即指针)传递进来。但该函数只能给 int 值用。
编译器会使用一切方式来做类型转换,类型转换有时候可以让编程更方便一些,也让相近的类型可以做到一点点的泛型。但类型转换会出很多问题。double 型的或 long 型 64 位的类型强转成 int,会导致程序的步长不一样。
C 语言的泛型
swap 函数
void swap(void* x, void* y, size_t size)
{
char tmp[size];
memcpy(tmp, y, size);
memcpy(y, x, size);
memcpy(x, tmp, size);
}
- 增加 size 参数:用了 void* 后类型被抽象掉了,编译器不能通过类型得到类型的尺寸,需要手动地加上一个类型长度的标识;
- 使用 memcpy() 函数:类型被抽象掉了,有可能传进来的参数类型是一个结构体,不能用赋值表达式,为了交换复杂类型的值,只能使用内存复制的方法;
- temp[size] 数组:交换数据时需要用的 buffer,用 buffer 来做临时的空间存储。
#define swap(x, y, size) {\
char temp[size]; \
memcpy(temp, &y, size); \
memcpy(&y, &x, size); \
memcpy(&x, temp, size); \
}
编译器做字符串替换,会导致代码膨胀,编译出的执行文件比较大。
无法检查传入参数的size,增加接口复杂度。