How to compare recursive data structures?

I have a complex and recursive data structure that I have simplified as follows:

data Node = Node { value :: Integer, next :: Node } deriving (Show,Eq)

Given the following expressions:

--Create a circular structure
a = Node 1 b
b = Node 0 a --Tie the knot
c = Node 1 b --Another structure which points to b

The expressions aand are cconceptually equal: both of them are a node that contains the value 1 and points to the expression b. My question is: how can I verify that they are really equal in a Haskell expression? If I evaluate a == c, he will continue to evaluate sub-elements in a circular structure forever.

Can this comparison be done in Haskell?

EDIT: In my case, I am trying to compare these two for verification / debugging purposes. But another reason to do this may be for unit testing.

+5
source share
2 answers

, a b , a c , , .

: . , . - Map :

data Node k =
    Node {
      nodeValue :: Integer,
      nodeNext  :: k
    }

, Map k . Eq . reflection:

{-# LANGUAGE ScopedTypeVariables #-}

import Data.Reflection

data Node n k =
    Node {
      nodeValue :: Integer,
      nodeNext  :: k
    }

instance (n `Reifies` Map k (Node n k)) => Eq (Node n k) where
    (==) = {- ... -}
        where
        nodeMap :: Map k (Node n k)
        nodeMap = reflect (Proxy :: Proxy n)

, , - .

+12

, , ghc-heap-view, Haskell :

Prelude> :script /home/jojo/.cabal/share/ghc-heap-view-0.4.0.0/ghci 
Prelude> data Node = Node { value :: Integer, next :: Node } deriving (Show,Eq)
Prelude> let { a = Node 1 b; b = Node 0 a ; c = Node 1 b}
Prelude> take 100 (show a) -- make sure it is evaluated, we are not interested in thunks here
"Node {value = 1, next = Node {value = 0, next = Node {value = 1, next = Node {value = 0, next = Node"
Prelude> take 100 (show c) -- dito
"Node {value = 1, next = Node {value = 0, next = Node {value = 1, next = Node {value = 0, next = Node"
Prelude> System.Mem.performGC
Prelude> :printHeap a
let x0 = Node (S# 1) (Node (S# 0) x0)
in x0
Prelude> :printHeap c
let x2 = Node (S# 0) (Node (S# 1) x2)
in Node (S# 1) x2

, , , " , Haskell".

-1

All Articles