看代码看了2个月,找BUG也断断续续有一个月了吧。已经各种诡异的疑难杂症,在这里写点心得记录一下。
不过讲道理我的工作就像是专门为了找BUG而生的。测试或者线上可能出现的各种问题都有可能到我们这儿,我们再来推断问题原因是自己、或是业务方、或是后台、或是算法。我遇到过的还没有BUG原因是自己这边的。然鹅,就算不是自己的也不代表就可以水水过去,还是要根据自身的代码和日志来分析问题究竟出在哪边,就跟柯南的推理一样,讲究证据。
1.搜索Ctrl+F
来了一条日志,有个变量不知道它的值代表什么意思怎么办?
比如下图:
当然是去代码里面“搜索”关键词,找到打印这条日志的函数,然后上下文分析。
2.查看定义&查找所有引用
那么怎么进行上下文分析?
上文:想要知道是什么函数调用了这个函数,那么请查找所有引用,在筛选结果中找到最合适的。然后一级一级地往上找,最后就能知道是从哪个入口调用了你这个模块的函数。
比如,你写了个SDK,给了接口给业务方A、B、C,结果通过上文分析发现是业务方B的那个函数出现的问题,那么就可以确定这个问题应该去找B跟进。
然而查找所有引用有个蛋疼的问题,加入编译器告诉你这个函数的被引用次数有几千个,那完了,天知道应该从哪个洞口往上爬。这就考验代码写得好不好了。
除此之外,查找所有引用还有个作用,就是去查看某个类的变量是被什么东西设置或者修改的,这在动态运行的程序里很常见。比如统计当前观众数的、统计攻击次数、伤害值的等等。
下文:下文分析很简单,函数A调用函数B,B又调用了函数C。当你想知道函数A的具体实现逻辑时,当然就是用下文分析,不停地查看包含函数的定义,这样就知道了底层实现逻辑。下文分析不可能有分支让你选择,它的定位就是这么准确。
3.举个栗子
假如你想知道日志里的 value 值是啥意思。
1.把这条日志具有显著特征的关键词复制下来,去源代码里搜索;
2.搜索到了,是在函数funSetValue(int num)里面,但是value值是被函数的参数num设置的;
3.怎么办,当然是上文分析,查找该函数的所有引用,看看是谁设置了num这个函数参数;
4.OK,经过层层向上剖析,终于知道了是哪个函数,假设是loop()函数;
5.接下来又想知道funSetValue(int num)的更底层逻辑,简单,下文分析查看定义就行了;
6.最后,又发现这个变量其实是被loop()根据私有变量m_nCount动态更新的,查找m_nCount这个变量的所有引用,一个一个地看,就能知道它是怎么变化的。