Java packages and compilation (why, not how)

I am working on some Java code in eclipse. The code is contained in a single class called Adder , which in Eclipse is in the org.processing package. The first thing in the class file is the line

 package org.processing 

Q1) What exactly is happening on this line? Why is there, what is this role.

The code works fine in eclipse, however, when I go to the workspace, if I go to the src/org/processing/ folder in src , compile with javac Adder.class , when I try to start using java Adder , I get the following error

java.lang.NoClassDefFoundError: Adder (wrong name: org/processing/Adder)

On the other hand, if I compile src using

 javac org/processing/Adder.java 

and I can run it from src using java org.processing.Adder , but STILL is not from inside the processing directory.

Q2) Does this mean that compilation always refers to the directory structure?

Finally, if I delete the package org.processing line from the beginning, this is a .class file that I can compile and run from the .class file directory.

Q3) Why is all this so? I can fully understand how to provide a directory structure for code development, but as soon as you get into the bytecode, it seems a little higher, because now I can (apparently) run the bytecode from only one director ( src ), using java org.processing.Adder . Now, I'm sure I miss the point here, so if someone can specify what it is, that would be great.

+4
source share
4 answers

The short answer is, Packages help keep the project structure well organized, allow you to reuse names (try having two classes named Account ) and are a common convention for large projects very much . They are nothing more than folder structures, but why they are used can burn newbies pretty badly. Oddly enough, with a project of less than 5 classes, you probably will not need this.


What exactly does this line do? Why is there, what is this role.

Line

 package org.processing 

tells Java that this class file lives in a folder named / org / processing. . This allows you to have a class that is fully defined as org.processing.Processor here, and in another folder - let's say / org / account / processing , you can have a class that is fully defined as org.account.processing.Processor . Yes, both use the same name, but they will not collide - they are in different packages. If you decide to use them in the same class, you will need to specify which one you want to use, either using either the import statements or the full name of the object.

Does this mean that compilation always refers to the directory structure?

Yes. Java and most other languages ​​have a concept known as a class path. Any of this class of the path can be compiled and launched, and by default the current directory in which you are located is in the class path for compilation and execution. To put other files in the classpath, you will have to use a different command line call for your compilation:

 javac -sourcepath /path/to/source MainClass.java 

... and this will compile everything in your source path into your current directory, neatly organized in the folder structure specified by your package operators.

To start them, as you already installed, you will need to include the compiled source in your classpath, and then execute through the fully qualified name of the object:

 java -cp /path/to/source org.main.MainClass 

Why is all this so?

As I said, this is mainly useful for very large projects or projects that include many other classes and a demand / organization structure, such as Android. He does a few things:

  • Keeps the source in a simple structure. You have no objects scattered everywhere.
  • Keeps the scope of your objects. If I had a package called org.music.db , it’s pretty clear that I was messing around with objects that deal with database and persistence. If I had a package called org.music.gui , then he realized that this package deals with the presentation side. This can help when you want to create a new function or update / reorganize an existing one; you can remember what he does, but you cannot name him exactly.
  • It allows you to have objects with the same name. There is more than one type of Map , and if you use projects that draw this in, you would like to specify which Map you will receive - again, by either importing or the full name of the object.
+1
source

The compiler should be able to find related source code files during compilation. This is why the structure of the package and directories must match the source code. Similarly, the JVM should be able to find .class referenced files. Thus, the same directory structure is required at runtime. It is no harder than that.

+2
source

Q1) The problem is that after you get to the folders representing the package hierarchy, you set this as the working directory. It will look inside org / processing / Adder for the path org / processing / Adder (mainly from the root for org / processing / Adder / org / processing / Adder). You must call it from the root with the full path. The goal of packages is: organize related classes into groups. And B: Along with A, classes in the Foo.bar package cannot view private classes in other packages, since they are similar to the inner classes for this package, only the packages in which they are located can use them.

Q2) Yes

Q3) Paths are used as the base structure for the JVM to know exactly where the class files are located (each of which contains their bytecode). If you change your name, basically try to change the location of the JVM to search for class files, but their true location has not changed.

+2
source

In Q1: declaring a package ensures that your class will never be mistaken for another class with the same name. This is why most programmers put their brand name in a package; this is unlikely to lead to conflict.

For Q2: there is a one-to-one correspondence between the package structure and the directory structure. In short, directories and packages should be the same, except that the package is usually rooted under the src folder.

In Q3: after compilation, class files are likely to be located in the appropriate folders in the jar file. Your ant or maven tasks will create a jar file, so you don’t have to worry about this before you install the ant task for the first time.

+1
source

All Articles