Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

When will two classes considered same? Like, is there something acting as the signature of a class? If so, what counts in the signature, package info, class name, etc? I'm asking this because I need to dynamically load a class and I always got a ClassNotFoundException

A bit more detail: I'm using Eclipse. I have an abstract class Panel in my package com.example.project.sub1. And a class Test in package com.example.project.sub2, which will call

ClassLoader loader = new URLClassLoader(
        new URL[]{new URL("file://" + path)});
                /*the path is specified runtime and can be in a different
                  directory other than working directory. It's the path 
                  to the parent directory of the class file I need to load.
                */
Class<Panel;> panelClass = (Class<Panel;>)loader.loadClass(className);
                //class name is runtime specified.

That compiles fine. Then I copied all the stuff in Panel.java in a new directory and created a class MyPanel extends Panel along with Panel.java. That compiles fine too, but when I specify the path to my new MyPanel.class, I always got a ClassNotFoundException. Any idea where I'm wrong? Thanks.

EDIT: The stack trace:

java.lang.ClassNotFoundException: MyPanel
    at java.net.URLClassLoader$1.run(URLClassLoader.java:202)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:306)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:247)
    at com.example.project.sub2 (Test.java:111)
    at java.lang.Thread.run(Thread.java:680)
share|improve this question
    
Most likely the file is just in the wrong location. Can you show all paths involved? And the whole exception? –  Thilo Jul 17 '13 at 6:02
    
@Thilo I used a JFileChooser to locate the file, so I assume the path is correct? I'm including the stack trace in a minute, though at first sight it's not helpful. –  YankeeWhiskey Jul 17 '13 at 6:05
1  
It is helpful ;-) It shows that you use the wrong class name (package is missing). –  Thilo Jul 17 '13 at 6:08

2 Answers 2

up vote 1 down vote accepted

If you want to dynamically load the class com.example.project.sub1.Panel from a file URL, then this URL should refer to the directory containing the directory com. From there, the ClassLoader will look for the class in a subdirectory path matching the package path. And the class name to pass is the fully qualified name: com.example.project.sub1.Panel.

Also, loding the class MyPanel will return a Class<MyPanel>, not a Class<Panel>. You should use Class<? extends Panel> as the type of the variable.

I'm not sure why you're dynamically loading classes though. The actual problem you're trying to solve is probably solvable in another way.

share|improve this answer
    
I'm writing an extendable application so users can provide their own subclass of Panel after I ship the application and plug in their own Panel. Other better way to achieve that? –  YankeeWhiskey Jul 17 '13 at 6:15
1  
Yes: let them put their own directories/jars in the classpath and configure the application using some config file. Then load the class by name, using Class.forName(), for example. Messing with several class loaders is not an easy task. And if the users are savvy enough to write and compile Java code, they should be savvy enough to configure and start the application. –  JB Nizet Jul 17 '13 at 6:19
    
I'm trying to understand what you are talking since I'm a bit inexperienced in this. So you mean if the user compiles, say, TheirPanel.class and put it in the classpath, I'm able to find it using Class.forName? Also I assume I need to provide my abstract Panel's source code as a blueprint, then do I also need to include the package info? –  YankeeWhiskey Jul 17 '13 at 6:23
1  
That's how all the libraries (jar files) you're using work: the vendor of the library provides a jar file containing classes. It also provides the javadoc. The developer using this library puts the jar in the build and runtime classpath and uses the documentation to develop his app using the library. Having the source code of the library can be useful, but is not necessary if the javadoc is exhaustive. In this case, you're the developer of a library, and you provide this library to other developers. If the developers put their classes in the classpath, your library can use Class.forName(). –  JB Nizet Jul 17 '13 at 6:29

java.lang.ClassNotFoundException: MyPanel

The class is not called "MyPanel", it is "com.example.project.sub1.MyPanel".

It's the path to the parent directory of the class file I need to load.

Yes, that won't work. It needs to be the directory at the root of the package hierarchy, so not "/some/path/classes/com/example/project/sub1/", but "/some/path/classes"

share|improve this answer
    
So if I don't specify the package info in the GamePanel.java and MyPanel.javain my new directory, will this MyPanel.class be considered as the subclass of GamePanel.class in my original package? Thanks. –  YankeeWhiskey Jul 17 '13 at 6:13

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.