AppleBee
AppleBee

Reputation: 1219

Get list of indexes using Array.filter instead of objects

is there any way to get list of filtered indexes instead of objects.

class Object
{
 var name
 var goal
}

var array<Object> = Array<Object>()

var filteredIndexes = array.filter{$0.name = "Sane"} // How to implement this?

Upvotes: 2

Views: 313

Answers (3)

Martin R
Martin R

Reputation: 539685

As Lame said above, the solution from Return an array of index values from array of Bool where true can be adapted to this case:

let filteredIndices = objects.enumerated().flatMap { $0.element.name == "Sane" ? $0.offset : nil }

One could also define a custom extension

extension Sequence {
    func indices(where predicate: (Element) -> Bool ) -> [Int] {
        return enumerated().flatMap { predicate($0.element) ? $0.offset : nil }
    }
}

which is then used as

let filteredIndices = objects.indices(where: { $0.name == "Sane" })

Remark: In Swift 4.1, this flatMap() method has been renamed to compactMap()

Upvotes: 1

Eugene
Eugene

Reputation: 10045

let animals = ["cat", "dog", "cat", "dog", "cat"]
let indexes = animals.enumerated().filter({ return $1 == "cat" }).map { return $0.offset }
print(indexes)

prints out [0, 2, 4]

Upvotes: 2

David Pasztor
David Pasztor

Reputation: 54706

There are several ways to achieve your goal. For instance, you can filter Array.indices instead of the array itself.

Self contained example:

struct Object {
    let name:String
    let goal:String
}

let objects = [Object(name: "John", goal: "a"),Object(name: "Jane", goal: "a"),Object(name: "John", goal: "c"),Object(name: "Pete", goal: "d")]
let nameToBeFound = "John"
let filteredIndices = objects.indices.filter({objects[$0].name == nameToBeFound}) //[0,2]

Upvotes: 2

Related Questions