【问题标题】:What is the best way to handle the NullPointerException thrown by Objects.requireNonNull()? [duplicate]处理 Objects.requireNonNull() 抛出的 NullPointerException 的最佳方法是什么? [复制]
【发布时间】:2018-10-18 07:50:35
【问题描述】:

这种方法看起来非常棒,但是,当将它与生产代码一起使用并将它用于可能为空的对象时,它看起来很笨拙。考虑我的例子:

public class ShowDialogTask extends AsyncTask<Void, Void, Void> {
    private WeakReference<Context> contextReference;

    public ShowDialogTask(Context context) {
        contextReference = new WeakReference<>(context);
    }

    @Override
    protected Void doInBackground(Void... voids) {
        ...do a long running task...
        return null;
    }

    @Override
    protected void onPostExecute(Void void) {
        super.onPostExecute(void);
        Context ctx = Objects.requireNonNull(contextReference.get(), "Context became null");
        AlertDialog.Builder builder = new AlertDialog.Builder(ctx);
        builder.setTitle("Dialog title");
        builder.setCancelable(true);
        builder.create().show();
    }

在 onPostExecute() 函数中,我使用 Objects.requireNonNull 方法设置了一个局部变量对象 ctx。我的问题是,让 contextReference.get() 等于 null 对我来说有点难以重现,而且它绝对有可能在生产中发生。

我想知道将此功能用于生产目的的最佳方式。

我的第一个想法是将代码包装在 try-catch 中,但在任何地方都这样做似乎是糟糕的编程:

try {
    Context ctx = Objects.requireNonNull(contextReference.get(), "Context became null");
    AlertDialog.Builder builder = new AlertDialog.Builder(ctx);
    builder.setTitle("Dialog title");
    builder.setCancelable(true);
    builder.create().show();
} catch (Throwable t) {
    Log.d(TAG, t.getMessage());
}

【问题讨论】:

  • requireNonNull 通常用于应该从不为空的东西。不是您期望有时为空的东西。
  • 如果您不知道如何处理它们,则永远不要捕获运行时异常,只有在您可以采取措施时才捕获它们。否则,您将隐藏随着时间的推移而积累的潜在问题,并且当一切停止工作时您将很难解决。
  • @khelwood 谢谢,我相信这就是我想要的澄清。

标签: java android nullpointerexception null


【解决方案1】:

最好的处理方法是什么?一开始就不要扔。

捕获NullPointerException 是您几乎不应该做的事情,除非您正在与编写不佳的 API 进行交互。 NullPointerException 是一个未经检查的异常,意思是它表示一个编程错误:最好修复这个编程错误。

使用条件检查事物是否为空,如果是,则执行不同的操作。

Context ctx = contextReference.get();
if (ctx != null) {
  // Use ctx.
} else {
  Log.d(TAG, "Context became null");
}

总的来说,捕捉Throwable几乎永远不会是正确的做法,因为你可能会捕捉和处理你不打算做的事情,导致你吞咽问题你不知道你必须处理。

【讨论】:

  • 谢谢!这就是我经常处理的方式。我只是对 Objects.requireNonNull 的用例感到好奇。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-09-06
  • 2011-02-18
  • 2010-09-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多