Throw vs. Throws
Overview
If Try-Catch is how you 'catch' errors, `throw` and `throws` are how you create and pass them. `throw` is an action verb used *inside* a method body to physically trigger an exception right now. `throws` is a declarative keyword used in the method *signature* to warn whoever calls the method: 'Hey, I might throw a bomb, so you better be prepared to catch it.'
Syntax
Use `throw` followed by the `new` keyword to create and launch an exception. It functions very similarly to a `return` statement; execution immediately halts.
public void setAge(int age) {
if (age < 0 || age > 150) {
// 'throw' instantly stops the method and fires an exception object
throw new IllegalArgumentException("Age must be between 0 and 150");
}
this.age = age;
}Java forces you to handle 'Checked Exceptions'. If you don't want to use a Try-Catch block inside your method, you must add `throws` to the method signature.
// The 'throws' keyword goes in the method signature
public void readFile(String filePath) throws FileNotFoundException {
File file = new File(filePath);
// FileInputStream throws a checked FileNotFoundException
// By using 'throws' in the signature, we refuse to handle it here
// and pass the responsibility to the caller.
FileInputStream stream = new FileInputStream(file);
}Common Pitfalls
- Using `throws Exception` on every single method in your codebase just to avoid writing Try-Catch blocks. This defeats the entire purpose of strongly-typed error handling.
- Throwing generic `RuntimeException` instead of specific exceptions (like `IllegalArgumentException`), making it impossible for the caller to know exactly what went wrong.
Interview Tips
- Use an analogy: 'throw' is the act of physically throwing a bomb, while 'throws' is a warning label on the box saying 'this might contain a bomb'.
Real-World Example
When validating user inputs in a service layer, you throw an exception if the input is bad. The web controller layer will catch it and send a 400 Bad Request to the user.
public class PaymentService {
// Declaring that this method might fail with a specific checked error
public void processCard(String cardNo) throws InvalidCardException {
if (cardNo == null || cardNo.length() != 16) {
// Actually throwing the error
throw new InvalidCardException("Card must be 16 digits.");
}
// ... process payment
}
}