Тип расширения протокола Self не соответствует типам инициализатора

Скажем, для академических целей я бы предпочел выражение как

someInt.asDouble

а не сток

Double(someInt)

Поскольку все различные целочисленные типы Swift соответствуют IntegerType протокол И потому что, кажется, есть Double() инициализатор, который подходит для всех этих типов int, я подумал, что мог бы что-то вроде:

extension IntegerType {
    var asDouble:Double {
        return Double(self)
    }
}

Это не работает. И я хотел бы знать, почему? Я хотел бы знать, есть ли какая-то магия, которая заставила бы это работать? where может быть? Или что-то делать с self ссылка?

Ошибка, которую я получаю в консоли игровой площадки, которую я попробовал в этом, гласит:

Playground execution failed: /var/folders/2k/6y8rslzn1m95gjpg534j7v8jzr03tz/T/./lldb/41416/playground37.swift:31:10: error: cannot invoke initializer for type 'Double' with an argument list of type '(Self)'
                return Double(self)
                       ^
/var/folders/2k/6y8rslzn1m95gjpg534j7v8jzr03tz/T/./lldb/41416/playground37.swift:31:10: note: overloads for 'Double' exist with these partially matching parameter lists: (Double), (UInt8), (Int8), (UInt16), (Int16), (UInt32), (Int32), (UInt64), (Int64), (UInt), (Int), (Float), (Float80), (String), (CGFloat), (NSNumber)
                return Double(self)

1 ответ

Все IntegerType типы могут быть повышены до IntMax, а также IntMax может быть преобразован в Double,

extension IntegerType {
    var asDouble: Double {
        return Double(self.toIntMax())
    }
}

Как вы предлагаете, это не особенно полезная вещь (Double(x) является правильным синтаксисом), но это может быть полезно для других проблем.

Я бы продолжил шаблон stdlib, если бы собирался создать это. Шаблон toX() скорее, чем asX:

extension IntegerType {
    func toDouble() -> Double {
        return Double(self.toIntMax())
    }
}

Смотрите также toOpaque() а также toUIntMax(), as предлагает простую реинтерпретацию типа без копирования и var предполагает, что это свойство этой ценности. Это не то, что происходит. Вы фактически конвертируете его в другое значение, хранящееся в другом формате, которое может даже не совпадать. (Для больших целых чисел могут быть ошибки округления, такие как x != Int(x.toDouble()).)

Стоит также прочитать Попытка расширить IntegerType (и FloatingPointType); Почему нельзя преобразовать все типы Int в NSTimeInterval, в котором обсуждается проблема, а также почему подобные функции могут быть опасны, если не будут выполнены с большой осторожностью.

Другие вопросы по тегам