[swift-evolution] Allowing enum extensions to also be able to expand case options

Paul Cantrell cantrell at pobox.com
Thu Jun 30 16:23:20 CDT 2016


> On Jun 30, 2016, at 3:54 PM, Dan Appel <dan.appel00 at gmail.com> wrote:
> 
> That is the current workaround (as the proposal mentions), but it is still missing support for enum features such as associated values and the pattern matching power that they bring.

Fair enough, it would be hard to generalize pattern matching to this approach. Associated types are a whole other kettle of fish.

> Also, by locking your OpenEnum conformers to reference types, you lose out on the value-semantics (very important, even for enums), and bring in the extra weight that a class is.

The class approach is the more lightweight option when you aren’t trying to get associated-value-like behavior.

There’s a fixed pool of instances, one per possible value, so there’s no per-usage allocation overhead. All one passes around are references to those fixed instances, so passing and comparing values is a one-word operation. The class is final, so any method dispatch is static.

Finally, you get the simplicity of leaning on pointer uniqueness to give you case uniqueness. Nothing to sneeze at there.

• • •

If you’re looking to have associated type-like behavior _and_ open cases, then yes, this “unique instances” approach breaks down.

At that point, though, why not just use a collection of separate struct types implementing a shared protocol?

    public protocol FileError: ErrorProtocol { }

    struct FileNotFound: FileError {
      let path: String
    }

    struct CorruptedFile {
      let bytes: [Int8]
    }

    func handleFileError(error: FileError) {
      switch(error) {
        case is CorruptedFile:
          print("Bummer")
        case let fileNotFound as FileNotFound:
          print("Can’t find \(fileNotFound.path)")
      }
    }

Here the dynamic type takes on the role of the enum value, and case let x as X gives you must of what associated types give.

Separate struct types are what I use for the problem the proposal mentions — structured, matchable errors with diagnostic data — and it does work out nicely in practice. Nicer, in fact; I’d say that this:

    if error is FileError { … }

…is easier to read and to remember than this:

    if case .fileError = error { … }

Cheers,

Paul

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20160630/a8e5be1b/attachment.html>


More information about the swift-evolution mailing list