If an enumeration instance with a default value (or garbage) doesn't really matter
enum MessageType { case audio(String) case photo case text } protocol SneakyEquatableMessage { func equals(message: MessageType) -> Bool } extension MessageType: SneakyEquatableMessage { func equals(message: MessageType) -> Bool { switch (self, message) { case (.audio(_), .audio(_)), (.photo, .photo), (.text, .text): return true default: return false } } } class Handler { let allowed: [MessageType] init(_ allowed: [MessageType]) { self.allowed = allowed } func canHandle(_ messageType: MessageType) -> Bool { return allowed.contains { $0.equals(message: messageType) } } }
Main use
let handler = Handler([.audio(""), .photo]) print(handler.canHandle(.text)) // Prints false print(handler.canHandle(.audio("abc")) //Prints true
The default values โโ(or garbage) are unrealistic
This particular section is more specific in this context, but in the end you will have a breakdown of your listing in some way on Swift 4 .. This is my suggestion: Injection of the Factory Template inside Handler . This completely eliminates all your problems without touching the switch in the Handler or additional ones.
enum DisassembledMessage { case audio case photo case text } protocol MessageTypeFactory { func disassemble(message: MessageType) -> DisassembledMessage func disassemble(messages: [MessageType]) -> [DisassembledMessage] } class Handler { let allowed: [MessageType] let factory: MessageTypeFactory init(allowed: [MessageType], with factory: MessageTypeFactory) { self.allowed = allowed self.factory = factory } func canHandle(_ messageType: DisassembledMessage) -> Bool { return factory .disassemble(messages: allowed) .contains { $0 == messageType } } }
Main use
let audioValue: Audio = //... let audioMessage = MessageType.audio(audioValue) let factory: MessageTypeFactory = //... let handler = Handler(allowed: [audioMessage, .photo], with: factory) print(handler.canHandle(.text)) // Prints false print(handler.canHandle(factory.disassemble(message: audioMessage))) //Prints true
Perhaps you are asking: wait ... you just created another enumeration (also this is just an example, you can convert it to any of what you want in this protocol). Well, I say: the enum you use is from the library ... see the section of my notes. In addition, you can now use this Factory anywhere to break the type of library into something, including inside the Handler . You could easily extend the MessageTypeFactory protocol to convert your enumeration to the other types (hopefully the behavior) that you created, and basically just distance yourself from the type of library when you need to. Hope this helps clarify what I was aiming for! I donโt even think you should store MessageType in your class. You must save your own type, which is some display version of MessageType , such as DisassembledType .
Hope this helps!
Notes
A few things:
- I'm sorry that your soul belongs to the library, really.
- Use an adapter template. Clean C ++ is one of many places where you can find out about it. Do not pollute your entire code base with one of their types! This is just a clue.
- I know that you said you donโt want to use the switch ... but you are working with enumerations ... At least it's in an enumeration!
- Use your own types! (Did I say that?)
- Use the adapter template! (Stop him.)
source share