Swift y Objective-C

throws y Result en Swift: conserva la causa del fallo

Compara errores convertidos en nil por try? con typed throws y resultados almacenados; usa get para recuperar valores o volver a lanzar errores.

2 min de lectura
Imagen de portada de throws y Result en Swift: conserva la causa del fallo

Si fallos distintos requieren acciones distintas, consérvalos con throws o Result en lugar de borrarlos con try?. throws propaga errores durante la llamada; Result guarda éxito o fallo como valor para tratarlo después.

Mecanismo y decisión de diseño

ParseError distingue una entrada no numérica de un número negativo. throws(ParseError) declara el tipo del error y permite responder con do-catch. try? convierte ambos fallos en nil, insuficiente cuando las políticas de recuperación difieren. Fuente primaria

Código reproducible

Pasa cat, -1, 0 y 42 por el mismo analizador. Comprueba que try? produce nil en ambos fallos y guarda los resultados como Result<Int, ParseError>. Un bloque do tipado explicita el tipo capturado; get recupera éxitos o vuelve a lanzar fallos.

Este ejemplo independiente se ejecutó el 2026-10-23 con Apple Swift 6.4 para arm64 macOS, en modo de lenguaje Swift 6. No necesita red ni paquetes adicionales.

Descargar el archivo Swift completo

Ejecuta el comando en la carpeta de descarga. Las precondiciones detienen la ejecución si falla una comprobación. No uses -Ounchecked: elimina estas comprobaciones.

swift -swift-version 6 swift-error-handling-throws-result.swift
enum ParseError: Error, Equatable { case notInteger, negative }
func parse(_ raw: String) throws(ParseError) -> Int {
    guard let value = Int(raw) else { throw .notInteger }
    guard value >= 0 else { throw .negative }
    return value
}

precondition((try? parse("cat")) == nil && (try? parse("-1")) == nil)
let results: [Result<Int, ParseError>] = ["cat", "-1", "0", "42"].map { raw in
    do throws(ParseError) { return .success(try parse(raw)) }
    catch { return .failure(error) }
}
precondition(results == [.failure(.notInteger), .failure(.negative), .success(0), .success(42)])
do {
    _ = try results[1].get()
    preconditionFailure("failure was lost")
} catch ParseError.negative {}
let recovered = try results[3].get()
precondition(recovered == 42)
print("try?-failures=nil,nil result=notInteger,negative,0,42 get-error=negative")

Salida registrada e interpretación

try?-failures=nil,nil result=notInteger,negative,0,42 get-error=negative

El array conserva notInteger, negative, 0 y 42 por separado. get sobre el fallo vuelve a lanzar negative; sobre el éxito devuelve 42. Esta verificación de conservación de información no necesita red ni E/S de archivos.

Alcance y limitaciones

throws no captura todos los fallos del programa. Las trampas por desempaquetado forzado o precondiciones incumplidas quedan fuera del contrato. Un try! fallido tampoco es recuperación normal. Solo se ejecutó análisis síncrono, no cancelación asíncrona, reintentos ni errores de archivos.

Qué comprobar después

Define casos de error según las acciones que el llamador pueda distinguir. Usa Optional para ausencia simple, throws para causas y Result para guardar o agregar resultados. Conecta mensajes y registros en un límite que conserve la causa real.

Experimento relacionado

Fuentes y verificación

  • The Swift Programming Language: Error HandlingSwift.org · Documentación oficial · Consultado 23 de octubre de 2026Respalda: Fuente del contrato de implementación y de la explicación. La salida se comprobó por separado con el experimento incluido aquí.