这里说一下为什么自定义的包不能以 java.xxx.xx 开头,这是一种安全机制,如果以java开头,则直接异常
private ProtectionDomain preDefineClass(String name,
ProtectionDomain protectionDomain)
{
if (!checkName(name))
throw new NoClassDefFoundError("IllegalName: " + name);
if ((name != null) && name.startsWith("java.")) { // 这里是防止恶意篡改系统中的类
throw new SecurityException("Prohibited package name: " +
name.substring(0, name.lastIndexOf('.')));
}
if (protectionDomain == null) {
protectionDomain = getDefaultDomain();
}
if (name != null)
checkCerts(name, protectionDomain.getCodeSource());
return protectionDomain;
}
如果自己定义了一个 java.lang.String 类,然后执行此类中的方法会出现什么情况 ?
java.lang.NoSuchMethodError: main
Exception in thread "main"
会发出上面的异常,为什么呢?
因为Java的类加载机制造成的,类的加载机制为双亲委派模型,也就是先交给其父亲加载器去加载,如果父亲加载不到,那么再由自己加载
我们自己定义的类一般都由AppClassLoader 进行加载,而它的父亲为ExtclassLoader,而 ExtClassloader的父亲则是 BoostrapClasslader,所以我们自定义的
java.lang.String 最先由 BootStrapClassLoader 加载,而BootStrapLoader 加载器由C++写,它负责加载系统中的类库,而java.lang.string 正是系统中的类,已经被
BootStrapLoader 加载过了,所以不需要再加载 java.lang.String(虽然我们写的与系统中的不是一个,但名字是一样的),所以这样就会免去了加载而直接执行java.lang.String
中的main方法,而系统中的java.lang.string 中没有main 方法,这也就出现了上面的异常