2017-08-23 43 views
13

TL;博士通用夫特4枚舉與空相關聯的類型

是否有可能實例的通用夫特4枚舉成員與Void類型的相關值?

背景

我用一個簡單的結果枚舉(類似於antitypical Result):

enum Result<T> { 
    case success(T) 
    case error(Error?) 
} 

現在,我想利用這個枚舉表示操作的結果這不會產生實際的結果值;該操作或者是成功失敗。爲此,我將該類型定義爲Result<Void>,但我正在爲如何創建Result實例而苦苦掙扎,let res: Result<Void> = .successlet res: Result<Void> = .success()都不起作用。

+0

你確定第二種方式嗎?看起來像它的作品http://swift.sandbox.bluemix.net/#/repl/599d61b1b459cc41aee76d9d – pacification

+0

有趣的,謝謝你的例子。我重新檢查了一下,但是在Xcode 9 Beta 5中,我得到了'調用參數#1缺少參數'。 –

+0

@Hamish:你可能是對的(我還在SE-0110和SE-0029 ... :) –

回答

28

在夫特3可以省略Void類型的相關聯的值:

let res: Result<Void> = .success() 

在夫特4你必須通過Void類型的相關聯的值:

let res: Result<Void> = .success(()) 
// Or just: 
let res = Result.success(()) 
+5

是否有一個不太難看的解決方案? –

+0

@RodrigoRuiz你可以定義一個擴展來擺脫'(())',[見我的回答](https://stackoverflow.com/a/46863180/2976878)。 – Hamish

3

空隙率爲簡單typealias空元組:(:)所以你可以使用它作爲以下任何一個:

let res1: Result<Void> = .success(()) 
let res2 = Result<Void>.success(()) 
let res3 = Result.success(() as Void) 
let res4 = Result.success(()) 
10

在Swift 4中,具有Void關聯值的枚舉情況不再等同於具有空值關聯值列表的枚舉情況。

我相信這是,as Martin saysSE-0029結果在那裏你可以不再傳遞的參數的元組的功能,並讓他們「圖示」穿越參數(雖然該提案被標註在斯威夫特3實現,我相信這個特殊情況在Swift 4的SE-0110的實現中稍後被採用)。

結果,這意味着你可以不再叫(Void) -> T作爲斯威夫特4 () -> T現在,您必須通過Void中明確:

let result = Result.success(()) 

不過,我覺得這是很醜陋,所以我通常實行這樣的擴展:

,它可以讓你說這樣的事情:

var result = Result.success 
result = .success 

值得注意的是,這種解決方法不僅僅侷限於枚舉情況,它還可以與一般的方法一起使用。例如:

struct Foo<T> { 
    func bar(_ a: T) {} 
} 

extension Foo where T == Void { 
    func bar() { bar(()) } 
} 

let f = Foo<Void>() 

// without extension: 
f.bar(()) 

// with extension: 
f.bar() 
+0

((Nice))。沒有意識到你可以根據泛型的類型定義變量。 – GoldenJoe