私は、van Laarhovenのisomorphism lensesの小さな例に興味があり、data BValue = BValue { π :: Float, σ :: Float, α :: Float } deriving Show
(具体的にはget/set/modify関数)のようなデータ型に適用されます。前もって感謝します。同形レンズ
同形レンズ
答えて
バンLaarhovenのポストから、Lens
タイプは
data Lens a b = forall r . Lens (Iso a (b, r))
だから、我々の場合にはa
がBValue
であり、我々は1つ以上の要素を取り出すいくつかのlenesesを構築したいです。例えば、πを選ぶレンズを作ってみましょう。
piLens :: Lens BValue Float
だから、Float
へBValue
からレンズになるだろう
piLens = Lens (Iso {fw = piFwd, bw = piBwd})
レンズは2つのことを選び出す(ラベルパイトリプルで、すなわち最初の1、。):残留r
(ここでは省略されているため、haskellに存在する型を明示的に指定する必要がないため)と同型性があります。同型写像は順方向関数と逆方向関数から構成されます。
piFwd :: BValue -> (Float, (Float, Float))
piFwd (BValue {pi, sigma, alpha}) = (pi, (sigma, alpha))
forward関数は、必要なコンポーネントを単離します。ここでの残差タイプは「残りの部分」、つまりシグマとアルファフロートのペアです。
piBwd :: (Float, (Float, Float)) -> BValue
piBwd (pi, (sigma, alpha)) = BValue { pi = pi, sigma = sigma, alpha = alpha }
backward機能は類似しています。
ここで、BValue
のπ成分を操作するためのレンズを定義しました。
他の7つのレンズは類似しています。 (7つのレンズ:シグマとアルファを選び、可能なすべてのペアを選び(注文を無視して)、BValue
をすべて取り出し、()
を選んでください。
私が確信していることはわかりませんが、私が書いたfwとbwの機能があまりにも厳しいと少し気になります。わからない。
我々はまだ行われていません。
は、我々はまだpiLens
が実際にレンズの法律を尊重していることを確認する必要があります。 van LaarhovenのLens
の定義についての素敵なことは、同形法則を調べるだけでいいということです。彼のブログ記事では、レンズの法則が計算されています。
だから、私達の証明の義務は以下のとおりです。
fw piLens . bw piLens = id
bw piLens . fw piLens = id
どちらの証明がpiFwd
とpiBwd
の定義と構成に関する法律から直接従ってください。
をチェックしてください。これは、レコードタイプのレンズを実装しています。
このパッケージを説明するために、次の2つのデータ型の例を考えてみましょう。
import Data.Label import Prelude hiding ((.), id) data Person = Person { _name :: String , _age :: Int , _isMale :: Bool , _place :: Place } data Place = Place { _city , _country , _continent :: String }
両方のデータ型は、すべてのラベルにアンダースコアを前に付けたレコード型です。この下線は、テンプレートハスケルコードがこれらのフィールドのレンズを取得するためのコードです。派生レンズは、この単純なワンライナーで行うことができます。
$(mkLabels [''Person, ''Place])
レンズが作成されますすべてのラベルについて。
この例を見てみましょう。この71歳の仲間、私の隣人は例として彼を使用して気にしなかった、ヤンと呼ばれる:私たちは月が本当に彼は我々が取得するには、Get関数を使用することができると主張ほど古いことを確認したい
jan :: Person jan = Person "Jan" 71 True (Place "Utrecht" "The Netherlands" "Europe")
年齢は整数として計算されます。
hisAge :: Int hisAge = get age jan
今はアムステルダムに移りたいと思っています。あなたの昔を過ごすにはどんな良い場所でしょうか。組成物を用いて、我々は、構造体の内部の深い街の値を変更することができます。
moveToAmsterdam :: Person -> Person moveToAmsterdam = set (city . place) "Amsterdam"
そして今:(。)
ghci> moveToAmsterdam jan Person "Jan" 71 True (Place "Amsterdam" "The Netherlands" "Europe")
組成物はControl.Categoryモジュールの一部であるオペレータを使用して行われます。このモジュールをインポートして、Haskell Preludeからデフォルト(。)、id関数を隠すようにしてください。
- 1. レンズ
- 2. レンズ
- 3. レンズ/
- 4. レンズ
- 5. デュアル魚眼レンズ映像を正方形に変換する
- 6. three.jsに凸レンズの形状を描く方法
- 7. scalazレンズは、
- 8. 対物レンズのカプセル化
- 9. 広角レンズ校正とOpencv
- 10. HaskellのMVCフレームワーク用レンズ
- 11. レンズを関数に渡す
- 12. レンズとジッパー付きトラバーサルツリー
- 13. レンズの使い方は?
- 14. 対物レンズCで2つのマルチスレッドを同時に実行するには?
- 15. 同形アプリケーションのユーザープロフィール
- 16. エラービル - 同形のApp
- 17. 「to」レンズでジッパーに踏み込む
- 18. 逆レンズの名前は何ですか?
- 19. 埋め込み画像用拡大レンズ
- 20. 検索アイコン - レンズ - 3つの状態で
- 21. ハスケル - レンズ、 'to'関数の使用
- 22. APIとのインターフェイスのためのHTTPレンズ?
- 23. 2枚のレンズを作る方法は?
- 24. より複雑なトラバーサル(レンズ)を書く
- 25. デフォルトの「アンダースコア」ベースのものの代わりにカスタムネームプロセッサを使用した「レンズ」ライブラリのレンズの生成
- 26. 同位体2角形
- 27. 同形フェッチのSinonスパイ
- 28. サーバサイド(同形)DOMマニュプレーションNode.js + Cheerio
- 29. iCal形式のカレンダー同期
- 30. 同形のjavascriptアプリケーションのテスト
最後の1つ:「BValue」の取得/設定/変更機能はありません。 get/set/modify関数は、すべての 'Lens a b'型に対して一度だけ定義されます。 (ブログ記事を参照)。残された唯一のことは、例えば、あなたのデータ型に合わせた特定のレンズに 'get'を適用することです。それで 'get piLens'は' BValue'のpiフィールドのゲッターです。 – Lambdageek
'bv :: BValue'のように、与えられた型の特定の変数に対してこれらのアクセサーを使う方法は?レンズはタイプに適用されるので、そのタイプに属する変数のフィールドを 'getまたは' setすることが可能でなければなりません。 –
@mindboundレンズと値の両方にget/set/modify関数を適用するだけです。 '' get piLens bv'または '' modify lens(+ 1.0)bv' – Lambdageek