簡體   English   中英

泛型類型返回 Nil

[英]Return Nil for Generic Type

我有以下代碼:

class Function<T> {
    var ptr: () throws -> T

    init<Func>(block: Func, args: AnyObject...) {
        self.ptr = {() throws -> T in
            let result: AnyObject? = nil

            if T.self == Void.self {
                return Void() as! T
            }

            return result //Error Here.. Cannot as! cast it either.. Cannot unsafeBitCast it either..
        }
    }
}

postfix operator ^ { }
postfix func ^ <T>(left: Function<T>) throws -> T {
    return try left.ptr()
}


func call() {
    let block: (String) -> String? = {(arg) -> String? in
        return nil
    }

    let fun = Function<String?>(block: block, args: "Hello")
    fun^
}

函數Block.execute返回AnyObject? . 我的通用類Function<T>期望返回類型為T

如果T已經是String? 為什么我不能返回零?

有沒有辦法將 nil 作為類型 T 返回,它已經是可選的?

如果我將T設為 Optional,則返回類型變為Optional<Optional<String>>這不是我想要的。然后編譯器抱怨OptionalOptional沒有用?? 這就是我知道T已經是可選的。

我通過一個令人討厭的工作解決了它。我為 nil 返回類型拋出了一個異常。 然后在通用函數運算符中,我捕獲該特定異常並返回nil如果TNilLiteralConvertible .. 否則我只是正常執行..

class Function<T> {
    var ptr: () throws -> T

    init<Func>(block: Func, args: AnyObject...) {
        self.ptr = {() throws -> T in
            let result: AnyObject? = execute(block, args...)

            if T.self == Void.self {
                return Void() as! T
            }

            throw BlockError.BlockReturnsNil
        }
    }
}

postfix func ^ <T>(left: Function<T>) throws -> T {
    return try left.ptr()
}

postfix func ^ <T : NilLiteralConvertible>(left: Function<T>) throws -> T {
    do {
        return try left.ptr() 
    }
    catch BlockError.BlockReturnsNil {
        return nil
    }
}

以下演員陣容Any? T返回nil只有T是可選的,並且fromnil 如果from不能轉換為T ,它就會崩潰。

func cast<T>(from v: Any?)->T {        
    return v as! T
}

func cast<T>(from v: Any?)->T where T: ExpressibleByNilLiteral {
    guard let v = v else { return nil }
    return v as! T
}

從 Swift 3.1 開始,這就是訣竅。 修改 user3763801 的回答。

func cast<T>(_ v: Any) -> T {
    return v as! T
}

在谷歌上搜索了很長時間后,我終於找到了一種優雅的方法來做到這一點。 可以編寫帶有類型約束的類擴展。

class Foo<T> {
  func bar() -> T {
    return something
    // Even if T was optional, swift does not allow us to return nil here:
    // 'nil' is incompatible with return type 'T'
  }

}
extension Foo where T: ExpressibleByNilLiteral {
    func bar() -> T {
        return nil
        // returning nil is now allowed
    }
}

根據 T 是否可選,將調用適當的方法。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM