12

Haskell にポインターの品質の概念はありますか? == は式を導出する必要があり、(値 -> IO 値) を含むものがありますが、-> も IO も式を導出しません。

編集:ポインターの等価性を持つ別の言語のインタープリターを作成しているため、Haskell関数を使用してクロージャーをモデル化できるようにしながら、この動作をモデル化しようとしています。

編集:例:specialこれを行う関数が必要です:

> let x a = a * 2
> let y = x
> special x y
True
> let z a = a * 2
> special x z
False
4

6 に答える 6

13

編集:あなたの例を考えると、これを IO モナドでモデル化できます。関数を IORef に割り当てて比較するだけです。

Prelude Data.IORef> z <- newIORef (\x -> x)
Prelude Data.IORef> y <- newIORef (\x -> x)
Prelude Data.IORef> z == z
True
Prelude Data.IORef> z == y
False
于 2009-11-11T22:38:07.643 に答える
9

ポインタの等価性は参照透過性を壊すので、いいえ。

意外かもしれませんが、コンパクト空間上の全関数の拡張等価性を実際に計算することは可能ですが、一般的には (例: 非終了の可能性がある整数上の関数)、これは不可能です。


編集:別の言語のインタープリターを作成しています

元のプログラムの AST またはソースの場所を、翻訳した Haskell 関数と一緒に保管できますか? それを踏まえて「平等」を望んでいるようです。

于 2009-11-11T20:06:36.543 に答える
5

== 式を導出する必要があります

実際(==)には、必ずしも派生インスタンスではなく、Eq のインスタンスが必要です。おそらくあなたがする必要があるのは、その部分を単純に無視する Eq の独自のインスタンスを提供することです。例えば、(Value -> IO Value)

data D = D Int Bool (Value -> IO Value)

instance Eq D where
  D x y _ == D x' y' _ = x==x && y==y'

それは役に立ちますか?

于 2009-11-11T21:06:24.357 に答える
3

ポインターが等しい別の言語用のインタープリターを作成しているので、Haskell 関数を使用してクロージャーをモデル化しながら、この動作をモデル化しようとしています。

このようなインタープリターを作成するには、コードがモナドでなければならないことは確かです。何らかの環境や状態を維持する必要はありませんか? もしそうなら、関数クロージャーのカウンターを維持することもできます。したがって、新しいクロージャを作成するたびに、一意の ID を装備します。次に、ポインターの等価性については、これらの識別子を比較するだけです。

于 2009-11-15T16:19:51.527 に答える
3

IORef は式を導出します。ポインターの等価性を取得するために他に何が必要かわかりません。

編集:ポインタの等価性を比較するのが理にかなっている唯一のものは、可変構造です。しかし、上で述べたように、IORef のような可変構造は、すでに Eq をインスタンス化しており、これにより、2 つの IORef が同じ構造であるかどうかを確認できます。これは、正確にポインターが等しいことです。

于 2009-11-11T19:47:38.517 に答える
3

これを行う別の方法は、StableNames を利用することです。

ただし、unsafePerformIO を悪用したくない場合を除き、special は IO モナド内で結果を返す必要があります。

IORef ソリューションでは、構造の構築全体で IO が必要です。StableNames をチェックすると、参照の等価性をチェックする場合にのみ使用されます。

于 2009-11-16T17:56:01.923 に答える