【问题标题】:java.lang.Void vs void vs Nulljava.lang.Void vs void vs Null
【发布时间】:2013-03-21 02:05:18
【问题描述】:

Voidvoid 之间到底有什么区别,我可以用null 代替吗?

我问这是因为我正在查看示例 Android 代码,其中他们使用了 Void 但 Eclipse 错误(上面写着Void cannot be resolved to a variable)。

我的代码中断是

public class MyAsyncTask extends AsyncTask<Void, Void, Boolean>{
    ...
}

我是这样用的

MyAsyncTask myAsyncTask = new MyAsyncTask();
myAsyncTask.execute((Void),null);//this is the line that breaks  "Void cannot be resolved to a variable"

【问题讨论】:

  • 如果我们能看到正在破坏的代码会有所帮助。
  • 我要添加一个小sn-p。只是清理它
  • 顺便也可以试试 myAsyncTask.execute(new Void[1]); =D
  • 没有 Null 类型。
  • @shmosel Fair,但虽然技术上不正确,但问题是关于它的,所以我相信它是正确的标题,这就是为什么我批准了编辑但将标题改回原来的 Null

标签: java android null void


【解决方案1】:

Void 最常见的用途是反射,但这并不是唯一可以使用它的地方。

void 是一个关键字,表示函数不会产生值。

java.lang.Void是一个引用类型,那么下面是有效的:

 Void nil = null;

(目前为止还没什么意思……)

作为结果类型(返回值为Void 类型的函数),它意味着函数*总是* 返回null(它不能返回除null 以外的任何内容,因为Void 没有实例)。

 Void function(int a, int b) {
    //do something
    return null;
 }

为什么我想要一个总是返回 null 的函数?

在发明泛型之前,我没有Void 的用例。

对于泛型,有一些有趣的案例。例如,Future&lt;T&gt; 是其他线程执行的异步操作结果的持有者。 Future.get 将返回操作值(T 类型),并且将阻塞直到执行计算。

但是……如果没有什么可以返回怎么办?很简单:使用Future&lt;Void&gt;。例如,在 Google App Engine 中,异步数据存储服务delete 操作返回一个Future&lt;Void&gt;。当在那个未来调用get() 时,null 在删除完成后返回。可以用Callables 写一个类似的例子。

另一个用例是没有值的Map,即Map&lt;T,Void&gt;。这种映射的行为类似于Set&lt;T&gt;,那么当没有Set 的等效实现时它可能很有用(例如,没有WeakHashSet,那么可以使用WeakHashMap&lt;T,Void&gt;)。

【讨论】:

    【解决方案2】:

    Void 是“一个不可实例化的占位符类,用于保存对表示 Java 关键字 void 的 Class 对象的引用。” (来自http://docs.oracle.com/javase/6/docs/api/java/lang/Void.html

    void 是一个返回类型,表示不返回。

    null 是没有值。

    【讨论】:

      【解决方案3】:

      您的代码中有一个额外的逗号。

      myAsyncTask.execute((Void),null);
                              //^extra comma right here
      

      此外,没有必要将 null 转换为 Void,因为 (1) Void 没有实例,因此没有 Void 对象,并且 (2) 将 null 转换为任何东西都是相当没用,因为 null 是任何 Object 数据类型的有效值。

      代码应该只是:

      myAsyncTask.execute(null);
      

      【讨论】:

      • 这是额外的逗号谢谢!我没有意识到它是一个演员(我认为它有两个 args),但由于某种原因它确实必须被演员,否则它会错误地说 execute(void[]) is ambiguous for the type MyAsyncTask
      • 这种情况下最安全的赌注其实是myAsyncTask.execute();
      【解决方案4】:

      java.lang.Voidvoid 类型的框表示。由于您不能拥有 void 类型的实例,因此它主要是为了完整性,而您需要它进行反射的非常罕见的实例。

      【讨论】:

      • java.lang.Void 不是 voidboxed representation。将其称为盒装表示意味着您正在包装一个原语。 void 不是原语,甚至不是类型,也没有发生换行。
      • 一些资源,例如idevelopment.info/data/Programming/java/miscellaneous_java/…,引用void 作为原始类型。这当然不是一堂课。它的全部目的是代表等效目的的原始类型,这就是“盒装表示”实际上所做的。
      • Java Langauge Specification 声明 void 不是类型。
      • 这很有趣。因为当我查看Void 类的代码时,我看到public static final Class&lt;Void&gt; TYPE = (Class&lt;Void&gt;) Class.getPrimitiveClass("void"); 表明 void 被认为是原始类型。
      【解决方案5】:

      void : java 关键字表示方法不会返回任何东西。用于方法

      Void : 围绕 void 进行包装。它扩展了 Object 类。

      需要,因为 Generic 不支持原始数据类型。 (void被认为是原始的是一个复杂的情况,但这只是为了解释)

      应该用于反射

      Constructor<Void> constructor = Void.class.getConstructor()
      

      null 表示没有值。用于对象,与用于方法的 void 进行比较。

      【讨论】:

        猜你喜欢
        • 2021-07-11
        • 1970-01-01
        • 2019-09-21
        • 1970-01-01
        • 2018-07-28
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多