2016-12-02 11 views
5

Ok, więc mam jakąś klasę zdefiniowaną następująco:Dlaczego mogę wprowadzić wymagania tego samego typu w przypadku szybkich generycznych? Czy jest jakiś sposób?

public final class Process<InputType, OutputType, Memory> 

i chcę zrobić z funkcji dostępnych tylko dla przypadku gdy InputType i OutputType są dokładnie tego samego typu. więc próbowałem tak jak to:

extension Process where InputType == OutputType { } 

Ale to doprowadziłoby:

wymaganie tego samego typu sprawia, że ​​parametry rodzajowe InputType i OutputType równoważne

Więc ja” poszło trochę dalej i próbowałem zrobić to tak:

func bypass<SameType>() -> Process<SameType, SameType, Memory> where OutputType == InputType {} 

Ale spowoduje to dokładnie ten sam błąd. Pytanie więc brzmi: dlaczego nie mogę zdefiniować generycznych w taki sposób, aby dwa typy generyczne były Równoważne, bo właśnie tego chciałem. Chciałem zdefiniować funkcję dostępną tylko dla tego przypadku, która zawiedzie w czasie kompilacji, jeśli ta reguła nie będzie przestrzegana.

Więc teraz używam coś takiego:

public static func bypass<SameType>() -> Process<SameType, SameType, Memory> 

Które ostatecznie nie tylko w czasie wykonywania, a nawet wtedy, gdy tworzone ale gdy beton klasy jest wyzwalany do działania.

Czy istnieje sposób zdefiniowania extension lub function dla ogólnych parametrów tego samego typu, które nie zostałyby skompilowane (spowoduje błąd podczas kompilacji)?

Aktualizacja: niektóre szczegóły implementacji są pominięte przyczyną stałaby Kod nieczytelny i nie są krytyczne dla kontekstu

Odpowiedz

6

W Swift 4 lub nowszy, można napisać:

public final class Process<InputType, OutputType, Memory> { 
    // ... 
} 

extension Process where InputType == OutputType { 
    func bypass() -> Process<InputType, OutputType, Memory> { 
     // ... 
    } 
} 

Oryginalna odpowiedź (Swift 3):

Nie można ograniczać typy na klasach ogólnych, mimo że some changes nadchodzą w Swift 4. Można jednak ograniczyć typy na protokole. Możesz utworzyć protokół, który tylko Process spełnia następujące warunki:

protocol ProcessProtocol { 
    // I haven't found a way to name these associated type identically to 
    // those in the class. If anyone discover a way, please let me know 
    associatedtype IT 
    associatedtype OT 
    associatedtype MT 
} 

final public class Process<InputType, OutputType, MemoryType>: ProcessProtocol { 
    typealias IT = InputType 
    typealias OT = OutputType 
    typealias MT = MemoryType 

    // your code 
} 

// Note that this is an extension on the protocol, not the class 
extension ProcessProtocol where IT == OT { 
    func foo() { 
     // this function is only available when InputType = OutputType 
    } 
} 
+0

Dzięki temu całkowicie rozwiązuję mój problem, dopóki nie pojawi się Swift 4 –

Powiązane problemy