简体   繁体   English

Swift:在数组中查找值并返回特定键

[英]Swift: Find value in array and return specific key

Im new to swift and would appreciate your help.. 我是swift的新手,非常感谢你的帮助..

Problem: 问题:

In my future project I would love to look for a specific String in an Array and get only the names back who have this value in their hobbies Array. 在我未来的项目中,我很乐意在数组中查找特定的字符串,并获取在其爱好数组中具有此值的名称

My example: 我的例子:

struct Person {
var name: String
var hobbies:Set <String>
}

var persons: [Person]

persons = [

Person(name: "Steve", hobbies: ["PC", "PS4", "Gaming", "Basketball"]),
Person(name: "Max", hobbies: ["Gaming", "Xbox", "cooking", "PC"]),
Person(name: "Julia", hobbies: ["Soccer", "Tennis", "cooking", "Painting"])

]

var StringToSearch = "PC"

I would love to get only the names back who hobbies "PC" is. 我很想得到只有爱好“PC”的名字。 How can I iterate through my collection and get only the keys instead of the values back like in a dictionary? 如何迭代我的集合并只获取键而不是字典中的值? Thank you! 谢谢!

Use flatMap : 使用flatMap

let result = persons.flatMap {
    $0.hobbies.contains(StringToSearch) ? $0.name : nil
}

Using filter(_:) 使用filter(_:)

let stringToSearch = "PC"
let pcHobbiests = persons.filter { $0.hobbies.contains(stringToSearch) }
let pcHobbiestNames = persons.map { $0.name }

Explaination

filter(_:) will iterate over elements of a Sequence , building up a new Array containing only those elements for which closure evaluates to true. filter(_:)将迭代Sequence元素,构建一个新的Array,其中只包含闭包计算结果为true的元素。 In this instance, the closure checks if the hobbies Array of the currently iteration's Person contains stringToSearch . 在这个例子中,闭包检查当前迭代的Personhobbies Array是否包含stringToSearch

You can then iterate over your pcHobbiests Array or use them as you please: 然后,您可以迭代pcHobbiests数组或随意使用它们:

for pcHobbiest in pcHobbiests {
    print(pcHobbiest)
}

you can use filter + map to return name array of all people who have "PC" hobbies: 你可以使用filter + map返回所有拥有“PC”爱好的人的名字数组:

let nameArray = persons.filter{$0.hobbies.contains("PC")}.map{$0.name}
//return ["Steve", "Max"]

Using reduce 使用reduce

After map , filter and flatMap here's my solution with reduce :) mapfilterflatMap这里是我的解决方案, reduce :)

let names = persons.reduce([String]()) { (names, person) -> [String] in
    guard person.hobbies.contains(keyword) else { return names }
    return names + [person.name]
}

One liner (but don't do it at home!) 一个班轮(但不要在家里做!)

And if your really want to write everything on 1 line... 如果你真的想在一行写一切......

let names = persons.reduce([String]()) { $0.0 + ($0.1.hobbies.contains(keyword) ? [$0.1.name] : []) }

Use Swift's for-in loop. 使用Swift的for-in循环。

for pers in persons {
    if pers.hobbies.contains(StringToSearch) {
        nameOfPCGamer = pers.name
    }
}

You may use a loop, collect: 你可以使用循环,收集:

for p in persons {
  if p.hobbies.contains("PC") {
    // then you've got one!
  }
}

or you can use a more generic programming by filtering the array, thus obtaining an array of filtered content and iterating on it: 或者您可以通过过滤数组来使用更通用的编程,从而获得过滤内容的数组并对其进行迭代:

for p in persons.filter({$0.hoobies.contains("PC")}) {
  // got one...
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM