Built-in exceptions like IllegalArgumentException do not say what went wrong in your own domain. A custom exception, like InsufficientBalanceException, names the exact problem and lets callers catch just that case. Create one when a business rule is broken and callers need to react to it specifically. If a built-in exception already describes the problem well, use it instead of making a new class.