Java 为什么JDK中存在Void包装器类?
可能重复:Java 为什么JDK中存在Void包装器类?,java,void,Java,Void,可能重复: Void类在现实问题中的实际用途是什么?在哪种情况下可以使用此类?Void类用于Java反射。 请参见如果您有一个对象(如ExecutorService)要求您提供一个可调用的对象,您可以向它传递一个可调用的,以指示您的可调用对象不返回任何内容Callable必须在某些类型上参数化,因此提供了Void来表示缺少类型。-不同于其他包装Void类本身不存储类型Void的值,因此本质上不是包装器 -根据javadoc存在Void类,因为有时我们可能需要将Void关键字表示为对象 -但在同
Void
类在现实问题中的实际用途是什么?在哪种情况下可以使用此类?Void
类用于Java反射。请参见如果您有一个对象(如
ExecutorService
)要求您提供一个可调用的
对象,您可以向它传递一个可调用的
,以指示您的可调用对象不返回任何内容Callable
必须在某些类型上参数化,因此提供了Void
来表示缺少类型。-不同于其他包装Void
类本身不存储类型Void
的值,因此本质上不是包装器
-根据javadoc存在Void
类,因为有时我们可能需要将Void关键字表示为对象
-但在同一点上,我们无法使用新运算符创建Void类的实例。这是因为Void中的构造函数已声明为private。
此外,Void类是最后一个类,这意味着我们无法继承这个类
-因此
Void
类存在的唯一目的是反射,在这里我们可以将方法的返回类型作为Void。java反射API使用Void.type来表示Luke Woodward指出的返回Void的方法的返回类型。(返回Void.class,正如我之前认为的那样,将导致返回声明java.lang.Void返回类型的方法不明确)
后java 1.5 Void可以在泛型类中使用,以指示它们不返回值-实现仍然必须返回null,但可以忽略它,因为这是Void类型的唯一有效值
interface<T> Example{
//Implementations may do something and return a result
T doSomeThing();
}
class ExampleVoid implements Example<Void>{
//does something without returning a result
Void doSomething(){return null;}
}
<> P>与C和C++不同,java编程语言只允许某些形式的表达式用作表达式语句。请注意,Java编程语言不允许“强制转换为void”void不是类型,因此编写表达式语句的传统C技巧如下:
不起作用。另一方面,Java编程语言允许在表达式语句中使用所有最有用的表达式,并且它不需要作为表达式语句调用void方法的方法调用,因此几乎不需要这种技巧。如果需要技巧,可以使用赋值语句(§15.26)或局部变量声明语句(§14.4)
void.class(§8.4.5)的类型为class
方法声明的结果要么声明该方法返回的值的类型(返回类型),要么使用关键字void指示该方法不返回值
Void类是一个不可实例化的占位符类,用于保存对表示Java关键字Void的类对象的引用
当您想要检查方法的返回类型时,它用于反射目的
if (getClass().getMethod("someMethod").getReturnType() == Void.TYPE)
这同样适用于一般方法
final Callable<Void> callable = new Callable<Void>() {
public Void call() {
return null;
}
};
final Callable Callable=new Callable(){
公开作废通知(){
返回null;
}
};
原因
引入该类型是为了允许回调和与外部系统的接口(JNI、来自applet的JavaScript调用等),并且从Java1.1时代起就一直存在于接口类型未知或其他接口无法强制执行的情况下(因此无法使用)。Java被设计为一种“一切都是对象”的语言,除了原语和空引用之外,还需要一个虚拟包装器/占位符来表示缺少预期的类型
定义
JLS()一节定义的方法必须在返回类型时正式声明:
方法声明的结果声明值的类型
方法返回(返回类型),或使用关键字void
来
指示该方法不返回值
如()的JLS部分所述:
void.class
()的类型是class
一般用途
随着Java 5中泛型的引入,它的使用变得更加突出,因为它允许这些接口的定义使用泛型,并允许对这些接口和回调的使用进行类型检查。以前,实现者有时会知道没有传递对象或没有返回对象,例如,在使用特权执行块的情况下,小程序中经常使用来定义安全代码路径:
somemethod() {
// ...normal code here...
AccessController.doPrivileged(new PrivilegedAction<Void>() {
public Void run() {
// privileged code goes here, for example:
System.loadLibrary("awt");
return null; // nothing to return
}
});
// ...normal code here...
}
进一步阅读和类似问题
List
可以用作一个空间效率非常低的计数器:-)您是对的。java中的list
。。。notList
。可以创建Void
类的实例,使用一些反射性黑客。Java反射API使用Void.class
作为Void
方法的返回类型,而不是Void.class
。在您的第一个示例中,断言将失败。@LukeWoodward谢谢,我更新了我的答案
if (getClass().getMethod("someMethod").getReturnType() == Void.TYPE)
final Callable<Void> callable = new Callable<Void>() {
public Void call() {
return null;
}
};
somemethod() {
// ...normal code here...
AccessController.doPrivileged(new PrivilegedAction<Void>() {
public Void run() {
// privileged code goes here, for example:
System.loadLibrary("awt");
return null; // nothing to return
}
});
// ...normal code here...
}
somemethod() {
// ...normal code here...
AccessController.doPrivileged(new PrivilegedAction() {
public Object run() {
// privileged code goes here, for example:
System.loadLibrary("awt");
return null; // nothing to return
}
});
// ...normal code here...
}