2015-12-03 1 views
4

Есть ли способ, используя обобщения и ограничения типа, свернуть первые два случая этого enum в один?Конец случая с ассоциированным значением родового типа с ограничениями

enum AllowedValueRange { 

    // Associated value represents (min, max). 'nil' represents 
    // "no limit" for that interval end (+/- infinity) 
    case IntegerRange(Int?, Int?) 


    // Associated value represents (min, max). 'nil' represents 
    // "no limit" for that interval end (+/- infinity) 
    case FloatRange(Float?, Float?) 


    // A finite set of specific values of any type 
    case ArbitrarySet([Any]) 

    // (...Other cases with different structure of associated values 
    // or no associated values...) 
} 

Добавление: Я знаю, что могу указать общий тип для всей enum, но только эти два типа нужен. Кроме того, я думаю, что она должна соответствовать как Equatable и Comparable, но я не могу достаточно найти синтаксис для указания, что ...


EDIT: (?) Оказывается Comparable содержит Equatable, поэтому, возможно, я могу это сделать:

enum AllowedValueRange { 

    // Associated value represents (min, max). 'nil' represents 
    // "no limit" for that interval end (+/- infinity) 
    case NumericRange((min:Comparable?, max:Comparable?)) 

    // (rest omitted) 

(также включен пару ассоциированных значений с одним, по имени кортеж из двух значений)

ответ

3

Вы могли определить

enum AllowedValueRange { 
    case NumericRange((min:Comparable?, max:Comparable?)) 
} 

но позволит вам создать экземпляр значения с двумя несвязанный сравнимых типов, например

let range = AllowedValueRange.NumericRange((min: 12, max: "foo")) 

, который, вероятно, не то, что вы хотите. Поэтому вам нужен общий тип (который может быть сопоставим):

enum AllowedValueRange<T: Comparable> { 
    case NumericRange((min:T?, max:T?)) 
} 
+0

Я вижу. Единственное, что мне не нравится в этом решении, это то, что мне действительно не нужно 'T' в любом другом случае; Я бы хотел объявить его только для 'NumericRange', а не для всего' enum'. Думаю, это лучшее, что я могу получить. –

+0

То есть, я бы хотел, чтобы было законно объявлять: 'enum AllowedValueRange {case NumericRange ((min: T ?, max: T?))/* ... * /}' –

+1

@NicolasMiari: Я вижу, но я не думаю, что это возможно. –

Смежные вопросы