Skip to content

Commit

Permalink
Merge pull request #25 from rkukuh/dev
Browse files Browse the repository at this point in the history
Add `countBy` extensions to Set and Dictionary
  • Loading branch information
rkukuh authored Apr 8, 2023
2 parents c9df7c8 + e68425b commit c27c289
Show file tree
Hide file tree
Showing 6 changed files with 102 additions and 0 deletions.
24 changes: 24 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -289,6 +289,30 @@ let countByResult = emails.countBy { (email) -> String in
print(countByResult) // // ["gmail.com": 2, "yahoo.com": 1]
```

#### Dictionary

```swift
let userAges = ["Alice": 30, "Bob": 28, "Carlos": 30, "David": 28]

let countByResult = userAges.countBy { (name, age) -> Int in
return age
}

print(countByResult) // [28: 2, 30: 2]
```

#### Set

```swift
let emails: Set = ["[email protected]", "[email protected]", "[email protected]"]

let countByResult = emails.countBy { (email) -> String in
return (email as! String).components(separatedBy: "@").last ?? ""
}

print(countByResult) // ["gmail.com": 2, "yahoo.com": 1]
```

### `sum`

The `sum` method returns the sum of all items in the collection.
Expand Down
17 changes: 17 additions & 0 deletions Sources/SwiftCollections/CountBy/DictionaryCountByExtensions.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
//
// DictionaryCountByExtensions.swift
//
//
// Created by R. Kukuh on 08/04/23.
//

import Foundation

public extension Dictionary {
func countBy<T: Hashable>(_ transform: (Key, Value) -> T) -> [T: Int] {
return reduce(into: [:]) { (counts, keyValue) in
let key = transform(keyValue.key, keyValue.value)
counts[key, default: 0] += 1
}
}
}
17 changes: 17 additions & 0 deletions Sources/SwiftCollections/CountBy/SetCountByExtensions.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
//
// SetCountByExtensions.swift
//
//
// Created by R. Kukuh on 08/04/23.
//

import Foundation

public extension Set {
func countBy<T: Hashable>(_ transform: (Element) -> T) -> [T: Int] {
return reduce(into: [:]) { (counts, element) in
let key = transform(element)
counts[key, default: 0] += 1
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ class ArrayCountByTests: XCTestCase {

func testArrayCountByClosure() {
let emails = ["[email protected]", "[email protected]", "[email protected]"]

let countByResult = emails.countBy { (email) -> String in
return email.components(separatedBy: "@").last ?? ""
}
Expand Down
21 changes: 21 additions & 0 deletions Tests/SwiftCollectionsTests/CountBy/DictionaryCountByTests.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
//
// DictionaryCountByTests.swift
//
//
// Created by R. Kukuh on 08/04/23.
//

import XCTest
@testable import SwiftCollections

class DictionaryCountByClosureTests: XCTestCase {
func testDictionaryCountByClosure() {
let userAges = ["Alice": 30, "Bob": 28, "Carlos": 30, "David": 28]
let countByResult = userAges.countBy { (name, age) -> Int in
return age
}

XCTAssertEqual(countByResult[30], 2, "The count for age '30' should be 2")
XCTAssertEqual(countByResult[28], 2, "The count for age '28' should be 2")
}
}
22 changes: 22 additions & 0 deletions Tests/SwiftCollectionsTests/CountBy/SetCountByTests.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
//
// SetCountByTests.swift
//
//
// Created by R. Kukuh on 08/04/23.
//

import XCTest
@testable import SwiftCollections

class SetCountByClosureTests: XCTestCase {
func testSetCountByClosure() {
let emails: Set = ["[email protected]", "[email protected]", "[email protected]"]

let countByResult = emails.countBy { (email) -> String in
return (email as! String).components(separatedBy: "@").last ?? ""
}

XCTAssertEqual(countByResult["gmail.com"], 2, "The count for 'gmail.com' should be 2")
XCTAssertEqual(countByResult["yahoo.com"], 1, "The count for 'yahoo.com' should be 1")
}
}

0 comments on commit c27c289

Please sign in to comment.