美文网首页Android开发Android开发经验谈Android技术知识
到底怎样写 try-catch,才能称之为高手?

到底怎样写 try-catch,才能称之为高手?

作者: bfc7f634299a | 来源:发表于2019-08-23 10:50 被阅读7次

try-catch,一个大家最常见不过的语法,但是有些人却用不好。当面对一个崩溃的时候,不管三七二十一先catch住再说,没错,老崩溃是被catch住了,但是新崩溃又出现了,想想都是坑啊,本文就和大家探讨下这个话题,此外买一送一,再和大家探讨下空指针异常。

乱用try-catch

写过C++的人都知道,那异常捕获特别不好用,甚至有些异常还捕获不了,在Java中,try-catch特别好使,如果一个人的代码没有try-catch,有时候会被大家质疑代码写的不健壮。

try-catch虽好,但不可乱用,原因在于try-catch可以隐藏代码缺陷,不利于bug排查。如果没有try-catch,那程序会崩溃,崩溃后从日志中可以一眼看出问题的原因。而如果用了try-catch以后,崩溃被catch住了,这个时候程序没有崩溃,但是程序运行会不正常。

我相信大家都明白:crash并不可怕,可怕的是crash后却没有找到日志,你就慢慢去查吧,这感觉谁查谁知道。

举个例子来说明下:

public class Example {
    public static void main(String[] args) {

        BusinessLogic bl = new BusinessLogic();
        bl.doA();
        bl.doB();
        bl.doC();
        bl.doD();
        bl.doE();

    }

}


class BusinessLogic {

    public void doA(){
        System.out.println("I am doing A");
    }

    public void doB(){
        System.out.println("I am doing B");
    }

    public void doC(){
        int i = 1/0;
        System.out.println("I am doing C");
    }

    public void doD(){
        System.out.println("I am doing D");
    }

    public void doE(){
        System.out.println("I am doing E");
    }
}

上面的程序有个问题,在doC函数中存在除0异常,程序运行后会崩溃,我们可以得到如下日志反馈:

I am doing A
I am doing B
Exception in thread "main" java.lang.ArithmeticException: / by zero
    at BusinessLogic.doC(Example.java:27)
    at Example.main(Example.java:7)
sandbox> exited with status 0

但是有的程序员,特别害怕崩溃,为了让自己的程序不会崩溃,直接在最外层进行try-catch:

public class Example {
    public static void main(String[] args) {
        try {
            BusinessLogic bl = new BusinessLogic();
            bl.doA();
            bl.doB();
            bl.doC();
            bl.doD();
            bl.doE();
        } catch(Exception e) {
            e.printStackTrace();
        }
    }

}

结果,程序是不会崩溃了,但是逻辑并没有正确地执行,这个时候如果让你去排查这个问题,你能第一时间定位到doC函数有问题吗?我觉得大部分人都不能。

虽然这个例子看起来有点可笑,但是在实际开发中确实看到过不少这种现象,更有甚者,连e.printStackTrace()这句话都懒得加,程序没有任何异常日志,想排查这种错误简直痛不欲生。

空指针强迫症

前面说到崩溃,大家知道排名前2的崩溃是什么吗?没错,那就是:
NullPointerException
IndexOutOfBoundsException

大家可以检查下自己的项目,看看这两个异常是不是占大头。所以,为了防止空指针异常,很多程序员会这样写代码:

public class Example {
    public static void main(String[] args) {
        BusinessLogic bl = new BusinessLogic();
        Object param = new Object();
        bl.doA(param);
    }

}


class BusinessLogic {

    public void doA(Object o){
        if (o != null) {
            System.out.println("I am doing A with param : " + o);
            doB(o);
        }
    }

    public void doB(Object o){
        if (o != null) {
            System.out.println("I am doing B with param : " + o);
            doC(o);
        }
    }

    public void doC(Object o){
        System.out.println("I am doing C with param : " + o);
    }

}

上面程序犯了一个错误,那就是重复判空,大量的冗余判断会影响程序的性能,上面的例子很简单,我相信大家都不会犯这个错误,但是当项目大了以后,当函数调用错综复杂的时候,你还能保证自己不犯错吗?很难!

大家还记得C语言的strcpy函数吗?

strcpy(char * __restrict to, const char * __restrict from)
{
    char *save = to;

    for (; (*to = *from); ++from, ++to);
    return(save);

可以看到,C语言的strcpy函数,没有进行任何判断,比如你传递个空,或者说to的长度比from小,这些都会导致程序异常,但strcpy依然是不做任何判断,为的就是追求高性能。

对于strcpy来说,异常判断是上层调用方该考虑的事情,它作为底层API并不需要关注那么多,如果上层调用不合法,那就让程序挂掉就行了,谁叫你不按我的要求来呢!

这个涉及到架构设计的理念,我们在开发一个sdk的时候,其实是不需要每次都校验参数合法性的,明确对外暴露的API,如果说外部调用不合法,一定要让程序挂掉,而不是不回应,这样上层也更好排查问题,尤其是一些调用频次较高的底层sdk,更要注重这一点,性能和调用反馈是我们需要注意的。

这就好比搭积木,我们无需保证每块积木都是完全可靠的,但是每个积木之间无缝衔接,没有多一点,也没有少一点,而是刚刚好,它们共同构成了一个完整健壮的个体。写程序也是如此:

无需做诸多冗余的保证,只要各层级的代码能够无缝衔接就好

这就是我心中的代码设计理念,大道至简,简单到每个人都能理解。

相关文章

  • 到底怎样写 try-catch,才能称之为高手?

    try-catch,一个大家最常见不过的语法,但是有些人却用不好。当面对一个崩溃的时候,不管三七二十一先catch...

  • Kotlin异常处理(2)捕获异常

    try-catch 语句try-catch 表达式多 catch 代码块try-catch 语句嵌套 一、try-...

  • 到底怎样做才能被称之为爱情?

    有人觉得爱情是陪伴。 有人觉得爱情是浪漫。 有人觉得爱情是忠诚。 还有的人觉得,自私也算是爱情。 我觉得...

  • 如何成为电话销售高手?

    每一个做电话销售的伙伴都想成为电话销售高手,到底如何做才能成为高手呢? 电话销售高手都做对了哪些事情呢? 有一个哥...

  • 刻意地写

    到底怎样写才能更有效果?有人说只要天天写,其他交给天意,我想持这一主张的,如果天天写,也许只能是流畅而已,真正写好...

  • 怎样才能成为SEO高手?搜外师兄成为SEO高手的终极心法

    SEO到底是什么,怎样才能成为SEO高手?下面的内容就是武功终极心法: SEO到底是什么?SEO是技术,是策略,是...

  • 自媒体写作,适者生存

    什么是自媒体写作,我们都在一点点的感知,自媒体写作应该怎样写,才能写得好,怎样写才能能深得要领。 传统文学是作者站...

  • 念影——(1)

    到底什么是父母的爱?到底什么样的喜欢才能称之为爱?到底朋友之间的友情是不是爱?小黎跟许多人一样想不明白。是...

  • 16|错误处理和调试

    try-catch语句的使用 ECMA-262 第 3 版引入了 try-catch 语句,作为 JavaScri...

  • 要成为写作高手,做到这四点就够了

    高手,如何诞生的? 高手的概念,是来自武侠小说,武功很厉害的,被称之为武林高手。武林高手,往往诞生得很容易,一个误...

网友评论

    本文标题:到底怎样写 try-catch,才能称之为高手?

    本文链接:https://www.haomeiwen.com/subject/eljzsctx.html