Error Handling in Scala
Có nhiều cách để Error Handling trong Scala, chúng ta sẽ cùng nhau tìm hiểu.
Hãy nhìn ví dụ dưới đây:
1 2 3 4 5 6 7 8 9 10 |
val coffeePrice = 10 def buyCoffee(money: Float): Coffee= { if(money < coffeePrice) { try { buyCoffee(5) } catch { case e: Exception => e.getMessage } |
Khi gọi hàm buyCoffee với tham số truyền vào là 5, hệ thống sẽ throw ra exception:
1 2 |
buyCoffee(5) //>Exception in thread "main" java.lang.Exception: Not enough money to buy a coffee, need 10 |
OK, theo cách truyền thống chúng ta sẽ sử dụng try/catch để xử lý:
1 2 3 4 5 6 |
try { buyCoffee(5) } catch { case e: Exception => e.getMessage } |
Look good, nhưng nhìn lại chúng ta đang code theo cách của Java :P.
Chúng ta sẽ viết lại đoạn code trên theo cách của Scala!
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
import scala.util.Try ... val coffeePrice = 10 def buyCoffee(money: Float): Try[Coffee] = { Try { if(money < coffeePrice) { throw new Exception(s"Not enough money to buy a coffee, need $coffeePrice") } else { new Coffee } } } |
Chúng ta sử dụng Try block trong hàm buyCoffee và kiểu trả về của hàm này sẽ là Try[Coffee]. Hàm buyCoffee lúc này không cần thực hiện “Error Handling”, nó trả ra Success(Coffee) hoặc Failure(java.lang.Exception: Not enough money to buy a coffee, need 10).
Có nhiều cách khác nhau để extract giá trị của lệnh gọi hàm buyCoffee(5),
1 2 3 |
val coffee = buyCoffee(5) if(coffee.isSuccess) coffee.get else "OK! I will back!" |
Hoặc bạn có thể dùng getOrElse
1 2 3 |
val coffee = buyCoffee(5) coffee.getOrElse("OK! I will back!") |
Hoặc bạn có thể sử dụng Pattern Matching:
1 2 3 4 5 |
buyCoffee(5) match { case Success(result) => result case Failure(result) => "OK! I will Back!" } |
Nhưng mình thích nhất là cách này,
1 2 3 4 5 6 |
buyCoffee(5).map { coffee => coffee }.recover{ case e: Exception => "OK! I will Back!" } |
Sử dụng recover để bắt trường hợp Try trả ra Failure
OK! Hẹn gặp lại các bạn trong các bài chia sẻ tiếp theo.