Java: Out with the Old, In with the New - java

Java is nearing version 7. It occurs to me that there must be plenty of textbooks and training manuals kicking around that teach methods based on older versions of Java, where the methods taught, would have far better solutions now.
What are some boilerplate code situations, especially ones that you see people implement through force of habit, that you find yourself refactoring to utilize the latest versions of Java?

Enums. Replacing
public static final int CLUBS = 0;
public static final int DIAMONDS = 1;
public static final int HEARTS = 2;
public static final int SPADES = 3;
with
public enum Suit {
CLUBS,
DIAMONDS,
HEARTS,
SPADES
}

Generics and no longer needing to create an iterator to go through all elements in a collection. The new version is much better, easier to use, and easier to understand.
EDIT:
Before:
List l = someList;
Iterator i = l.getIterator();
while (i.hasNext()) {
MyObject o = (MyObject)i.next();
}
After
List<MyObject> l = someList;
for (MyObject o : l) {
//do something
}

Using local variables of type StringBuffer to perform string concatenation. Unless synchronization is required, it is now recommended to use StringBuilder instead, because this class offers better performance (presumably because it is unsynchronized).

reading a string from standard input:
Java pre-5:
try {
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
String str = reader.readLine();
reader.close();
}
catch (IOException e) {
System.err.println("error when closing input stream.");
}
Java 5:
Scanner reader = new Scanner(System.in);
String str = reader.nextLine();
reader.close();
Java 6:
Console reader = System.console();
String str = reader.readLine();

Older code using Thread instead of the many other alternatives to Thread... these days, very little of the code I run across still needs to use a raw thread. They would be better served by a level of abstraction, particular Callable/Futures/Executors.
See:
java.util.Timer
javax.swing.Timer
java.util.concurrent.*

Here is one that I see:
String.split() versus StringTokenizer.
StringTokenizer is not recommended for new code, but I still see people use it.
As for compatibility, Sun makes a huge effort to have Java be backwards and forwards compatible. That partially accounts for why generics are so complex. Deprecation is also supposed to help ease transitions from old to new code.

VARARGS can be useful too.
For example, you can use:
public int add(int... numbers){
int sum = 0 ;
for (int i : numbers){
sum+=i;
}
return sum ;
}
instead of:
public int add(int n1, int n2, int n3, int n4) ;
or
public int add(List<Integer> numbers) ;

Using local variables of type Vector to hold a list of objects. Unless synchronization is required, it is now recommended to use a List implementation such as ArrayList instead, because this class offers better performance (because it is unsynchronized).

Formatted printing was introduced as late as in JDK 1.5. So instead of using:
String str = "test " + intValue + " test " + doubleValue;
or the equivalent using a StringBuilder,
one can use
String str = String.format("test %d test %lg", intValue, doubleValue);
The latter is much more readable, both from the string concatenation and the string builder versions. Still I find that people adopt this style very slowly. Log4j framework for example, doesn't use this, although I believe it would be greatly benefited to do so.

Explicit conversion between primitive and wrapper types (e.g. Integer to int or vice versa) which is taken care of automatically by autoboxing/unboxing since Java 1.5.
An example is
Integer myInteger = 6;
int myInt = myInteger.intValue();
Can simply be written as
Integer myInteger = 6;
int myInt = myInteger;
But watch out for NullPointerExceptions :)

Q1: Well, the most obvious situations are in the generics / type specific collections. The other one that immediately springs to mind is the improved for loop, which I feel is a lot cleaner looking and easier to understand.
Q2: In general, I have been bundling the JVM along side of my application for customer-facing apps. This allows us to use new language features without having to worry about JVM incompatibility.
If I were not bundling the JRE, I would probably stick to 1.4 for compatibility reasons.

A simple change in since 1.5 but makes a small difference - in the Swing API accessing the contentPane of a JFrame:
myframe.getContentPane().add(mycomponent);
becomes
myframe.add(mycomponent);
And of course the introduction of Enums has changed the way many applications that used constants in the past behave.
String.format() has greatly improved String manipulation and the ternary if statement is quite helpful in making code easier to read.

Generic collections make coding much more bug-resistant.
OLD:
Vector stringVector = new Vector();
stringVector.add("hi");
stringVector.add(528); // oops!
stringVector.add(new Whatzit()); // Oh my, could spell trouble later on!
NEW:
ArrayList<String> stringList = new ArrayList<String>();
stringList.add("hello again");
stringList.add(new Whatzit()); // Won't compile!

Using Iterator:
List list = getTheList();
Iterator iter = list.iterator()
while (iter.hasNext()) {
String s = (String) iter.next();
// .. do something
}
Or an alternate form sometimes seen:
List list = getTheList();
for (Iterator iter = list.iterator(); iter.hasNext();) {
String s = (String) iter.next();
// .. do something
}
Is now all replaced with:
List<String> list = getTheList();
for (String s : list) {
// .. do something
}

Although I admit that static imports can easily be overused, I like to use
import static Math.* ;
in classes that use a lot of Math functions. It can really decrease the verbosity of your code. I wouldn't recommend it for lesser-known libraries, though, since that can lead to confusion.

copying an existing array to a new array:
pre-Java 5:
int[] src = new int[] {1, 2, 3, 4, 5};
int[] dest = new int[src.length];
System.arraycopy(src, 0, dest, 0, src.length);
Java 6:
int[] src = new int[] {1, 2, 3, 4, 5};
int[] dest = Arrays.copyOf(src, src.length);
formerly, I had to explicitly create a new array and then copy the source elements to the new array (calling a method with a lot of parameters). now, the syntax is cleaner and the new array is returned from a method, I don't have to create it. by the way, the method Arrays.copyOf has a variation called Arrays.copyOfRange, which copies a specific region of the source array (pretty much like System.arraycopy).

Converting a number to a String:
String s = n + "";
In this case I think there has always been a better way of doing this:
String s = String.valueOf(n);

The new for-each construct to iterate over arrays and collection are the biggest for me.
These days, when ever I see the boilerplate for loop to iterate over an array one-by-one using an index variable, it makes me want to scream:
// AGGHHH!!!
int[] array = new int[] {0, 1, 2, 3, 4};
for (int i = 0; i < array.length; i++)
{
// Do something...
}
Replacing the above with the for construct introduced in Java 5:
// Nice and clean.
int[] array = new int[] {0, 1, 2, 3, 4};
for (int n : array)
{
// Do something...
}
Clean, concise, and best of all, it gives meaning to the code rather than showing how to do something.
Clearly, the code has meaning to iterate over the collection, rather than the old for loop saying how to iterate over an array.
Furthermore, as each element is processed independent of other elements, it may allow for future optimizations for parallel processing without having to make changes to the code. (Just speculation, of course.)

Related to varargs; the utility method Arrays.asList() which, starting from Java 5, takes varargs parameters is immensely useful.
I often find myself simplifying something like
List<String> items = new ArrayList<String>();
items.add("one");
items.add("two");
items.add("three");
handleItems(items);
by using
handleItems(Arrays.asList("one", "two", "three"));

Annotations
I wonder no one mentioned it so far, but many frameworks rely on annotations, for example Spring and Hibernate. It is common today to deprecate xml configuration files are in favor of annotations in code (though this means losing flexibility in moving from configuration to meta-code, but is often the right choice).The best example is EJB 2 (and older) compared to EJB 3.0 and how programming EJB has been simplified thanks to annotations.
I find annotations also very useful in combination with some AOP tools like AspectJ or Spring AOP. Such combination can be very powerful.

Changing JUnit 3-style tests:
class Test extends TestCase {
public void testYadaYada() { ... }
}
to JUnit 4-style tests:
class Test {
#Test public void yadaYada() { ... }
}

Improved singleton patterns. Technically these are covered under the popular answer enums, but it's a significant subcategory.
public enum Singleton {
INSTANCE;
public void someMethod() {
...
}
}
is cleaner and safer than
public class Singleton {
public static final Singleton INSTANCE = new Singleton();
private Singleton() {
...
}
public void someMethod() {
...
}
}

Converting classes to use generics, thereby avoiding situations with unnecessary casts.

Okay, now it's my turn to get yelled at.
I don't recommend 90% of these changes.
It's not that it's not a good idea to use them with new code, but breaking into existing code to change a for loop to a for(:) loop is simply a waste of time and a chance to break something. (IIWDFWI) If it works, don't fix it!
If you are at a real development company, that change now becomes something to code-review, test and possibly debug.
If someone doing this kind of a refactor for no reason caused a problem of ANY sort, I'd give them no end of shit.
On the other hand, if you're in the code and changing stuff on that line anyway, feel free to clean it up.
Also, all the suggestions in the name of "Performance" really need to learn about the laws of optimization. In two words, Don't! Ever! (Google the "Rules of optimization if you don't believe me).

I'm a little wary to refactor along these lines if that is all you are doing to your source tree. The examples so far do not seem like reasons alone to change any working code base, but maybe if you are adding new functionality you should take advantage of all the new stuff.
At the end of the day, these example are not really removing boiler plate code, they are just using the more manageable constructs of newer JDKs to make nice looking boiler plate code.
Most ways to make your code elegant are not in the JDK.

Using Swing's new DefaultRowSorter to sort tables versus rolling your own from scratch.

New version of Java rarely break existing code, so just leave old code alone and focus on how the new feature makes your life easier.
If you just leave old code alone, then writing new code using new features isn't as scary.

String comparisons, really old school Java programmers I've met would do:
String s1 = "...", s2 = "...";
if (s1.intern() == s2.intern()) {
....
}
(Supposedly for performance reasons)
Whereas these days most people just do:
String s1 = "...", s2 = "...";
if (s1.equals(s2)) {
....
}

Using Vector instead of the new Collections.
Using classes instead of enums
public class Enum
{
public static final Enum FOO = new Enum();
public static final Enum BAR = new Enum();
}
Using Thread instead of the new java.util.concurrency package.
Using marker interfaces instead of annotations

It is worth noting that Java 5.0 has been out for five years now and there have only been minor changes since then. You would have to be working on very old code to be still refactoring it.

Related

SonarQube-compliant solution, increment cell value

I am using Apache POI to create a excel form a Java POJO class.
The POJO has 65 fields which needs to be populated while creating a POJO.
One way I figured out was -
int i = 0;
hssfRow.createCell(i++).setCellValue(POJO.getField1());
hssfRow.createCell(i++).setCellValue(POJO.getField2());
hssfRow.createCell(i++).setCellValue(POJO.getField3());
.....
hssfRow.createCell(i++).setCellValue(POJO.getField65());
The drawback of the above approach is SonarQube says it is non compliant with the following reason
Extract this increment or decrement operator into a dedicated
statement
The first question is why is it not advised to use i++ here?
Also, is it advisable to declare constant from 1 to 65 in a separate Constant class and use it instead of i++ (i.e. hssfRow.createCell(Constant.ONE))?
And is there any alternative to this solution which is compliant and is a better approach?
I could be like this:
private static final Map<Integer, Function<POJO, TypeOfCellValue>> cellDataProviders = new HashMap<>();
static{
cellDataProviders.put(1, POJO -> POJO.getField1());
cellDataProviders.put(2, POJO -> POJO.getField2());
...
}
And use in code:
IntStream.range(1, cellDataProviders.size()).foreach( i -> hssfRow.createCell(i).setCellValue(cellDataProviders.get(i).apply(POJO)));
or with use of traditional for loop:
for(int i = 0; i < cellDataProviders.size(); i++){
hssfRow.createCell(i).setCellValue(cellDataProviders.get(i).apply(POJO));
}
the mapping from POJO to cell has been separated from the data population code.
IMHO, you can mark it as a false positive. The stated reasons for the issue are
It can significantly impair the readability of the code.
It introduces additional side effects into a statement, with the potential for undefined behavior.
It is safer to use these operators in isolation from any other arithmetic operators.
Given the circumstances of your current code, I'd say they are invalid. The code is perfectly readable as it is and there's no undefined behavior possible and I don't see any safety concern there.
As it is a false positive you can use #SuppressWarnings("squid:S...") or //NOSONAR:
//NOSONAR
hssfRow.createCell(i++).setCellValue(POJO.getField1());
//NOSONAR
hssfRow.createCell(i++).setCellValue(POJO.getField2());
//NOSONAR
hssfRow.createCell(i++).setCellValue(POJO.getField3());
...
However then it is more clear to slavely change the code to:
hssfRow.createCell(i).setCellValue(POJO.getField1()); ++i;
hssfRow.createCell(i).setCellValue(POJO.getField2()); ++i;
hssfRow.createCell(i).setCellValue(POJO.getField3()); ++i;
...
Does not hurt.
Playtime
One could hide the index using a vararg method.
Assuming the POJO object variable is pojo and its class Pojo.
fillCells(hssfRow, pojo,
Pojo::getField1,
Pojo::getField2,
p -> createDateCellValue(p.getField2()),
Pojo::getField4,
Pojo::getField5,
p -> f(pojo),
Pojo::getField7):
void fillCells(Row hssfRow, Pojo pojo, Function<Pojo, CellValue>... cellProviders) {
for (int i = 0; i < cellProviders.length; ++i) {
hssfRow.createCell(i).setCellValue(cellProviders[i].apply(pojo));
}
}
This is not as flexible, but would remove some repetitive hssfRow.createCell.

How to create an array depending on an argument in a clear and readable way?

Here is my problem :
I want to create an array in a very clear and readable way, so that the reader can instantly know the elements of the array.
When the array is fixed, then it is easy and very clear :
String[] columns = new String[] { "unit", "file_row", "unit_row", "content" };
String[] types = new String[] { "INTEGER", "INTEGER", "INTEGER", "TEXT" };
But I also have variable arrays, depending on an argument :
// Is an argument of my method, containing the variable elements of the future array
String[] method_arg = new String[] {"key1", "key2"};
// The clear and readable way doesn't work anymore
String[] columns = new String[] { "unit", method_arg, "hash"};
String[] types = new String[] { "INTEGER", method_arg_types, "INTEGER"};
// And the ways that work are ... much less readable
String[] columns = new String[] {"unit"};
columns = Stream.concat(Arrays.stream(columns), Arrays.stream(method_arg)).toArray(String[]::new);
columns = Stream.concat(Arrays.stream(columns), Arrays.stream(new String[] {"hash"})).toArray(String[]::new);
// Awkward
String[] types = new String[method_arg.length + 2];
Arrays.fill(types, "TEXT");
types[0] = "INTEGER";
How do you make it so that the code stay clear and readable ?
The code is rather flexible, using lists should not be a problem, I'd prefer to avoid using non standard libraries though.
Also, I know a solution would be to create a method to create those arrays, like
join_arrays(new String[] {"unit"}, method_arg, new String[] {"hash"});
But if there are solutions making the code clear and avoiding the creation of a dedicated function, it would be better. If not I will fall back on this option.
Thank you, have a nice day !
I usually end up using a custom method for this sort of problem:
private <T> T[] makeArray(T... elements) {
return elements;
}
Your example would look like:
String[] columns = makeArray("unit", method_arg, "hash");
String[] types = makeArray("INTEGER", method_arg_types, "INTEGER");
I think you misinterpret the clarity and readability of code. First of all, you are completely RIGHT that clarity and readability of code are of the highest value. However, it doesn't mean that a reader should see immediately the outcome of the code - in your case the contents of the array. It means that the reader can clearly see first - WHAT the code does and second - HOW it does it. There are many ways to insure clarity.
Break your longer methods to shorter ones preferably 4 - 5 lines but at the most no longer than 10 - 15. Make sure that each method deals only with a single logically indivisible issue.
Make sure that method name is informative
The number of parameters is kept to a minimum (0 - 3)
The names and order of parameters are meaningful.
Return value matches the purpose of the method.
This, of course, is not a full list.
Java has an easier way for this, which is imho a little bit easier and is compiled away :-)
Example usage, similar to other suggestion:
private static void method(String method_arg, String method_arg_types) {
String[] columns = array("INTEGER", method_arg, "INTEGER");
String[] types = array("INTEGER", method_arg_types, "INTEGER");
}
The implementation is far easier, as a side effect of how var-args are implemented.
#SafeVarargs
public static <T> T[] array(T... values) {
return values;
}
Its also implemented in org.assertj.core.util, it should be part of the JDK imho :-)

Connect multiple strings efficiently

I've got an interface IO, that offers two methods, void in(String in) and String out(). I've implemented that in a first, naive, version:
private String tmp="";
public void in(String in){
tmp=tmp+in;
}
public String out(){
return tmp;
}
I know this is an horrible implementation, if you have multiple, very long Strings. You need make a new String with length = tmp.length+in.length, copy tmp, copy in. And then repeat that again for evey inserted String. But what is an better implementation for that?
private List<String> tmp= new ArrayList<>() //maybe use an different list?
public void in(String in){
tmp.add(in);
}
public String out(){
return connect(tmp);
}
private String connect(List<String> l){
if(l.size()==1) return l.get(0);
List<String> half = new ArrayList<>();
for(int i=0;i<l.size();i+=2){
half.add(l.get(i)+l.get(i+1)); \\I have to check, if i+1 is valid, but this is just a draft ;)
}
return connect(half);
}
This is a bit better, it has to make the same number of String-connections, but the Strings are going to be smaller by averange. But it has an giant offset, and i'm not sure it's worth it. There schould be an easier option than this imho, too...
You may be looking for a StringBuilder.
private StringBuilder tmp = new StringBuilder();
public void in(String in) {
tmp.append(in);
}
public String out() {
return tmp.toString();
}
The standard library provides a class specifically for efficient string concatenation, the StringBuilder:
https://docs.oracle.com/javase/7/docs/api/java/lang/StringBuilder.html
Note that the compiler will actually desugar your string "additions" into expressions involving StringBuilders, and in a lot of simple/naïve cases it will also optimize the code to make use of the append() method instead of constantly creating new StringBuilders. In your case, however, it is definitely a good idea to explicitly use a StringBuilder.
As for your adventurous attempt at optimizing the concatenation, I honestly don't think you will notice any improvements over the naïve solution, and clean code is always preferable to "slightly faster code", unless clock cycles are extremely expensive.
From Java Doc:
If your text can change and will only be accessed from a single
thread, use a StringBuilder because StringBuilder is unsynchronized.
If your text can changes, and will be accessed from multiple threads,
use a StringBuffer because StringBuffer is synchronous.
In your case StringBuilder will work just fine.
The StringBuilder class should generally be used in preference to this
one, as it supports all of the same operations but it is faster, as it
performs no synchronization.
http://download.oracle.com/javase/6/docs/api/java/lang/StringBuffer.html

Is it a bad practice to use arrays as parameter(s) to return multiple values

I sometimes (actually, often) find myself using a one-element array to return multiple values from a method. Something like this:
public static int foo(int param1, int param2[], String param3[])
{
// method body
....
// set return values
param2[0] = <some value>;
param3[0] = <some value>;
return <some value>;
}
Is this a bad practice? (It seems like it is because some of my friends said they didn't know what it was doing for 2 seconds!)
But the reason I used this in the first place was because this looked closest to what is know as pass-by-reference in C++. And the practice wasn't discouraged in C++, so ...
But if this is really a wrong way of doing things, any idea how to rewrite this in the clean way?
Thanks
Create an object that contains the data you want to return.
Then you can return an instance of that object.
class FooData {
private int someInt;
private int anotherInt;
private String someString;
public FooData(int a, int b, String c) {
someInt = a;
anotherInt = b;
someString = c;
}
}
public FooData foo() {
// do stuff
FooData fd = new FooData(blah, blahh, blahhh);
return fd;
}
While I agree with the general opinion here that using arrays for such a purpose is bad practice, I'd like to add a few things.
Are you sure that "pass by reference" really is what you need in the first place?
Many have said that your code is bad style, but now let me tell you why that is IMHO.
"Pass by reference" is mostly a synonym for "programming by side effect" which is a thing you always want to avoid. It makes code much harder to debug and understand, and in a multi-threaded environment, the bad effects of this attitude really can hit you hard.
To write scalable and thread-safe code in Java, you should make objects "read-only" as much as possible, i.e. ideally, you create an object and initialize it at the same time, then use it with this unmodifiable state throughout your application. Logical changes to the state can almost always be considered a "creation" of new state, i.e. creation of a new instance initialized to a state then needed. Many modern scripting languages only let you work in this way, and it makes things much easier to understand.
As opposed to C++, Java is much more efficient in allocating and releasing short-lived objects, so there is actually nothing wrong with what others here have suggested: To create an instance of a special class to hold the function result, just for the purpose of returning the result. Even if you do that in a loop, the JVM will be smart enough to deal with that efficiently. Java will only allocate memory from the OS in very large chunks when needed, and will deal with object creation and release internally without the overhead involved in languages like C/C++. "Pass by reference" really doesn't help you very much in Java.
EDIT: I suggest you search this forum or the net for the terms "side-effect", "functional programming" or "immutability". This will most likely open a new perspective to your question.
I believe that it is bad practice to "return" values using one-element arrays that are parameters to your method.
Here's another SO question about this topic. In short, it's very bad for readability.
There is an easy workaround: Wrap all values that you wish to return in a class you define specifically for this purpose, and return an instance of that class.
return new ValueHolder(someValue1, someValue2, someValue3);
That's not very idiomatic java. There are usually better approaches to software design.
What you're really doing with the "one-element array" is creating a mutable object (since String is immutable, as are primitives like int) and passing it by reference. Modifying this mutable object is called a "side effect" of the method. In general, you should minimize mutability (Effective Java Item 15) and your methods should be side-effect free. There are a couple approaches here.
1. Split the method into two (or three) methods that all take the same params:
public static int foo1(int param1)
{
// method body
....
return <some value>;
}
Similarly, you might have
public static int foo2(int param1) { ... }
and
public static String foo3(int param1) { ... }.
2. Return a composite object.
public Container {
private final int originalReturn;
private final int param2;
private final String param3;
public Container(int originalReturn, int param2, String param3) {
this.originalReturn = originalReturn;
this.param2 = param2;
this.param3 = param3;
}
// getters
}
public static Container foo(int param1, int param2[], String param3[])
{
// method body
....
// set return values
return new Container(<some value>, <some value>, <some value>);
}
This is indeed bad practice if the values are unrelated. This is usually an indicator that you can split that function into two, with each returning one of the values.
EDIT:
I am assuming that you are returning two values calculated in the method in an array. Is this not the case?
e.g.
public int[] getStatistics(int[] nums)
{
//code
int[] returns = new int[2];
returns[0] = mean;
returns[1] = mode;
return returns;
}
The above function could be split into getMean() and getMode().
Passing variables by reference allows the function to "legally" change their value. See this article to clear up the confusion of when this is possible in Java, and when it's not...
This is bad practice if the values are of different type and different entities, e.g. name and address, etc. It is fine with create an array with same data type, e.g list of addresses.

Java Best Practices: Performance with method parameters

Which is faster and/or less resources consuming:
class Foo()
{
public int value;
}
This way?
public int doSomeStuff(Foo f)
{
return (f.value + 1);
}
public int doOtherStuff()
{
...
Foo f = new Foo();
int x = doSomeStuff(f);
...
)
or this way?
public int doSomeStuff(int v)
{
return (v + 1);
}
public int doOtherStuff()
{
...
Foo f = new Foo();
int x = doSomeStuff(f.value);
...
)
In both cases, "doSomeStuff" will not change nothing in foo class. It just needs to know the "value".
They both perform the same, the same sequence of operations occurs. Your main concern is maintainability and sensible design here. Think carefully about which methods need which data and design it properly.
If you do have issues, you can optimise later. But you should always optimise last.
In terms of resource consuming, it is exactly the same.
But the second option is clearly better in terms of programming because if doSomeStuff only needs value, then there is no point to passing f.
I don't think there is any performance difference at all. And Java compiler will optimize to the best one anyway...
Depends how often you're going to call doSomeStuff without calling doOtherStuff, but generally performance difference is negligible and if you only call doOtherStuff then they'll be equally performant.
Probably even better:
Decalre doSomeStuff() as a method of foo, and invoke: f.doSomeStuff()
It is much more readable and will be easier to maintain doing it so, since if you have a
sub class of foo: Bar, and you want to calculate things a bit different - all you have to do is override doSomeStuff() in Bar
You should prefer readability over micro optimizations - let the compiler take care of those for you.
code snap:
class foo() {
public int value;
public int doSomeStuff() {
return value + 1;
}
}
and:
public int doOtherStuff() {
...
foo f = new foo();
int x = f.doSomeStuff();
...
}
The difference between doing:
object.intvariable + 1
and
int + 1
is so negligible as to be irrelevant for real world apps. It's probably one or two more JVM opcodes to look up foo and find its value variable which is not worth mentioning. You'd never notice that unless you were trying to create a pseudo real-time app in Java (which is all but an exercise in futility).
However, that said, the way you are doing it is very bad. You should not be exposing value directly, but be using proper data encapsulation via getter and setter methods.
It does not matter from performance perspective.
The recommendation is: do not think about pre-mature optimization. Think about correctness and good design of your code.
For example your code
Does not follow naming conventions: class names must start with capital letter
Contains public fields. It is forbidden. Use bean notation (getters and setters).
Cannot be compiled (there is no type integer. Choose among int and Integer

Categories

Resources