2016-12-26 1 views
6

Ошибка протокола has only one свойство локализованноеОписание. Я попытался создать пользовательский объект, унаследованный от NSObject и Error, но я не могу переопределить localizedDescription. Как я могу это сделать?Как переопределить localizedDescription для пользовательской ошибки в Swift 3?

Этот код не позволяет мне получить пользовательское описание:

class MyError: NSObject, Error { 
    var desc = "" 
    init(str: String) { 
     desc = str 
    } 
    override var description: String { 
     get { 
      return "MyError: \(desc)" 
     } 
    } 
    var localizedDescription: String { 
     get { 
      return self.description 
     } 
    } 
} 

func test_my_code() { 
    let error = MyError(str: "my test string") 
    let x = error as Error 
    print(x.localizedDescription) 
} 

Вызов функции «test_my_code» получить неожиданный результат: «Операция не может быть завершена ...».

Что мне делать, чтобы получить результат «MyError: моя тестовая строка»?

+0

Не вам нужно 'override' ? –

+0

Не можете ли вы расширить Error с новым свойством и затем прочитать это вместо этого? – Honey

+0

@SunilChauhan no. Ничего из протокола не следует переопределять. Добавление 'override' нарушит компиляцию. – Speakus

ответ

20

Документация о новой ошибке мостиковых функции недостаточно ясно еще сейчас, так что этот ответ может потребоваться некоторые обновления в ближайшем будущем, но, по словам SE-0112 и latest Swift source code, вам, возможно, придется использовать LocalizedError, а не Error и осуществлять errorDescription ,

class MyError: NSObject, LocalizedError { 
    var desc = "" 
    init(str: String) { 
     desc = str 
    } 
    override var description: String { 
     get { 
      return "MyError: \(desc)" 
     } 
    } 
    //You need to implement `errorDescription`, not `localizedDescription`. 
    var errorDescription: String? { 
     get { 
      return self.description 
     } 
    } 
} 

func test_my_code() { 
    let error = MyError(str: "my test string") 
    let x = error as Error 
    print(x.localizedDescription) 
} 
test_my_code() //->MyError: my test string 

Другие, чем при использовании LocalizedError, реализация этого по умолчанию работает:

(NSError.swift, ссылка показано выше)

public extension Error { 
    /// Retrieve the localized description for this error. 
    var localizedDescription: String { 
     return NSError(domain: _domain, code: _code, userInfo: nil).localizedDescription 
    } 
} 

Это немного сложнее, как Swift определяет _domain или _code от произвольных типов, только соответствующих Error, но кажется, что NSError генерирует "The операция не может быть завершена ... »для неизвестных комбинаций домена и кода.

+0

Отлично! Я боролся с этим и сделал уродливые переключатели/случаи. Работает как шарм! – denis631

2

Если пользовательский тип соответствует протоколу CustomStringConvertible и обеспечивает локализованное description, то следующее расширение LocalizedError может быть полезным:

extension LocalizedError where Self: CustomStringConvertible { 

    var errorDescription: String? { 
     return description 
    } 
} 

Пример кода:

class MyError: LocalizedError, CustomStringConvertible { 

    let desc: String 

    init(str: String) { 
     desc = str 
    } 

    var description: String { 
     let format = NSLocalizedString("Operation error: %@", comment: "Error description") 
     return String.localizedStringWithFormat(format, desc) 
    } 
} 


let error = MyError(str: "my test string") 
let x = error as Error 
print(x.localizedDescription) // Prints "Operation error: my test string" 
print(String(describing: x)) // Prints "Operation error: my test string" 

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

  • Нет связанных вопросов^_^