这是我参与「第五届青训营 」伴学笔记创作活动的第8天
Nil异常续
上次说到空指针异常是因为没有初始化服务接口去调用接口函数。有时候不需要初始化调用函数也可以,这是为什么呢!现在就给个说法吧:当结构体没有调用其他服务接口时,可以不用初始化。但是如果结构体里调用了其他接口服务,需要出初始化。
type VideoServiceImpl struct {
}
func(videoService *VideoServiceImpl) Method(){
// videoService不需要初始化
videoService.OtherMethodOfVideoService
}
type VideoServiceImpl struct {
UserService
CommentService
LikeService
}
func(videoService *VideoServiceImpl) Method(){
// videoServiceNew需要初始化
videoServiceNew := &VideoServiceImpl{
UserService: &UserServiceImpl{},
CommentService: &CommentServiceImpl{},
LikeService: &LikeServiceImpl{},
}
// videoServiceNew需要初始化,调用其他服务的方法
videoServiceNew.OtherMethodOfOtherService
}
循环依赖
结合上面的代码可以看到,videoService需要用到likeService里的方法,likeService需要调用videoService方法,所以会导致循环依赖,体现在代码层面我感觉是阻塞,或者说是死锁,下面图片videoService里调用likeService的函数测试卡住了。videoService卡在likeService的调用处,当我在此处不再调用likeService里的方法,测试就可以通过。但需要调用仍然未解决!
type LikeServiceImpl struct {
VideoService
}
总结
- 初始化对象最保险,报Nil异常时,首先看下有没初始化的情况。
- 这种服务接口之间调用很麻烦,耦后性高,容易造成循环依赖!
- 写代码的时候一定要写单元测试。从Dao层到Service层的每个函数,只要每个单元测试都没问题了,代码出错的概率降低。