Home > Blockchain >  Filter a nested arrays of structs and return the child object in swift
Filter a nested arrays of structs and return the child object in swift

Time:11-09

I have read multiple discussions about filtering nested arrays in swift, however they all return the parent object.

Let's have these simple data:

struct MenuSection: Identifiable {
    let id: id
    var name: String
    var menuRows: [MenuRow]
}

struct MenuRow: Identifiable, Hashable {
    let id: id
    var name: String
}

private let menuSections: [MenuSection] = [
    MenuSection(id: 0, name: "Menu Group 1", menuRows: [
        MenuRow(id: 0, name: "Menu 1")
    ]),
    MenuSection(id: 1, name: "Menu Group 2", menuRows: [
        MenuRow(id: 1, name: "Menu 2"),
        MenuRow(id: 2, name: "Menu 3")
    ])
]

My goal is to get the MenuRow with its id.

So, I create this function and it works:

func getMenuRowWithId(menuRowId: id) -> MenuRow? {
    for menuSection in menuSections {
        for menuRow in menuSection.menuRows {
            if menuRow.id == menuRowId {
                return menuRow
            }
        }
    }
    return nil
}

However, I want to do something more swifty (and maybe more efficient).

I tried something like:

var filtered = menuSections.filter { $0.menuRows.filter { $0.id == 1 }.count != 0  }

but it's returning the MenuSection containing the right MenuRow. => I only want the menuRow.

I have tried many things, such playing with compactMap/flatMap to flatten the array before filtering. No way.

How can I browse the menuSections and obtain ONLY the right menuRow ? Thanks

CodePudding user response:

You can use flatMap first to get all MenuRow objects in one array and then find the correct object in that array using first(where:)

let menuRow = menuSections.flatMap(\.menuRows).first(where: { $0.id == 1 })
  • Related