大きなデータ ブロックの処理に関する私の最近の質問に密接に関連して、大きな不変データ ブロックを取得し、いくつかの操作で変更可能にし、完了したら再び不変にする必要があるところまで来ました。
少なくとも純粋な外観を保持したいので、可変データは元の不変データの可変コピーになります。参考までに、実世界の Haskell でブルーム フィルターの例を見ていますが、runST で実際にコードを実行できないことがわかりました。
私のデータ構造、最初は純粋なもの、次に不純なもの:
import Data.Vector.Unboxed (Vector)
import Data.Vector.Unboxed.Mutable (MVector)
data PixelMap = Bitmap Int Int (Vector Bool)
data MPixelMap s = MBitmap Int Int (MVector s Bool)
次に、基本的な newBitmapM 関数を作成します。
newBitmapM :: (Int, Int) -> ST s (MPixelMap s)
newBitmapM (width, height) = MBitmap width height `liftM` MV.replicate (width * height) False
これは問題なく GHCI に読み込まれますが、実行してみます。
> runST $ newBitmapM (15, 15)
<interactive>:78:9:
Couldn't match type `a' with `PixelMapMutable s'
`a' is a rigid type variable bound by
the inferred type of it :: a at <interactive>:78:1
Expected type: ST s a
Actual type: ST s (PixelMapMutable s)
In the return type of a call of `newBitmapM'
In the second argument of `($)', namely `newBitmapM (15, 15)'
In the expression: runST $ newBitmapM (15, 15)
このエラー メッセージは、私にはまったく意味がありません。 a
の型で定義されている は、runST
ポリモーフィックである必要があるため、まったく「固定」されていません。誰かがこれを十分にデコードして、コードの何が実際に間違っているかを教えてもらえますか?