2012-10-30 23 views
1

为什么java不会阻止你实例化任何单例类对象?为什么我可以使用反射创建一个以上的单例实例?

我试图创建太虚类

java.lang.Void 

的对象我写了这个代码来创建两个实例

try{ 
    Class clazz = Void.class; 
    Constructor cons = clazz.getDeclaredConstructor(); 
    cons.setAccessible(true); 
    Void s2 = (Void) cons.newInstance(); 
    System.out.println(s2); 
    Void s3 = (Void) cons.newInstance(); 
    System.out.println(s3); 

}catch (Exception e) { 
    e.printStackTrace(); 
} 

任何人都可以解释 - 为什么这是允许在java吗?

+2

使用Singleton模式并不能保存您通过'Reflection'创建的实例。你可以使用'Reflection'来访问私人领域和构造函数。所以,它不是'Java'允许的。它的Reflection API违反了规则。 –

+0

'Void'不是单例,顺便说一下,它的意图是有_no_实例,因为它的目的仅仅是作为'Void.TYPE'的容器,符合其他基本类型'Class'对象'int'的Integer.TYPE等)。 –

回答

5

使用这样的反射可以避开正常的保护机制,并执行像调用私有构造函数和通常无法访问的方法之类的东西。 Java不允许你在没有调用setAccessible的情况下通过私有构造函数实例化一个类 - 实质上这意味着“我知道我不应该这样做,但是......”

如果你需要运行不可信代码,那么您可以使用SecurityManager机制来禁止这种“违规”。

2

因为Java无法知道您希望该类用作单例。如果你想要这样一个类,使用枚举。

相关问题