• Java断言(Assertion)


    断言(Assertion)是Java中一条语句,包含一个布尔表达式,当该布尔值为真,程序则被认为是正确的;当布尔值为假,则系统会抛出错误。

    断言默认禁用的,在开发时候可开启功能,有利于纠正错误,增加可维护性。

    PS:断言,换句话就是 立flag,false则啪啪啪打脸。

    断言两种语句形式

    assert Expression1 ;
    assert Expression1 : Expression2 ;

    Expression1是一个布尔表达式,作为断言的真假。

    Expression2是一个有返回值的表达式,用来提供详细的错误信息。

    当没有Expression2时,默认抛出没有详细信息的 AssertionError。

    用断言的场景

    1、变量值明确

    变量值如果很确定是某个值,则可以用断言。

    2、执行不到的语句

    某个地方语句确定是执行不会达到的,例如没有default的switch,则default可加上断言。

    3、前置条件

    前置条件(precondition)是一条语句,在方法执行前必须为真。

    例子:判断线程的拥有锁,结合断言,可以测试当前线程是否拥有某对象的锁。

    private Object[] a;
    public synchronized int find(Object key) {
      return find(key, a, 0, a.length);
    }
    // Recursive helper method - always called with a lock on this.
    private int find(Object key, Object[] arr, int start, int len) {
      assert Thread.holdsLock(this); // lock-status assertion 
      ...
    }

    我觉得前置条件的异常不要用断言为好,无论是public还是private方法。

    4、后置条件

    后置条件(postcondition)是一条语句,当前置条件满足且完全执行方法后,它为真。

    /**
      * Returns a BigInteger whose value is (this-1 mod m).
      *
      * @param  m the modulus.
      * @return this-1 mod m.
      * @throws ArithmeticException  m <= 0, or this BigInteger
      *has no multiplicative inverse mod m (that is, this BigInteger
      *is not relatively prime to m).
      */
    public BigInteger modInverse(BigInteger m) {
      if (m.signum <= 0)
        throw new ArithmeticException("Modulus not positive: " + m);
      ... // Do the computation
      assert this.multiply(result).mod(m).equals(ONE) : this;
      return result;
    }
    View Code

    5、检查类的状态

    加一个内部方法,返回布尔值,当检查类状态正常时返回true。

    不要用断言场景

    1、不要用断言做参数检查

    因为无论断言是启用还是禁用,都必须进行参数检查的,而断言是可能被禁用的。并且断言报出的AssertionError异常,不能准确反馈运行时异常(例如IllegalArgumentException,IndexOutOfBoundsException或NullPointerException)。

    2、不要用断言来完成程序正确操作所需的任何工作

    例如,假设你想要从列表名称中删除所有空元素,并且知道该列表包含一个或多个空值。

    错误的做法:

    //行为包含在断言中
    assert names.remove(null);

    当断言被启用时,程序会正常工作,但在禁用时会失败,因为它不再从列表中删除空元素。

    正确的用法:

    //固定 - 动作先于断言
    boolean nullsRemoved = names.remove(null);
    assert nullsRemoved; //运行是否启用断言

    开启断言

    可在eclipse运行配置中VM arguments,添加-ea。

    参考文献

    https://docs.oracle.com/javase/8/docs/technotes/guides/language/assert.html

  • 相关阅读:
    sql server获取指定库下的所有表名
    sql根据字符将一行拆成多行
    刷题416. Partition Equal Subset Sum
    刷题394. Decode String
    刷题347. Top K Frequent Elements
    刷题309. Best Time to Buy and Sell Stock with Cooldown
    刷题338. Counting Bits
    刷题337. House Robber III
    刷题312. Burst Balloons
    刷题621. Task Scheduler
  • 原文地址:https://www.cnblogs.com/lovesong/p/8921976.html
Copyright © 2020-2023  润新知