Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does a set (or list) in Racket print with #0# as the only piece of data?

I'm writing a Racket program that makes extensive use of sets. Looking at the output of the program, several of the sets include #0# as their only piece of data. What is causing this?

like image 356
superlizardmo Avatar asked Aug 22 '16 22:08

superlizardmo


1 Answers

#0# is used in the Racket printer to describe cyclic data structures or objects with shared memory. Basically, the way it works is that there is an object that is tagged with, say, #0=, then, when you see #0# refers to that object.

So for example:

#0=(1 . #0#)

Is a list of infinite length containing only 1s. It does this because the data structure created is just a cons pair, where the first item is 1, and the second item points back to itself.

You can have any number of these to create more complex graph structures. Such as:

#0=(#1=(1 . #0#) . #1#)

Finally, you don't need to have a cyclic data structure at all. Lets say x was the following data structure:

'(#0=#&42 . #0#)

(wehre #& represents a mutable box), mutating the element in the first element of the pair would additionally mutate the element in the second part of the pair. So if this pair was set to the variable x, then:

> x
'(#0=#&42 . #0#)
> (set-box! (car x) 43)
> (car x)
'#&43
> (cdr x)
'#&43
> x
'(#0=#&43 . #0#)

Normally you cannot write this directly in code directly in code, but it is possible to construct it using read.

> (define x (read)
#0=(1 . #0#)
> x
#0='(1 . #0#)
> (car x)
1
> (cadr x)
1
> (cdr x)
#0=1(1 . #0#)

You can also modify the reader to just let you put it in code directly with read-accept-graph when reading in a module's source code.

like image 89
Leif Andersen Avatar answered Oct 23 '22 05:10

Leif Andersen