Published: Oct 28, 2015
With the advent of protocol-oriented programming Swift types are able to adopt all sorts of super powers with minimal work.
But sometimes it’s not clear what that minimal work is. SequenceType, for example, simply requires that you implement func generate()
; you get everything else for free.
This article provides copy-pastable snippets that represent the minimal implementation required to conform to a given protocol. Please feel free to suggest additional implementations by tweeting @featherless with a GitHub gist.
#
ArrayLiteralConvertibleConforming types can be initialized with array literals.
<# type #> <# extendedType #> : ArrayLiteralConvertible { required init(arrayLiteral elements: <# elementType #>...) { self.<# storage #> = elements } }
Note that this init method can’t be defined in an extension.
#
CollectionTypeConformity to
CollectionType
simply requires implementing the methods ofIndexable
.
extension <# extendedType #> : CollectionType { var startIndex: <# indexType : ForwardIndexType #> { return <# startIndex #> } var endIndex: <# indexType : ForwardIndexType #> { return <# endIndex #> } subscript (index: <# indexType : ForwardIndexType #>) -> <# elementType #> { return <# subscript value #> } }
indexType
will usually be some type of Int which is a ForwardIndexType
.
#
HashableConforming types may be used in
switch
statements and as the element of aSet
.
extension <# extendedType #> : Hashable { var hashValue: Int { return <# hashValue #> } } func ==(lhs: <# extendedType #>, rhs: <# extendedType #>) -> Bool { return <# comparator #> }
#
SequenceTypeConforming types may be used in
for-in
statements.
extension <# extendedType #> : SequenceType { func generate() -> <# generatorType #><<# elementType #>> { <# generator state #> return anyGenerator { if <# terminal condition #> { return nil } <# iteration logic #> return nil } } }
A collection is a sequence, but a sequence isn’t necessarily a collection.