一:背景
在 CLR 源码中,我们会看到很多关于 typedef
的定义,比如下面这样:
// Callback function type used by DacStreamManager to coordinate
// amount of available memory between multiple streamable data
// structures (e.g. DacEENamesStreamable)
typedef bool (*Reserve_Fnptr)(DWORD size, void * writeState);typedef BOOL (*NTQUERYSYSTEMINFORMATION)(SYSTEM_INFORMATION_CLASS SystemInformationClass,PVOID SystemInformation,ULONG SystemInformationLength,PULONG ReturnLength);typedef struct _HashInstanceKey {TADDR addr;DAC_INSTANCE* instance;
} HashInstanceKey;typedef TokenHashMap<EEClass> EEClassToTypeRefMap;
typedef TokenHashMap<MethodTable> MTToTypeRefMap;
如果你不了解 C 的话又是一阵头晕,那 typedef
到底能给我们带来什么好处呢?直白的说,它可以给某一些类型定义别名,比如结构体
,变量
,函数指针
等等,类型越复杂好处越大,接下来我们举两个例子说明一下。
二:typedef 的简单用法
使用 typedef 定义函数指针
在不用 typedef
的前提下,我们看看原生方式的 函数指针
有多么复杂,参考代码如下:
#include <iostream>//函数指针
int (*ptrAddFunc)(int a, int b);int Add(int a, int b) { return a + b; }int main()
{int (*ptrAddFunc1)(int a, int b) = Add;int (*ptrAddFunc2)(int a, int b) = Add;int sum1 = ptrAddFunc1(10, 20);int sum2 = ptrAddFunc1(100, 200);printf("sum1=%d, sum2=%d", sum1, sum2);
}
如果用 typedef
来统一替换别名会怎么样呢?试一试就知道了哈,参考代码如下:
#include <iostream>//函数指针
typedef int (*ptrAddFunc)(int a, int b);int Add(int a, int b) { return a + b; }int main()
{ptrAddFunc func1 = Add;ptrAddFunc func2 = Add;int sum1 = func1(10, 20);int sum2 = func2(100, 200);printf("sum1=%d, sum2=%d", sum1, sum2);
}
是不是找到了写 C# 的感觉了哈,太方便了。
建立一套自己的类型系统
熟悉 C# 的朋友应该了解其有一套基元类型如:Int32, Int64,Float, Double,那如何将它带到 C 的环境下呢?这就需要用 typedef 啦,参考如下代码:
#include <iostream>typedef long long Int64;
typedef int Int32;
typedef float Float;
typedef double Double;int Add(int a, int b) { return a + b; }int main()
{Int32 i32 = 10;Int64 i64 = 11;size_t s1 = sizeof(Int32);size_t s2 = sizeof(Int64);printf("output:sizeof_int=%zu,sizeof_long=%zu,i32=%d,i64=%d", s1, s2, i32, i64);
}output:sizeof_int=4,sizeof_long=8,i32=10,i64=11
三:typedef 和 define 的区别
仔细想想,其实它们基因是不同的,一个是占位符
,一个是取别名
,两个不同用途的东西自然就会在多个场景下有着不一样的展示, 比如在指针
上就有区别。
#include <iostream>#define ptr1 char*
typedef char* ptr2;int main()
{ptr1 p1, p2;ptr2 p10, p20;printf("output: p1=%zu, p2=%zu,p10=%zu, p20=%zu", sizeof(p1),sizeof(p2),sizeof(p10),sizeof(p20));
}output: p1=4, p2=1,p10=4, p20=4
从size大小可判断,4 表示一个32bit的指针单元,那 1
是什么东西呢?我们截图看一下:
可以看出它是一个 char
类型,这就是它们俩不一样,当然这是编译器层面做出的选择,大体上就聊这么多吧,希望对你有帮助。