一托管代码定义由 .NET 运行时CLR全权管着的代码帮你做内存管理、安全检查、垃圾回收特点运行依赖 CLR公共语言运行时你的 C# 代码编译后不是直接变成机器码而是先变成IL中间语言运行时由 CLR 即时编译JIT成机器码执行。CLR 帮你做所有脏活累活自动垃圾回收GC不用手动new/delete自动回收不用的内存类型安全检查防止越界、非法指针操作异常处理try/catch机制内存管理栈 / 堆分配、装箱拆箱全由 CLR 管安全沙箱限制代码权限防止恶意操作完全不用管指针你写 C# 时几乎碰不到*指针所有内存访问都是安全的不会出现野指针、内存泄漏除非你故意用非托管。二非托管代码定义非托管代码就是不依赖 CLR直接跑在操作系统上的原生代码。完全自己管自己的代码内存、指针、生命周期全靠自己出问题直接崩。特点直接编译成机器码比如 C/C 代码编译后直接生成.exe/.dll直接给 CPU 执行没有中间层。所有事情自己来手动内存管理malloc/free/new/delete漏了就内存泄漏错了就野指针崩溃自己处理类型安全数组越界、指针错误不会被拦截直接崩没有 GC内存生命周期完全由开发者控制C# 里怎么写非托管C# 本身默认是托管的要写非托管必须用unsafe上下文 指针还要开启项目的「允许不安全代码」选项三两者区别特性托管代码C# 日常写的非托管代码C/C /unsafe C#运行依赖.NET CLR 运行时操作系统直接执行编译产物IL 中间语言JIT 即时编译原生机器码内存管理GC 自动回收无需手动手动分配 / 释放自己负责指针操作默认禁止安全访问完全支持野指针风险高类型安全CLR 严格检查防止越界无检查直接崩溃性能开销有 CLR overhead很小零 overhead极致性能开发效率极高不用管内存极低全靠自己踩坑适用场景业务系统、桌面应用、Web、游戏逻辑高性能计算、驱动、底层交互、游戏引擎四为什么要懂这个哪怕你 99% 的时间都写托管代码懂托管 / 非托管的区别是 C# 开发者的「底层认知」原因有 5 个1.理解 C# 的「安全」和「便利」从哪来你写 C# 不用管内存、不会崩不是 C# 厉害是CLR 帮你扛了所有风险。懂了这个你就明白为什么 C# 不能直接操作指针CLR 禁止保证安全为什么string不可变CLR 托管优化为什么 GC 会暂停托管代码的代价2.排查性能问题的关键很多性能坑本质都是「托管 / 非托管交互」搞的频繁 P/Invoke 调用非托管 DLL每次调用都有跨边界开销性能暴跌非托管内存泄漏C# 调用 C DLL 时没释放非托管内存程序越跑越慢unsafe 代码滥用为了性能写了一堆指针结果出了野指针调试到崩溃3.和底层系统 / 其他语言交互的必备知识你迟早会遇到这些场景调用 Windows API全是非托管用 C 写的第三方库比如游戏引擎、图像处理库操作硬件、驱动、嵌入式全是非托管做高性能计算、游戏开发Unity 里大量非托管交互不懂托管 / 非托管这些场景你根本写不对出问题也查不出来。4.理解 C# 的「边界」和「极限」C# 不是万能的极致性能、底层操作、硬件交互必须用非托管托管代码的安全是用「性能开销」和「功能限制」换来的懂了这个你就不会在需要极致性能的场景硬扛 C#而是知道什么时候该用非托管什么时候该用 C。5.面试必问区分「会用 C#」和「懂 C#」几乎所有中高级 C# 面试都会问这个问题什么是托管代码什么是非托管C# 里怎么写非托管unsafe 关键字的作用托管 / 非托管交互有什么坑GC 是托管还是非托管不懂这个直接被判定为「只会写业务的初级开发者」。五什么时候用到非托管代码极致性能优化比如游戏引擎、高频交易系统用 unsafe 指针绕开 CLR 开销调用系统 API / 第三方 DLL比如调用 Windows API、C 写的算法库操作非托管内存比如和硬件、驱动、嵌入式设备交互互操作场景比如 Unity 中 C# 和 C 引擎的交互内存敏感场景比如嵌入式、物联网设备资源有限不能用 GC2/3/4是上位机开发常用