ios swift swift2 ios9 eventkit

ios - Encuentre la condición de coincidencia del primer elemento en la matriz Swift(por ejemplo, EKSource)



swift2 ios9 (6)

Probemos algo más funcional:

public extension Sequence { func find(predicate: (Iterator.Element) throws -> Bool) rethrows -> Iterator.Element? { for element in self { if try predicate(element) { return element } } return nil } }

¿Qué tiene de bueno esto?
Obtienes acceso a element o i mientras buscas. Y es funcional.

Me gustaría encontrar el primer EKSource de tipo EKSourceType.Local con una expresión de "única" línea en Swift. Esto es lo que tengo actualmente:

let eventSourceForLocal = eventStore.sources[eventStore.sources.map({ $0.sourceType }) .indexOf(EKSourceType.Local)!]

¿Hay una forma mejor de hacerlo (como sin mapear y / o con una versión genérica de find )?


Alternativamente en Swift3 puedes usar:

let local = eventStore.sources.first(where: {$0.sourceType == .Local})


Hay una versión de indexOf que requiere un cierre de predicado; indexOf para encontrar el índice de la primera fuente local (si existe) y luego use ese índice en eventStore.sources :

if let index = eventStore.sources.indexOf({ $0.sourceType == .Local }) { let eventSourceForLocal = eventStore.sources[index] }

Alternativamente, podría agregar un método de find genérico a través de una extensión en SequenceType :

extension SequenceType { func find(@noescape predicate: (Self.Generator.Element) throws -> Bool) rethrows -> Self.Generator.Element? { for element in self { if try predicate(element) { return element } } return nil } } let eventSourceForLocal = eventStore.sources.find({ $0.sourceType == .Local })

(¿Por qué no está ya allí?)


No entiendo por qué estás usando el map en absoluto. ¿Por qué no usar filter ? Luego terminarás con todas las fuentes locales, pero en realidad, probablemente solo habrá una o ninguna, y puedes averiguarlo fácilmente preguntando por la primera (será nil si no hay una):

let local = eventStore.sources.filter{$0.sourceType == .Local}.first


Para Swift 3 tendrá que hacer algunos pequeños cambios en la respuesta de Nate anterior. Aquí está la versión Swift 3:

if let firstMatch = yourArray.first{$0.id == lookupId} { print("found it: /(firstMatch)") } else { print("nothing found :(") }

Cambios: SequenceType > Sequence , Self.Generator.Element > Self.Generator.Element


La solución Swift 4 que también maneja la situación cuando no hay elementos en su matriz que coincidan con su condición:

let arr = [0,1,2,3] let result = arr.lazy.map{print("💥");return $0}.first(where: {$0 == 2}) print(result)//3x 💥 then 2