はじめに
Core MLを使っていると、モデルの出力がMLMultiArrayとして返されることがよくあります。特に一次元のMLMultiArrayを扱う際に、それをSwiftのArrayに変換したいと思うことがあったのですが、情報が少ないためか何気に時間を取られてしまいました。
MLMultiArrayとは
MLMultiArrayは、Core MLが多次元の数値データを扱うためのデータ構造です。画像や音声、テキストなどのデータをモデルに渡す際や、モデルからの出力を受け取る際に使用されます。MLMultiArrayは、多次元配列を表現するために使われるため、一次元だけでなく、二次元や三次元のデータも扱うことができます。
MLMultiArrayをArrayに変換
private func mlMultiArrayToDoubleArray(_ multiArray: MLMultiArray) -> [Double] {
let length = multiArray.count
let doublePtr = multiArray.dataPointer.bindMemory(to: Float16.self, capacity: length) // Float16はモデルのデータ型に合わせて変更
let doubleBuffer = UnsafeBufferPointer(start: doublePtr, count: length)
let output = Array(doubleBuffer).compactMap { Double($0) }
return output
}
multiArray.dataPointerはMLMultiArrayのデータが格納されているメモリ領域へのポインタで、bindMemory(to:capacity:)メソッドを使ってFloat16型として扱っています。このデータ型はモデルの型に合わせて変更してください。さらにUnsafeBufferPointerでメモリ領域を安全にアクセスするためのバッファを作成し、ポインタを介して直接メモリにアクセスできるようにしているのがミソです。