Refactor Multiple If' Statements in Java-8

multiple if else if with && condition in JAVA8

Note: in your example, you return 3 as a default, so if i=2 or j=2 for example you would return 3. Is that the expected behavior? I will provide examples where the values of i and j are assumed to always be 0 or 1

For your specific example:

This seems to be a good compromise, it is shorter and easy enough to read:

if(counterFlag==0) {
return priorityEnable == 0 ? 0 : 1;
}
return priorityEnable == 0 ? 2 : 3;

For more complex cases (i.e. 3, 4, or more variables):
I'd go for something like this:

Map<int[], Integer> map = new HashMap<>();
map.put(new int[] {0, 0}, 0);
map.put(new int[] {0, 1}, 1);
map.put(new int[] {1, 0}, 2);
map.put(new int[] {1, 1}, 3);

return map.entrySet().stream()
.filter(e -> e.getKey()[0] == counterFlag)
.filter(e -> e.getKey()[1] == priorityEnable)
.map(Map.Entry::getValue)
.findFirst()
.orElseThrow(IllegalArgumentException::new);

EDIT:
@Holger pointed out that "It's a waste to use a HashMap and then search it linearly. Use IntBuffer as key and you can perform a straight-forward lookup via get"

That is a good point, I tried it out and I think that this is what he meant:

Map<IntBuffer, Integer> map = new HashMap<>();
map.put(IntBuffer.wrap(new int[] {0, 0}), 0);
map.put(IntBuffer.wrap(new int[] {0, 1}), 1);
map.put(IntBuffer.wrap(new int[] {1, 0}), 2);
map.put(IntBuffer.wrap(new int[] {1, 1}), 3);

IntBuffer intBuffer = IntBuffer.wrap(new int[] {counterFlag, priorityEnable});
return map.get(intBuffer);

How do I refactor multiple if-else statements in Java?

Simplify

You can extract the common lines, before or after the ifs

System.out.println(lineOfText);
Scanner scanner2 = new Scanner(lineOfText);

if (typeOfData.equals("Book data")) {
LibraryItem libraryItem = new Book();
libraryItem.readData(scanner2);
storeItem(libraryItem);
} else if (typeOfData.equals("Periodical data")) {
LibraryItem libraryItem = new Periodical(); // LibrayItem => Periodical(subtype)
libraryItem.readData(scanner2);
storeItem(libraryItem);
} else if (typeOfData.equals("CD data")) {
LibraryItem libraryItem = new CD(); // LibrayItem => CD(subtype)
libraryItem.readData(scanner2);
storeItem(libraryItem);
} else if (typeOfData.equals("DVD data")) {
LibraryItem libraryItem = new DVD();
libraryItem.readData(scanner2);
storeItem(libraryItem);
} else if (typeOfData.equals("Library User data")) {
LibraryUser libraryUser = new LibraryUser();
libraryUser.readData(scanner2);
storeUser(libraryUser);
}

scanner2.close(); // ends scanner2


Improve

You could imagine the constructors to take the Scanner as parameter like

public Book(Scanner sc) {
readData(sc);
}

Then the ifs becomes

if (typeOfData.equals("Book data")) {
storeItem(new Book(scanner2));
} else if (typeOfData.equals("Periodical data")) {
storeItem(new Periodical(scanner2));
} else if (typeOfData.equals("CD data")) {
storeItem(new CD(scanner2));
} else if (typeOfData.equals("DVD data")) {
storeItem(new DVD(scanner2));
} else if (typeOfData.equals("Library User data")) {
storeUser(new LibraryUser(scanner2));
}

Or a switch

switch (typeOfData) {
case "Book data" -> storeItem(new Book(scanner2));
case "Periodical data" -> storeItem(new Periodical(scanner2));
case "CD data" -> storeItem(new CD(scanner2));
case "DVD data" -> storeItem(new DVD(scanner2));
case "Library User data" -> storeUser(new LibraryUser(scanner2));
}

Refactor multiple or conditions with java8

There is always the possibility to introduce a loop like:

private boolean isStatusAvailable(List<Hierarchy> hierarchyList, ResultStatus status, int i) {
Hierarchy hierarchy = hierarchyList.get(i + 1);
for (ResultStatus s : Arrays.asList(status, SUCCESS, PEND)) {
if (isContainsStatus(hierarchy, s)) {
return true;
}
}
return false;
}

If you want to use Streams then you can write:

private boolean isStatusAvailable(List<Hierarchy> hierarchyList, ResultStatus status, int i) {
Hierarchy hierarchy = hierarchyList.get(i + 1);
return Stream.of(status, SUCCESS, PEND).anyMatch(s -> isContainsStatus(hierarchy, s));
}

How to avoid multiple If Statements in Java?

    public String getFirstOrLastNameOrBoth() {
return (getFirstname() == null ? "" : getFirstname())
+ (getLastname() == null ? "" : getLastname());
}

Multiple If Statement Reduction

The simple answer to the overt question of, "can I make this more concise/terse" is "no". You're not really going to get what you're looking for in making this more terse or concise, nor would computeIfPresent really give you what you're looking for and keep your code readable.

The issue is that, when you go to retrieve a key from your map, you're putting it in a different field in your collateral instance. This means that trivial solutions such as looping over the map won't satisfy since you're not going to be able to get the exact field you need to map to without getting deep into reflection.

The code you have here, albeit verbose, is perfectly readable and reasonable to any other maintainer to understand what's going on. I see no incentive to change it.

how to refactor this method which has multiple if/else statements

If you absolutely want to change it, you could initialise url to the default return and only change it if one of the two conditions is met:

private String someReportUrl(HttpServletRequest request, HttpServletResponse response) {
String url = "/standAlone/reportUrl.jsp";
if (isBackToReportsSummary(request)) {
url = SUMMARY_PAGE;
getReportsSummary(request, response);
} else if (isComingFromPageA(request)) {
url = getTabUrl(request, REPORT_URL_FOR_PAGE_A);
}
return url;
}

But really, it's fine as is.



Related Topics



Leave a reply



Submit