Skip to main content

Posts

Showing posts from July, 2014

Swift: A list of all types and protocols that adopt, and inherit from, the Sequence protocol

Sequence For the use of generics in Swift it is important to understand the adoption and inheritance of protocols. Here are the types and protocol(s) that are adopted by Sequence (which is a top-level protocol that adopts no other protocols): struct EmptyGenerator struct EnumerateGenerator struct FilterGenerator struct FilterSequenceView struct GeneratorOf struct GeneratorOfOne struct GeneratorSequence struct IndexingGenerator struct LazySequence struct MapSequenceGenerator struct MapSequenceView struct PermutationGenerator struct RangeGenerator struct SequenceOf struct StrideThrough (note: might adopt Collection in future update instead) struct StrideTo (note: might adopt Collection in future update instead) struct UnsafeArrayGenerator struct Zip2 protocol Collection Collection Since the Collection protocol adopts the Sequence protocol, all types and protocols that adopt Collection also inherit the Sequence protocol. And the types and protocol(s) that adopt Collection are

Swift: Inheritance and generics in algorithms

Swift algorithms rely heavily on generics, but being generic doesn't necessarily mean that an algorithm can accept any instance type. Often the instance types that can be accepted by an algorithm are restricted to ones that adopt or inherit a certain protocol. For example extend() requires that the instance being extended adopts the Sequence protocol (S : Sequence) and that the extension is made up of elements of the same type as contained in the sequence being extended (hence T == T). func extend<S : Sequence where T == T>(sequence: S) So how do we know that extend(), for example, can accept both an array and a string? Well, the Array type adopts the MutableCollection protocol, which in turn adopts the Collection protocol, which finally adopts the Sequence protocol. This means that the Array type inherits the Sequence protocol down the chain and so we can do this: var array = ["one","two"] array.extend(["three","four"])

An A-Z of Swift Protocol Names (Xcode 6, beta 4)

There are 47 protocols listed in the Swift header file, here's the A-Z (or rather A-U) for reference. Those with colons are protocols that adopt other protocols. protocol AbsoluteValuable : SignedNumber protocol ArrayBound protocol ArrayLiteralConvertible protocol ArrayType : ExtensibleCollection, MutableSliceable, ArrayLiteralConvertible protocol BidirectionalIndex : ForwardIndex protocol BitwiseOperations protocol BooleanLiteralConvertible protocol CVarArg protocol CharacterLiteralConvertible protocol Collection : Sequence protocol Comparable : Equatable protocol DebugPrintable protocol DictionaryLiteralConvertible protocol Equatable protocol ExtendedGraphemeClusterLiteralConvertible protocol ExtensibleCollection protocol FloatLiteralConvertible protocol FloatingPointNumber : Strideable protocol ForwardIndex protocol Generator protocol Hashable : Equatable protocol Integer : RandomAccessIndex protocol IntegerArithmetic : Comparable protocol IntegerLiteralConvertible protocol

Swift: Using filter() to remove items from Arrays

Here's a quick and easy use of filter() var myArray = ["Explore","","#Swift","Algorithms"] var noEmptyStrings = myArray.filter({$0 != ""}) Filter can be called on an Array and simply requires that the Elements contained within the Array (in this case Strings) are tested in the closure and return a Bool value. Everything that returns true is then included in the filtered array, everything returning false is not. See earlier posts on algorithms ,  generics  and closures  for further information and guidance. Follow @sketchytech

Swift: Replacing the NSString method componentsSeparatedByCharactersInSet with a combination of the split() and find() algorithms

NSString method A Swift string instance is automatically bridged to NSString, so there's no work to be done in order to leverage the method componentsSeparatedByCharactersInSet . let myString = "Explore #Swift: Algorithms" let separated = myString.componentsSeparatedByCharactersInSet(NSCharacterSet(charactersInString: ":, .!")) However, doing so we not only need to employ the method itself and the NSCharacterSet class, but often what we then have is an array not only with the values we want but also with empty strings. As Apple outlines: Adjacent occurrences of the separator characters produce empty strings in the result. Similarly, if the string begins or ends with separator characters, the first or last substring, respectively, is empty. Apple Docs So we then need to perform a clean-up operation to delete these empty strings. Swift algorithms Our alternative to relying on the Cocoa Framework, in this instance, is instead to pass one of Swift&#

Swift: join() and split() explained

Using a method like join() is simple if we look inside the Swift header file (which can be accessed by pressing Command+click on any Swift Type in your code). There we see a simple and easy to follow example demonstrating that it takes a joining String and a String Array, something like this: let joined = join(", ",["Hello","Swift!"]) And if join() is so simple to understand, then it's counterpart split() should be equally simple to understand. Right? No, wrong. We are hit in the face with things like  Seq.GeneratorType.Element->R and expected to decipher them when there's little explanation of what this actually means in the documentation.  So let's start with the method's requirements: func split<Seq : Sliceable, R : LogicValue>(seq: Seq, isSeparator: (Seq.GeneratorType.Element) -> R, maxSplit: Int = default, allowEmptySlices: Bool = default) -> [Seq.SliceType] The first thing to note is that this is a ge