Ràng buộc có điều kiện: nếu để xảy ra lỗi - Bộ khởi tạo cho ràng buộc có điều kiện phải có Loại tùy chọn


120

Tôi đang cố xóa một hàng khỏi Nguồn dữ liệu của mình và dòng mã sau:

if let tv = tableView {

gây ra lỗi sau:

Bộ khởi tạo cho ràng buộc có điều kiện phải có Loại tùy chọn, không phải UITableView

Đây là mã đầy đủ:

// Override to support editing the table view.
func tableView(tableView: UITableView, commitEditingStyle editingStyle:UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath) {
    if editingStyle == .Delete {

        // Delete the row from the data source

    if let tv = tableView {

            myData.removeAtIndex(indexPath.row)

            tv.deleteRowsAtIndexPaths([indexPath], withRowAnimation: .Fade)

Tôi nên sửa những điều sau đây như thế nào?

 if let tv = tableView {

8
tableViewkhông phải là một giá trị tùy chọn, không cần phải kiểm tra xem nó có phải là nil hay không. Vì vậy, bạn có thể trực tiếp sử dụng nó, tôi remove bình đó if let và chỉ sử dụng tableViewtrong hàm
Eric Qian

Cho hậu thế, sau khi tôi cố định vấn đề này, tôi chạy vào variable with getter/setter cannot have an initial value, mà đã được giải quyết bằng cách đơn giản loại bỏ các khối còn sót lại {} sau khi khởi tạo, ala câu trả lời này: stackoverflow.com/a/36002958/4544328
Jake T.

Câu trả lời:


216

if let/ if vartùy chọn ràng buộc chỉ hoạt động khi kết quả của phía bên phải của biểu thức là tùy chọn. Nếu kết quả của phía bên phải không phải là tùy chọn, bạn không thể sử dụng ràng buộc tùy chọn này. Điểm của ràng buộc tùy chọn này là kiểm tra nilvà chỉ sử dụng biến nếu nó không phải nil.

Trong trường hợp của bạn, tableViewtham số được khai báo là kiểu không tùy chọn UITableView. Nó được đảm bảo là không bao giờ có nil. Vì vậy, ràng buộc tùy chọn ở đây là không cần thiết.

func tableView(tableView: UITableView, commitEditingStyle editingStyle:UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath) {
    if editingStyle == .Delete {
        // Delete the row from the data source
        myData.removeAtIndex(indexPath.row)
        tableView.deleteRowsAtIndexPaths([indexPath], withRowAnimation: .Fade)

Tất cả những gì chúng ta phải làm là loại bỏ if letvà thay đổi bất kỳ sự kiện nào của tvnó thành chỉ tableView.



16

Trong trường hợp bạn đang sử dụng loại ô tùy chỉnh, chẳng hạn như ArticleCell, bạn có thể gặp lỗi cho biết:

    Initializer for conditional binding must have Optional type, not 'ArticleCell'

Bạn sẽ gặp lỗi này nếu dòng mã của bạn trông giống như sau:

    if let cell = tableView.dequeReusableCell(withIdentifier: "ArticleCell",for indexPath: indexPath) as! ArticleCell 

Bạn có thể sửa lỗi này bằng cách làm như sau:

    if let cell = tableView.dequeReusableCell(withIdentifier: "ArticleCell",for indexPath: indexPath) as ArticleCell?

Nếu bạn kiểm tra ở trên, bạn sẽ thấy rằng sau này đang sử dụng truyền tùy chọn cho một ô thuộc loại ArticleCell.


Trong trường hợp của tôi, tôi cần sử dụngas! ArticleCell?
lilbiscuit

9

Tương tự cũng áp dụng cho các tuyên bố bảo vệ . Cùng một thông báo lỗi dẫn tôi đến bài đăng này và câu trả lời (cảm ơn @nhgrif).

Mã: Chỉ in họ của người đó nếu tên đệm ít hơn bốn ký tự.

func greetByMiddleName(name: (first: String, middle: String?, last: String?)) {
    guard let Name = name.last where name.middle?.characters.count < 4 else {
        print("Hi there)")
        return
    }
    print("Hey \(Name)!")
}

Cho đến khi tôi khai báo cuối cùng dưới dạng tham số tùy chọn, tôi vẫn gặp lỗi tương tự.


4

ràng buộc điều kiện phải có loại optinal có nghĩa là bạn chỉ có thể liên kết các giá trị tùy chọn trong câu lệnh if let

func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {

    if editingStyle == .delete {

        // Delete the row from the data source

        if let tv = tableView as UITableView? {


        }
    }
}

Điều này sẽ hoạt động tốt nhưng hãy chắc chắn rằng khi bạn sử dụng nếu để nó phải có loại optinal "?"


0

Chà, sẽ vẫn thuận tiện (về mặt cú pháp) nếu chúng ta có thể khai báo các giá trị thông thường bên trong điều kiện if. Vì vậy, đây là một mẹo: bạn có thể làm cho trình biên dịch nghĩ rằng có sự gán Optional.some(T)cho một giá trị như vậy:

    if let i = "abc".firstIndex(of: "a"),
        let i_int = .some(i.utf16Offset(in: "abc")),
        i_int < 1 {
        // Code
    }
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.