使用反射作为hadoop jar运行的程序抛出java.lang.NoClassDefFoundError

使用反射作为hadoop jar运行的程序抛出java.lang.NoClassDefFoundError,java,hadoop,reflection,jar,Java,Hadoop,Reflection,Jar,我有一个基础和子类。需求是使用反射调用子类的方法。下面是两个程序 base.java import java.io.File; import java.net.URL; import java.net.URLClassLoader; public class base { public static void main(String[] args) { URLClassLoader loader = null; Class<?> cls;

我有一个基础和子类。需求是使用反射调用子类的方法。下面是两个程序

base.java

import java.io.File;
import java.net.URL;
import java.net.URLClassLoader;
public class base {
    public static void main(String[] args) {
        URLClassLoader loader = null;
        Class<?> cls;

        try {
            File file = new File("sub.jar" );
            URL[] urls = { file.toURI().toURL() };
            loader = new URLClassLoader(urls);

            cls = loader.loadClass("sub");
            base obj =  (base) cls.newInstance();

            obj.print();

        }
        catch(Exception e) {
            System.out.println("Exception occured:" + e);
            e.printStackTrace();
        }
    }

    public void print() {
        System.out.println("In Base class");
    }
}

将两者编译到JAR中

javac base.java;
jar cvf base.jar base.class

javac sub.java;
jar cvf sub.jar sub.class
如果我以“java-cp”的形式调用base.jar,它就可以正常工作

java -cp base.jar base 
output: "In subclass"
但是如果我用“hadoopjar”命令调用它,我会得到

hadoop jar base.jar base

Exception in thread "main" java.lang.NoClassDefFoundError: base
        at java.lang.ClassLoader.defineClass1(Native Method)
        at java.lang.ClassLoader.defineClass(ClassLoader.java:763)
        at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142)
        at java.net.URLClassLoader.defineClass(URLClassLoader.java:467)
        at java.net.URLClassLoader.access$100(URLClassLoader.java:73)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:368)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:362)
        at java.security.AccessController.doPrivileged(Native Method)
        at java.net.URLClassLoader.findClass(URLClassLoader.java:361)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
        at base.main(base.java:15)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.lang.reflect.Method.invoke(Method.java:498)
        at org.apache.hadoop.util.RunJar.run(RunJar.java:221)
        at org.apache.hadoop.util.RunJar.main(RunJar.java:136)
Caused by: java.lang.ClassNotFoundException: base
        at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)

非常感谢您的帮助。

我相信您的问题出现在第15行,您试图将加载程序作为基类进行装箱。我相信编译器不知道如何处理这个问题。此外,我不知道为什么要用Hadoop运行这个程序,因为它没有任何Hadoop实现或类

将base.jar放在Hadoop类路径中就可以解决这个问题。运行“hadoop类路径”命令,该命令列出所有类路径目录。将jar放在其中一个目录中

Marty,我把我的程序简化为没有hadoop类的简单代码只是为了演示
hadoop jar base.jar base

Exception in thread "main" java.lang.NoClassDefFoundError: base
        at java.lang.ClassLoader.defineClass1(Native Method)
        at java.lang.ClassLoader.defineClass(ClassLoader.java:763)
        at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142)
        at java.net.URLClassLoader.defineClass(URLClassLoader.java:467)
        at java.net.URLClassLoader.access$100(URLClassLoader.java:73)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:368)
        at java.net.URLClassLoader$1.run(URLClassLoader.java:362)
        at java.security.AccessController.doPrivileged(Native Method)
        at java.net.URLClassLoader.findClass(URLClassLoader.java:361)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
        at base.main(base.java:15)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.lang.reflect.Method.invoke(Method.java:498)
        at org.apache.hadoop.util.RunJar.run(RunJar.java:221)
        at org.apache.hadoop.util.RunJar.main(RunJar.java:136)
Caused by: java.lang.ClassNotFoundException: base
        at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)