Hi all, I’ve got quite some pieces of code in my a...
# announcements
b
Hi all, I’ve got quite some pieces of code in my application like this:
Copy code
val product: Product = products.find { it.name = input } ?: throw IllegalArgumentException("Product $input not found")
I know that it will be very unlikely to not find the product in this list (say, impossible), so, I’d rather not clutter my code with the “if null throw exception” stuff, and rather have
find
throw an exception if the product can’t be found, like this:
Copy code
val product: Product = products.find { it.name = input }
I’d rather not make Product nullable (
Product?
), cause that will lead to some if/then elses later in my code. Is there any clean way I’ve missed to accomplish this?
‼️ 4
y
Just define an extension function that does that as follows:
Copy code
inline fun <T> Iterable<T>.findOrThrow(
    predicate: (T) -> Boolean
): T? = find(predicate) ?: throw IllegalArgumentException("Item not found")
n
what about
val product: Product = products.first { it.name == input }
? That throws a NoSuchElementException though. Or ``val product: Product = checkNotNull(products.find { it.name == input }` but that throws an IllegalStateException.
n
don't forget about
require
and
check
functions
b
@Youssef Shoaib [MOD] thanks, that’s actually what I ended up doing (with an optional error message)
@nkiesel that would also work great, thanks! I’m okay with the NoSuchElementException, I had not seen that
first
can also take a predicate. Thanks!
n
yeah, clearly beats the Java
Product product = products.stream().filter(it -> it.getName().equals(input)).findFirst().orElseThrow(NoSuchElementException::new);
To be fair, that can be shortened to
Product product = products.stream().filter(it -> it.getName().equals(input)).findFirst().get();
b
That’s not bad, but not as elegant as the Kotlin version. Thanks again for the help!
v
I have an inline extension function “required”, which throws same exception as error() and returns not-null instance of the receiver type i.e. Product. It takes lambda to make message if assertion failed. val product: Product = products.find { it.name = input }.required { “Product $input not found” }