0

I was testing this code in guile:

> (define xxx  (let ((x '(1 2 3))) (set-cdr! (cddr x) x) x))
> xxx

it display (1 2 3)

but this:

(define x '(1 2 3))
(set-cdr! (cddr x) x)
x
=> (1 2 3 . #-2#)

creates circular list

Why first code don't work in guile? If you don't know about guile I just want to know if it should work according to scheme spec, don't know where to search for such things.

jcubic
  • 61,973
  • 54
  • 229
  • 402
  • *"it display (1 2 3)"* - again, no it doesn't. It throws an error: `In procedure set-cdr!: Wrong type argument in position 1 (expecting mutable pair): (3)`. What guile version do you use? – rsm Apr 23 '19 at 13:37
  • They produce the same, circular, result in Guile 2.0.13 [here](https://ideone.com/CQl54m). I believe 2.0 was pretty far from compliant with any of the Scheme standards, though. – molbdnilo Apr 23 '19 at 19:13
  • Neither are valid Scheme since you are trying to modify constant quoted literal data. Thus if the implementation had printed `"BaNaNa"` it still would have been a OK. – Sylwester Apr 23 '19 at 21:59

1 Answers1

3

Problem with your examples is - they don't work. None of them. I have no clue how did the first one returned (1 2 3). But when you fix the same problem in both examples, they work as expected and create circular list.

Problem?

'(1 2 3) and (quote 1 2 3) is something very different than (list 1 2 3). They both "look" the same, but first one is static list and you can't modify it. Only list created with with list function (well and cons) is a list you can modify.

Fix:

(define xxx
  (let ((x (list 1 2 3)))
    (set-cdr! (cddr x) x)
    x))

xxx ;; => (1 2 3 . #-2#)

And the same goes for second example:

(define x (list 1 2 3))
(set-cdr! (cddr x) x)

Please test your code before posting.

rsm
  • 2,530
  • 4
  • 26
  • 33
  • 1
    Second code was working in guile, it was exact code I was testing, maybe `(quote 1 2 3)` work differently when using with `define`. Didn't know that `'(1 2 3)` is different then `(list 1 2 3)`. But if `quote` work differently then `list` then why this works `(let ((x '(1 2 3))) (append! x '(10)))`? – jcubic Apr 23 '19 at 14:32
  • 1
    I was testing it also on guile (v 2.2.4). And I was getting an error. Don't know why your guile works differently. – rsm Apr 23 '19 at 14:45
  • 1
    Later guile got a memory protection and errors. Older version doesn't have this protection. – Stefan Apr 24 '19 at 12:53