Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Collecting errors in a Java method, empty ArrayList vs. LinkedList

I seem to create these two kind of methods occasionally:

// return null on errors, and append errors to 2nd param, otherwise return result
String fetchSomething(String parameter, List<String> errorMessagesOut);

// return empty list or null on no errors, otherwise list of errors
List<String> verifySomething(String parameter);

And then the code which calls these will join the error list with appropriate separator (such as simple comma, newline, HTML tags...), usually using Apache Commons Stringutils.join method. And in normal case there's no error, and list will be empty.

So, I started wondering about these two questions:

  1. Do you see a problem with returning error message strings as list? If so, what is better alternative? (Not exceptions, that would be thrown by code which calls these methods, when that is wanted.)

  2. Is new LinkedList() or new ArrayList(0) or new ArrayList() better for list which is expected to remain empty, and which should normally have only sequential iterator access when it is not empty?


EDIT: Example use case:

List<String> verifyParameters(JSONObject params) {
    List<String> ret = new ArrayList<String>(0);

    if (!verifyKey(params.get("key"))) 
        ret.add("Invalid key: " + key);

    if (!verifyAccess(params.get("user"), params.get("pass"))) 
        ret.add("Authentication error");

   return ret;
}

...

List<String> errors = verifyParameters(params);
if (!errors.isEmpty()) {

    connection.sendErrorListMessage(errors);
    logger.warn(StringUtils.join(errors, ", "));
    controlPanel.show("Errors: \n- " + StringUtils.join(errors, "\n- ") + '\n');
    throw new AbortException("invalid params); // or maybe return false/null;
}
// proceed with valid params

Usually handling of error list would not have all of those, it just tries to illustrate the point that error list is a list of messages meant for humans to see, independent of how it will be shown, and also not related to/useful for handling different errors differently.

like image 736
hyde Avatar asked Mar 04 '13 16:03

hyde


People also ask

What is the difference between manipulating LinkedList and ArrayList?

Manipulating LinkedList takes less time compared to ArrayList because, in a doubly-linked list, there is no concept of shifting the memory bits. The list is traversed and the reference link is changed. This class implements a List interface. Therefore, this acts as a list. This class implements both the List interface and the Deque interface.

How to check if a LinkedList is empty in Java?

The isEmpty method of the LinkedList class returns true if the LinkedList object is empty. The isEmpty method returns a boolean value indicating whether there are any elements in the LinkedList (i.e. it is empty or not).

What is collection emptylist () in Java?

Collections.emptyList () returns a list ( java.util.Collections.EmptyList) that can't be modified. When creating a new list instance you can modify it depending on the implementation: 3. Object Creation Collection.emptyList () creates a new empty list instance only once, as shown in source code:

What is the difference between emptylist () and New ArrayList<>?

The core difference between java.util.Collections.emptyList () and a new list e.g. new ArrayList<> () is immutability. Collections.emptyList () returns a list ( java.util.Collections.EmptyList) that can't be modified.


2 Answers

I think it's fine to use a List for the Strings. I would be inclined to make a dedicated Result class at least for fetchSomthing and make it like this, especially if the errorMessagesOut passed is never anything except a new empty List:

Result result = fetchSomething(String parameter);
if (result.hasErrors()) {
    List<String> errors = result.getErrors();
} else {
    String fetched = result.getValue();
}

I would then also put any of the methods that process the error Strings on this class also so you could do something like:

String errorMessage = result.getErrorString();

This encapsulates the error data and the formatting of it within the one Class and means that in the case of no errors you don't need to create any List internally in your Result instance.

My above points are mostly about the code design. There is no point in trying micro-optimization without profiling and having benchmarks to compare to the results of any changes.

like image 156
Alb Avatar answered Oct 21 '22 10:10

Alb


What are these errors for? Are you going to do some business decision off of the errors returned by a method? Otherwise, if the errors are just for logging, a simple Logging solution would suggest that the errors are logged as soon as they occur. I'm talking about those logger.debug("Error message");.

Anyway, could you give us an example of what is done to this errors after they are returned?

One thing I point, though: It tends to be confusing if you're using the same array / list / collection for both processing results and for errors. It would also be confusing if your methods returned error lists (or empty/null lists in case of no error) as it would appear that the errors are the very result of executing your method.

like image 22
Filipe Fedalto Avatar answered Oct 21 '22 10:10

Filipe Fedalto