ASP.NET Core 面试八股,在 .NET 圈子里是个绕不开的话题。先讲个结论:我和不少做技术负责人、做架构师的朋友聊过,大家面试时并不指望你把概念背得一字不差,而是希望从这些高频题里听出你真正写过、踩过坑、思考过“为什么”。这篇文章算是把我在面试中常被问到、也常拿来问别人的一批 ASP.NET Core 高频题整理成精简版,每道题都给出可以直接输出的标准答案要点,再补上一些代码里才见得到的代价。适合正在准备 .NET 岗位面试的开发者,也适合想系统性查缺补漏的初级、中级后端工程师,看完你可以直接拿去对照自己的回答,不用抱着几百页文档啃。
之所以说是“精简版”,是因为这里的每一题都不是让你背的,而是帮你在面试时快速抓住题眼。面试官追问才是分水岭,所以我在每道题的答案后面会附上“为什么这么答”的说明和常见扩展追问方向,这部分往往才是真正拉开差距的地方。
1. 生命周期三兄弟:面试官绕不开的第一个大坑
1.1 AddSingleton、AddScoped、AddTransient 到底怎么答
这是 .NET 面试中出现频率几乎百分之百的题。标准答案很多人会背:Singleton 是单例,整个应用生命周期只有一个实例;Scoped 是作用域,每个请求一个实例;Transient 是瞬态,每次获取都会创建新实例。但面试官真正想听的是后面那句:你用它们的时候有没有吃过亏。
我建议的回答框架是这样的:
- 先给出三者的注册方式和典型用途:DbContext 默认用 Scoped,因为一个请求内的数据操作应该共享同一个上下文;配置类、日志 Provider 这类无状态组件适合 Singleton;轻量级、短生命周期的服务适合 Transient。
- 然后主动提到Captive Dependency(被捕获的依赖)问题:Singleton 不能注入 Scoped 或 Transient 服务。这是因为 Singleton 实例一旦创建会一直存活,而 Scoped 服务是跟着请求走的,请求结束就销毁,Singleton 里握着这个实例不放,就等于把本应该短命的东西拖成了“长命”,下一个请求再来时拿到的是上一个请求残留的对象,DbContext 虽然设计上能在多个请求里被复用(因为它内部有状态清理),但这样用迟早出大问题。
这里有个很经典的实际事故:有人把 ILogger 注册成 Transient,然后一个 Singleton 工作类里注入它,正