Posted at

optionalな配列からnilを取り除く(compactMap)

Swiftプログラムのコードレビューをしていて、オプショナル型の配列をフィルタリングするコードを見かけました。

self.linkFiles.map{ getLinkFile($0) }.filter{ $0 != nil }.map{ path + "/" + $0! }

最後のmapの$0!の部分はforced-unwrapping(【Swift】Optional型を安全にunwrapしよう - Qiita) している。

できれば安全にアンラップされたデータを扱いたい。

そこでfilterの部分で、nilを取り除いて、アンラップされたデータだけの配列が手に入ればいいなと考えました。

Swiftならこんなケースには対応しているはず!! と思えたので調べてみると、スタックオーバーフローに答えがありました。

ただ、使用しているflatMapは非推奨となっているようで、compactMapをつかった以下のような書きかたが良いようです。

// Swift version 4.2.1 (swift-4.2.1-RELEASE)

struct Animal {
let name: String
}
let array:[Animal?] = [
nil,
Animal(name: "Tiger"),
nil,
Animal(name: "Lion")]
print( array )
//[
// nil,
// Optional(main.Animal(name: "Tiger")),
// nil,
// Optional(main.Animal(name: "Lion"))
//]

// 非推奨
// let filterd = array.flatMap{ $0 }
let filterd = array.compactMap{ $0 }

print( filterd )
//[
// main.Animal(name: "Tiger"),
// main.Animal(name: "Lion")
//]