Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Generic sum() and mean() extensions for Swift numeric collections
/// To use reduce() to sum a sequence, we need
///
/// - a zero (identity) element
/// - an addition operator
protocol Summable {
/// Identity element for this type and the + operation.
static var Zero: Self { get }
/// + operator must be defined for this type
func +(lhs: Self, rhs: Self) -> Self
}
extension SequenceType where Generator.Element: Summable {
/// Return sum of all values in the sequence
func sum() -> Generator.Element {
return self.reduce(Generator.Element.Zero, combine: +)
}
}
// Define Zero for Int, Double, and String so we can sum() them.
//
// Extend this to any other types for which you want to use sum().
extension Int: Summable {
/// The Int value 0
static var Zero: Int { return 0 }
}
extension Double: Summable {
/// The Double value 0.0
static var Zero: Double { return 0.0 }
}
extension String: Summable {
/// Empty string
static var Zero: String { return "" }
}
/// A generic mean() function requires that we be able
/// to convert values to Double.
protocol DoubleConvertible {
/// Return value as Double type
var doubleValue: Double { get }
}
// Define doubleValue() for Int and Double.
//
// Extend this to any other types for which you want
// to use mean().
extension Int: DoubleConvertible {
/// Return Int as Double
var doubleValue: Double { return Double(self) }
}
extension Double: DoubleConvertible {
/// Return Double value
var doubleValue: Double { return self }
}
extension CollectionType where
Generator.Element: DoubleConvertible,
Generator.Element: Summable,
Index.Distance: DoubleConvertible {
/// Return arithmetic mean of values in collection
func mean() -> Double {
assert(!self.isEmpty, "cannot calculate mean of empty collection")
return self.sum().doubleValue / self.count.doubleValue
}
}
// Examples
[1, 2, 3, 4, 5].sum() // 15
[1.1, 2.2, 3.3, 4.4, 5.5].sum() // 16.5
["a", "b", "c", "d", "e"].sum() // "abcde"
[1, 2, 3, 5].mean() // 2.75
[0.4, 1.2, 3.2].mean() // 1.6
@knguyen2708

This comment has been minimized.

Copy link

commented Apr 28, 2017

Awesome work man!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.