객체 배열을 Swift에서 세트로 줄이려고하는데 이것이 내 코드입니다.
objects.reduce(Set<String>()) { $0.insert($1.URL) }
그러나 오류가 발생합니다.
Type of expression is ambiguous without more context.
URL 유형이 확실히 String이기 때문에 문제가 무엇인지 이해하지 못합니다. 어떤 아이디어?
답변:
집합으로 만들기 위해 배열을 줄일 필요가 없습니다. 배열로 세트를 만듭니다 let objectSet = Set(objects.map { $0.URL })
..
let objectSet = Set(objects.map { $0.URL })
.
Swift 5.1에서는 문제를 해결하기 위해 다음 세 가지 예제 중 하나를 사용할 수 있습니다.
Array
의 map(_:)
방법 Set
의 init(_:)
초기화를가장 간단한 경우에는 초기 배열을 url
s ( String
) 배열에 매핑 한 다음 해당 배열에서 집합을 만들 수 있습니다. 아래 코드는 그 방법을 보여줍니다.
struct MyObject {
let url: String
}
let objectArray = [
MyObject(url: "mozilla.org"),
MyObject(url: "gnu.org"),
MyObject(url: "git-scm.com")
]
let urlArray = objectArray.map({ $0.url })
let urlSet = Set(urlArray)
dump(urlSet)
// ▿ 3 members
// - "git-scm.com"
// - "mozilla.org"
// - "gnu.org"
Array
의 reduce(into:_:)
방법을struct MyObject {
let url: String
}
let objectArray = [
MyObject(url: "mozilla.org"),
MyObject(url: "gnu.org"),
MyObject(url: "git-scm.com")
]
let urlSet = objectArray.reduce(into: Set<String>(), { (urls, object) in
urls.insert(object.url)
})
dump(urlSet)
// ▿ 3 members
// - "git-scm.com"
// - "mozilla.org"
// - "gnu.org"
대안으로 Array
의 reduce(_:_:)
방법을 사용할 수 있습니다 .
struct MyObject {
let url: String
}
let objectArray = [
MyObject(url: "mozilla.org"),
MyObject(url: "gnu.org"),
MyObject(url: "git-scm.com")
]
let urlSet = objectArray.reduce(Set<String>(), { (partialSet, object) in
var urls = partialSet
urls.insert(object.url)
return urls
})
dump(urlSet)
// ▿ 3 members
// - "git-scm.com"
// - "mozilla.org"
// - "gnu.org"
Array
확장 사용필요한 경우, 당신은 만들 수 있습니다 mapToSet
에 대한 방법 Array
소요 transform
폐쇄 매개 변수를과를 반환합니다 Set
. 코드 아래의 플레이 그라운드는 사용 방법을 보여줍니다.
extension Array {
func mapToSet<T: Hashable>(_ transform: (Element) -> T) -> Set<T> {
var result = Set<T>()
for item in self {
result.insert(transform(item))
}
return result
}
}
struct MyObject {
let url: String
}
let objectArray = [
MyObject(url: "mozilla.org"),
MyObject(url: "gnu.org"),
MyObject(url: "git-scm.com")
]
let urlSet = objectArray.mapToSet({ $0.url })
dump(urlSet)
// ▿ 3 members
// - "git-scm.com"
// - "mozilla.org"
// - "gnu.org"
reduce()
method는 결합 된 값 을 반환 하는 클로저를 기대 하지만 value의 insert()
메서드는 Set
아무것도 반환하지 않고 대신 기존 세트에 새 요소를 삽입합니다.
작동하게하려면 다음과 같은 작업을 수행해야합니다.
objects.reduce(Set<String>()) {
$0.union(CollectionOfOne($1.URL))
}
그러나 위의 내용은 약간의 불필요한 복잡성입니다. 큰 배열이 있다면 Swift가 objects
. @NRitH의 조언을 따르고 map()
한 번에 결과 세트를 만들 수 있으므로 사용하십시오 .
func reduce<T>(_ initial: T, @noescape combine combine: (T, Self.Generator.Element) throws -> T) rethrows -> T
이 당신이 전달하는 것이 아니라고 생각합니다.