Skip to content

Instantly share code, notes, and snippets.

@jakebromberg
jakebromberg / PlayerLoader.swift
Created October 3, 2017 03:38
Takes out some of the pain from loading an AVPlayer object.
import AVFoundation
/// The `PlayerLoader` class provides a callback mechanism for consumers of `AVPlayer` when loading a resource.
/// AVFoundation works by an inconvenient series of APIs that rely on KVO for asynchronous operations. This class
/// eliminates the boilerplate that KVO imposes and makes the callsite much more clean.
public final class PlayerLoader: NSObject {
public typealias Callback = (AVPlayer) -> ()
/// The callback will initialize to a non-nil value. The callback is set to nil once it's invoked, at which time the
/// KVO observation is removed. This is necessary to avoid double-removing the KVO observation.
@jakebromberg
jakebromberg / Disposable.swift
Created October 14, 2017 20:47
Encapsulates the steps necessary to tear down some unit of work, typically an asynchronous operation like a network task.
import Foundation
/// `Disposable` encapsulates the steps necessary to tear down some unit of work, typically an asynchronous operation
/// like a network task.
public protocol Disposable {
/// Disposes the object. This may be invoked multiple times, but only performs its side-effects once.
func dispose()
}
extension URLSessionTask: Disposable {
extension Collection where Iterator.Element: Equatable {
/// Computes the indices of different elements between two collections. This is useful for updating table views
/// with row deletions and insertion
/// - Parameter other: the collection to compute the index difference
/// - Returns: a tuple with indices to delete and insert on `self` to create a collection equivalent to `other`
/// - Discussion: This algorithm does not work for collections with duplicate elements.
public func indexDifference(with other: Self) -> (deleted: [Index], inserted: [Index]) {
var (deleted, inserted): ([Index], [Index]) = ([], [])
extension RawRepresentable where RawValue: Numeric {
/// Returns all the values of a RawRepresentable whose RawValue is Numeric. This static property expressly exists
/// for enumerations, though can be used elsewhere. Works only for contiguous values.
/// Supposing we have:
/// ```
/// enum Counter {
/// case one, two
/// }
/// ```
/// then `Counter.allValues == [.one, .two]`.
@jakebromberg
jakebromberg / DataStreamer.swift
Created November 19, 2017 17:24
`DataStreamer` class is a `URLSessionDataTask` delegate that logs out incoming data
extension URL {
static var WXYCStream: URL {
return URL(string: "http://audio-mp3.ibiblio.org:8000/wxyc.mp3")!
}
}
class DataStreamer: NSObject, URLSessionDataDelegate {
func urlSession(_ session: URLSession, dataTask: URLSessionDataTask, didReceive data: Data) {
dump(data)
}
@jakebromberg
jakebromberg / Numeric+arc4random.swift
Last active November 25, 2017 22:21
Swifty wrapper around arc4random
import Foundation
public extension Numeric {
static func arc4random() -> Self {
var r: Self = 0
arc4random_buf(&r, Int(MemoryLayout<Self>.size))
return r
}
}
struct OrderedSet<Element: Comparable & Hashable> {
private let elements: [Element]
init<S: Sequence>(_ elements: S) where S.Element == Element {
let set = Set<Element>(elements)
let array = Array(set)
self.elements = array.sorted()
}
}
struct AnyEquatable: Equatable {
static func ==(lhs: AnyEquatable, rhs: AnyEquatable) -> Bool {
return lhs.isEqual(rhs.value)
}
private let isEqual: (Any) -> Bool
private let value: Any
init<T: Equatable>(_ value: T) {
self.value = value
extension Sequence {
func sorted<T: Comparable>(by keyPath: KeyPath<Element, T>, comparator: (T, T) -> Bool = { $0 < $1 }) -> [Element] {
return sorted(by: { (e1, e2) -> Bool in
return comparator(e1[keyPath: keyPath], e2[keyPath: keyPath])
})
}
}
let names = ["Alice", "Bob", "Charlie", "Dave"]
assert(names.sorted(by: \.count) == ["Bob", "Dave", "Alice", "Charlie"])
extension Collection {
/// Splits a collection into its first element and a SubSequence of the rest of its elements.
func split() -> (head: Element, tail: SubSequence)? {
guard let first = first else {
return nil
}
return (first, dropFirst())
}