tags:

views:

78

answers:

3

Can anyone please explain the answer to the following question:

Given a correctly compiled class whose source code is:

 package com.sun.test;
 public class Commander {
  public static void main(String[] args) {
  }
 }

Assume that the class file is located in /foo/com/sun/test/, the current directory is /foo/, and that the classpath contains "." (current directory). Which command line correctly runs Commander?

A. java Commander

B. java com.sun.test.Commander

C. java com/sun/test/Commander

D. java -cp com.sun.test Commander

E. java -cp com/sun/test Commander

+4  A: 

And the best answer would be B. C also works on some platforms but is not recommended and is very uncommon (at least, I've not seen it in over 10 years programming Java).


EDIT

A common misconception with beginners in Java is that a class name is something like "MyClass". But that is not accurate; the nomenclature "MyClass" as seen in the declaration class MyClass is really a convenience for the programmer which the compiler combines with the package declaration to create what Java refers to as a qualified class name, which all class names really are to the runtime. (In C#, they use namespaces for this).

This becomes quite evident in many cases such as stack traces and method signatures which always contain, for example, java.lang.String. Because "String" is just a short form that is resolved to java.lang.String. You can prove this by making your own String in your own package... but beware doing so will require that you explicitly use java.lang.String or my.package.String everywhere that both packages or classes are imported.

Once you assimilate the fact that all class names are fully qualified, and that the compiler helps you avoid tedious work by using imports to resolve short forms to fully qualified forms, things become clearer.

It should then be evident why:

java -cp com/sun/test Commander

doesn't work. The cp option puts the directory ./com/sun/test (relative to the current directory) on the class path, but there is no class named Commander... it's com.sun.test.Commander. This implies two things: (a) the command line requires com.sun.test.Commander and (b) the classpath must contain an entry for the directory which contains "com" in order to resolve this class since a class named x.y.MyClass must be in x/y relative to some classpath element.


PS: You should not be using com.sun as a package name unless you are employed by Sun, since the domain name sun.com belongs to Sun. This convention exists to avoid class packaging and naming collisions.


PPS: There is such a thing as the default package, which is "specified" by omitting the package declaration -- but it should almost never be used. The one legitimate place I have found is with a self-contained "Launcher/Classloader" where it is desired to be able to do:

java -cp . Launcher com.xxx.yyy.TargetApp

with Launcher.class in the current directory... and that is only because JAR files are held locked while the app is running while class files are not, which means that Launcher.class can self-update, while Launcher.jar cannot.

Software Monkey
Thanks Software Monkey. Can you please explain the reason. I think E should also work.
Zacky112
E doesn't work because the class is "com.sun.test.Commander", and it can't pretend to be in the default package (i.e., just "Commander").
Michael Brewer-Davis
+2  A: 

A. Not working, as Java will not found the Commander class

B. Will work, as Java will not found the com.sun.test.Commander class

C. Will work, at least on a Windows plateform. That's why you must use . instead of /.

D and E. They will not work because we still ask Java to search for the class Commander and not com.sun.test.Commander

romaintaz
C will also work at least on Windows
Lauri
You're totally right. I've edited my answer.
romaintaz
+2  A: 

Assuming CLASSPATH environment variable is not set (and thus current working directory is in the classpath by default), the answers are the following:

A. Does not work, there is no Commander class in the default package

B. This one works

C. This one works also, but B is preferred

D. Class path is foo/com.sun.test where there is no Commander class in the default package

E. Class path is foo/com/sun/test where there is no Commander class in the default package

Lauri