Trong bài này chúng ta sẽ tìm hiểu về kiểu Optional trong Swift. Nó chính là một trong những yếu tố làm cho swift có tính an toàn. Vậy thì Optional là gì? Và vì sao nó lại làm cho ngôn ngữ Swift trở nên an toàn. Chúng ta sẽ cùng tìm hiểu với bài viết bên dưới. Trước tiên, chúng ta bắt đầu tạo mới một playgrounds cho bài viết này, sử dụng nó chính là một cách tuyệt vời để học cú pháp và hiểu các khái niệm cơ bản của Swift. Chạy Xcode 9, tạo mới một playground bằng cách chọn: New-> Playground… từ menu File của Xcode, sau đó nhập tên cho playground và chọn nền tảng iOS, chọn Next, Xong chúng ta bắt đầu code nào.

Optional là gì?

Một biến optional là một biến mà có thể có giá trị cụ thể nào đó hoặc không giữ giá trị nào cả ( hay biến đó bị nil). Đặc điểm của một biến Optional là sau kiểu dữ liệu của biến đó sẽ có thêm dấu hỏi. Như ví dụ bên dưới:

var name: String? = "Cafedev.vn"

Có thể nói Optional là một khái niệm khó hiểu của Swift. Khó ở chổ cách sử dụng cũng như cách viết nó cho phù hợp với ý tưởng của chúng ta. Để khắc phục được điều này thì chỉ có một cách đó là code càng nhiều để có nhiều kinh nghiệm sử dụng nó. Để tạo một biến Optional, chúng ta chỉ cần thêm sau kiểu dữ liệu một dấu ? và không có khoàng trắng giữ dấu ? và kiểu dữ liệu nhé.

Ví dụ:

var name: String? = "Bob" // Tạo một Optional kiểu String với trị là Bob dùng var

var peter: Person? = Person() //Một Oprional “Persion” 

//Một Class có properties là một kiểu Option String. 
class Car { 
  var modelName: String // Trị này phải luôn có giá trị
  var internalName: String? // Trị này có thể có hoặc không giá trị.
}

Cách khác để tạo biến Optional như sau:

var name: Optional<String> = Optional("Bob")

var serialNumber:String? = Optional.none 
serialNumber = Optional.some("1234")
 print("\(serialNumber.debugDescription)")

Nếu bạn dùng cách tạo biến Optional như trên thì chúng ta có thể dùng các toán tử so sánh ==, != cho các biến đó.

Ví dụ:

var tuxedoRequired: String? = nil
let temp: Optional<String> = Optional.none
if tuxedoRequired == temp { // HIều là tuxedoRequired == nil
  print("tuxedoRequired is nil") 
}

let numberToFind: Int = 23 
let numberFromString: Int? = Int("23") // Optional(23) 
if numberToFind == numberFromString { 
  print("It's a match!") // Prints "It's a match!"
 }

Thêm ví dụ:

let a: Any = "hello" 
let b: Any = "goodbye" 

if (a as? Double) == (b as? Double) { 
  print("these will be equal because both nil...")
 }

Cách sử dụng Optional

Sử dụng biến Optional, để dùng biến optional trước tiên chúng ta phải kiểm tra biến đó có bị nil hay không. Nếu bị nil có nghĩa là biến không có giá trị thì chúng ta sẽ không dùng được nó và ngược lại.

VÍ du:

var name: String? = "Bob" 
name = nil // Gán name = nil. Ý là name không có giá trị nào cả
if name != nil { 
  print("There is a name") 
} 

if name == nil {
 // Chúng ta có thể dùng name với trường hợp "else" 
  print("Name has no value") 
}

Lưu ý:

Chỉ có duy nhất biến Optional mới có thể gán dược trị nil. Nếu biến bình thường mà gán trị nil thì Xcode sẽ báo lỗi. Vậy để dùng biến Optional chúng ta phải “unwarp” nó, hiểu đơn giản là chúng ta phải kiểm tra xem nó có trị hay không rồi mới dùng.
Có nhiều cách “Unwarp” một biến Optional, có thể dùng cú pháp
! , nhưng cú pháp này không an toàn nếu trường hợp biến đó bị nil mà ta đem đi Unwap thì sẽ gây ra crash ứng dụng.
Ví dụ:

var name: String? = "Bob" 
let unwrappedName: String = name!
print("Unwrapped name: \(unwrappedName)") 
name = nil let nilName: String = name! // Runtime crash. Unexpected nil.

Do đó trước khi dùng biến optional thì chúng ta nên kiểm tra nó trước bắng cách như sau:

var mealPreference: String? = "Vegetarian" 
if mealPreference != nil { 
  let unwrappedMealPreference: String = mealPreference! 
  print("Meal: \(unwrappedMealPreference)") 
}

Hoặc Swift còn hỗ trợ cho chúng ta cách kiểm tra như sau:

var mealPreference: String? = "Vegetarian" 
if let unwrappedMealPreference: String = mealPreference {
  print("Meal: \(unwrappedMealPreference)") 
}

Hoặc dùng grand let trong Swift 2.0 trờ lên mới có.

Ví dụ:

Let s:Int? = 10
guard let i = Int(s) else { 
  fatalError("Input must be a number") 
}
print(i+1)

Ở đây có một ít thú vị khi sử dụng Unwrap biến như sau:

var mealPreference: String? = "Viet Nam" 
if var mealPreference: String = mealPreference { 
  print("Meal: \(mealPreference)") // mealPreference là String không phải là String?
  mealPreference = "HCM" // Cú pháp thì không báo lỗi nhưng dòng code này vô nghĩa 
}

print("Meal: \(mealPreference)") // Prints "Meal: Optional("Viet Nam")"

Như các bạn đã thấy biến mealPreference vẫn giá trị như cũ nhé. Trong Xcode 8.3 và Swift 3.1 trờ về sau thì chúng ta có thể in biến Optional bằng cách như sau để không bị Xcode cảnh báo.

print(“\(mealPreference.debugDescription)”)

So sánh nil Bạn có thể dùng bất kỳ biến Optional nào giống như kiểu Bool:

Ví dụ:

let leatherTrim: CarExtras? = nil // CarExtras là một object nào đó.
if leatherTrim {
   price = price + 1000 
}

 var religiousAffiliation: String? = "Viet Nam" 
religiousAffiliation = nil 
if religiousAffiliation != nil { ... }

Khi nào thì sử dụng Optional

Cụ thể hơn thì khi nào sẽ dùng biến Optional? Sẽ có 2 trường hợp như sau:

  • Bạn nghĩ rằng biến đó có thể rơi vào trường hợp bị lỗi và có thể nhận giá trị nil(ngoài trường hợp thuận lợi thì biến đó có thể bị nil)
  • Bạn nghĩ rằng nếu có trường hợp lỗi thì bạn sẽ muốn xử lý tiếp cái gì đó. Thì bạn sẽ dùng Optional để kiểm tra và xử lý lỗi.

Ví dụ cụ thể như:

  • Một thuộc tính name có thể có hoặc không có trị, như middName of Person class.
  • Một Phương thức(method) có thể trả về giá trị nào đó hoặc không gì cả.
  • Properties Delegate không phải lúc nào cũng được dùng, nên có lúc có trị hoặc không.
  • Properties có weak , nó sẽ có trường hợp tự bị giải phóng nên tự gián được nil.
  • Các Biến có chứa giá trị lớn cần phải giải phóng khi dùng xong, để giảm bộ nhớ cho máy.
  • Một biến nào đó chúng ta biết sẽ có 2 trường hợp có và không có trị để xử lý.

Qua bài này các bạn đã hiểu thêm về một điểm tạo nên tính an toàn trong Swift, đó là dùng Optional, Tuy ban đầu nó hơi rối với các bạn mới như khi dùng quen và hiểu khi nào đùng nó thì các bạn sẽ làm cho code của mình thêm an toàn và tránh gây ra crash ứng dụng.

Hy vọng các bạn thích và học được nhiều kiến thức từ bài viết này. Mong các bạn chia sẽ nó để mọi người cùng học và cùng trao đổi. Mọi thắc mắc hay trao đổi về bài viết, các bạn có thể để lại bình luận bên dưới mình sẽ hỗ trợ sớm nhất. Chân thành cảm ơn các bạn đã theo dõi.

Đăng ký kênh youtube để ủng hộ Cafedev nha các bạn, Thanks you!

1 BÌNH LUẬN

Bình luận bị đóng.