一些面试题的备忘
ASP.NET Core
服务的注册方式和获取方式
解答
- 使用框架自带的
IoC
框架是通过Startup
的ConfigureService
方法里的IServiceCollerction
进行注册 - 一般通过接口与实现类的方式实现,也可以通过工厂的方式进行注册服务,不推荐直接
new
服务进行注册,这样IoC
框架是不会进行该服务的生命周期管理 - 获取方式一般可以通过构造函数、参数的
[FromService]
、通过BuilderServiceProvider
获取serviceProvider
对象,在serviceProvider
里获取服务
- 使用框架自带的
autofac
和自带的IoC
框架的区别解答
- Autofac新增基于名称的注入、属性注入、AOP
- 注册服务的地方是在
Startup
里新增的ConfigureContainer
方法里
WebAPI
的CQRS
策略JWT
的组成和加密方式解答
- 加密方式.经过base64转码的消息主体.签名
- 使用HS256的签名加密方式
ViewData
、ViewBag
、TempData
的区别解答:
ViewBag
是在ViewData
上面加一层dynamic
,如果用同个key
,比如ViewBag.Info="ABC"
,在页面其实也可以通过ViewData["Info"]
来获取,同时也以为着ViewBag="ABC";ViewData["info"]="123"
,后面会覆盖前面的;TempData
是存放在session
里面,意味着可以跨action
来取值,比如ActionA
中赋值了TempData["Info"]="ABC"
,在ActionA
对应的ViewA
中点击跳转到ActionB
,则可以直接在ActionB
中通过TempData["Info"]
来取得"ABC"
- 但是要注意,
TempData
在被取值之后就会被删除,所以上面的场景如果在ActionA
对应的ViewA
中把TempData["Info"]
取出来,则在ActionB
中就获取不到TempData["Info"]
的值,获取到的是个null
API
的版本管理解答
- 使用URL带版本的方式,在
Controller
里使用[Route('')]
来指定版本
- 使用URL带版本的方式,在
使用中间件Use/Run/Map的区别
解答
- 通常使用的
Use
Run
起到的是断路器的作用,即不再执行后面的中间件Map
一般是针对特殊的路径使用特殊的中间件管道
- 通常使用的
中间件里面怎么获取服务
解答
- 使用中间件的
Invoke
方法中的HttpContext
对象context.RequestServices.GetService<T>()
来获取
- 使用中间件的
EFCore
的TPH
EFCore
的lazyload
数据库相关
delete
、truncate
的区别解答:
delete
可以带where
,truncate
不能带where
delete
慢,truncate
快delete
每删一条数据都会在数据库日志里记录这条记录,truncate
只会记录整表做了清除记录,这意味这delete
可以被回滚,truncate
是不能回滚的delete
会触发delete
触发器,truncate
是不会触发任何触发器的
view
、table
的区别go
做了什么,go
上面定义的变量go
下面能获得到吗?- 定义事务的标准
- 连续自增的主键删除掉一个断开了,怎么补回这个断掉的逐渐
select * into A from B
、insert into A select * from B
的区别
上面的执行结果是什么create table #tmp_A(id int) go insert into #tmp_A values(1) --select * from #tmp_A if @@error<>0 print @@error else print @@rowcount
- 存储过程中
@
、#
、##
、CTE
的区别 - 聚集索引与非聚集所以区别
其他
.xsd
、XML
的schemas
json
是什么rabbitmq
中的topic
、queue
是什么,消息持久化是在哪个位置说一下
pub/sub
,订阅的时候能获得订阅之前的消息吗?Queue
、ConQueue
的区别从数据结构说一下
stack
、queue
的区别编译的时候
Debug模式
和Release模式
的区别解答:
- 在
Debug
模式可以使用#IF DEBUG
来跑一些调试模式下的特殊代码,在打包成Release
的DLL
的时候,#IF DEBUG
的代码会被忽略
- 在
编译时选择
Any CPU
、x86
、x64
的区别DDD
是怎么分层的说一下 聚合根、实体、值对象
DDD
的仓储层是怎么实现的async/await
会不会堵塞主线程,如果会,那为什么还要用?解答
- 调用线程在遇到
await
的时候,会直接返回去做调用后的事情,不会执行await
后面的代码 - 可以粗暴的认为,在
await
后面的代码会被包装成一个回调,在await
代码执行完成之后,再执行回调代码,其中回调的线程具备多种可能行,可能是执行await
代码的线程,也可能是新线程 - 反编译查看:首先IL里面是没有
async/await
的,就是常规代码,代码正常执行的时候,会实例化一个状态机,状态=-1,然后执行Task前面的普通代码,遇到await Task.Run()
的时候会启动线程去执行Task,然后判断是否完成,这时候线程刚启动肯定没完成,所以判断为未完成,并将状态重置=0,然后递归调用一下自己,调用之后再次判断是否状态,发现状态=0,则表示调用线程任务完成,返回去做自己原来的事
- 调用线程在遇到