Avoiding Switch and if-Else using Map and Java Reflection
Here's an exercise where you can use Java Reflection to avoid using switch cases and refactor the code to be more maintainable:
Problem: Handle Different Types of Operations Without Switch Statements
You are given an interface Operation with multiple implementations. Each implementation of Operation performs a different task, such as addition, subtraction, etc. Instead of using a switch statement to determine which operation to perform based on the type of the operation, use Reflection to dynamically call the appropriate method based on the operation type.
Exercise Steps:
Define the Operation interface:
public interface Operation {
void execute();
}
Implement different operation classes:
public class AddOperation implements Operation {
@Override
public void execute() {
System.out.println("Performing Addition");
}
}
public class SubtractOperation implements Operation {
@Override
public void execute() {
System.out.println("Performing Subtraction");
}
}
public class MultiplyOperation implements Operation {
@Override
public void execute() {
System.out.println("Performing Multiplication");
}
}
Create a class OperationExecutor that uses Reflection:
Instead of using a switch statement to determine which operation to execute, you can use Reflection to dynamically invoke the execute method based on the operation type.
import java.lang.reflect.Method;
public class OperationExecutor {
public void executeOperation(String operationType) {
try {
// Dynamically determine the class based on operation type
String className = "com.example." + operationType + "Operation"; // Assuming operation classes are named this way
Class<?> operationClass = Class.forName(className);
Object operationInstance = operationClass.getDeclaredConstructor().newInstance();
// Invoke the execute method using Reflection
Method executeMethod = operationClass.getMethod("execute");
executeMethod.invoke(operationInstance);
} catch (Exception e) {
e.printStackTrace();
}
}
}
Test the solution:
public class Main {
public static void main(String[] args) {
OperationExecutor executor = new OperationExecutor();
executor.executeOperation("Add"); // Performing Addition
executor.executeOperation("Subtract"); // Performing Subtraction
executor.executeOperation("Multiply"); // Performing Multiplication
}
}
Explanation:
Benefits:
Recommended by LinkedIn
Using Map to avoid Switch
Here's another exercise where you can avoid using a switch statement by leveraging a Map. This time, let's implement a system where we dynamically map operations to their corresponding functions using a Map and avoid using conditional statements like switch.
Problem: Map-Based Operation Dispatcher
You are tasked with creating a system that performs different arithmetic operations (addition, subtraction, multiplication, division) based on the input operation type, without using a switch statement. Use a Map to dynamically associate operation types with their corresponding implementation.
Exercise Steps:
Define the Operation interface:
public interface Operation {
double apply(double a, double b);
}
Implement concrete operation classes:
public class AddOperation implements Operation {
@Override
public double apply(double a, double b) {
return a + b;
}
}
public class SubtractOperation implements Operation {
@Override
public double apply(double a, double b) {
return a - b;
}
}
public class MultiplyOperation implements Operation {
@Override
public double apply(double a, double b) {
return a * b;
}
}
public class DivideOperation implements Operation {
@Override
public double apply(double a, double b) {
if (b == 0) throw new IllegalArgumentException("Cannot divide by zero");
return a / b;
}
}
Create the OperationExecutor class with a Map to avoid the switch:
import java.util.HashMap;
import java.util.Map;
public class OperationExecutor {
private final Map<String, Operation> operationMap;
public OperationExecutor() {
operationMap = new HashMap<>();
operationMap.put("add", new AddOperation());
operationMap.put("subtract", new SubtractOperation());
operationMap.put("multiply", new MultiplyOperation());
operationMap.put("divide", new DivideOperation());
}
public double executeOperation(String operationType, double a, double b) {
// Retrieve the operation dynamically using the map
Operation operation = operationMap.get(operationType.toLowerCase());
if (operation == null) {
throw new IllegalArgumentException("Unknown operation: " + operationType);
}
return operation.apply(a, b);
}
}
Test the solution:
public class Main {
public static void main(String[] args) {
OperationExecutor executor = new OperationExecutor();
double resultAdd = executor.executeOperation("add", 5, 3);
System.out.println("Addition: " + resultAdd); // Output: 8.0
double resultSubtract = executor.executeOperation("subtract", 5, 3);
System.out.println("Subtraction: " + resultSubtract); // Output: 2.0
double resultMultiply = executor.executeOperation("multiply", 5, 3);
System.out.println("Multiplication: " + resultMultiply); // Output: 15.0
double resultDivide = executor.executeOperation("divide", 6, 3);
System.out.println("Division: " + resultDivide); // Output: 2.0
}
}
Explanation:
Benefits: