Understanding Deep Reverse

后端 未结 2 1178
时光取名叫无心
时光取名叫无心 2020-12-11 13:37

Say I have the list \'(1 2 3 (4 5 6) 7 8 9). It should return (9 8 7 (6 5 4) 3 2 1) using the following code below. I\'m trying to understand how this iterative process work

相关标签:
2条回答
  • 2020-12-11 13:50

    Well, I just answered something like this here, but I didn't really go into detail on the deep-reverse.

    What happens is it reverses each item that happens to be a list before appending it to the end of the list. Imagine what would happen if it didn't call deep-reverse on the car of the list: (reverse '(a (b c d) e) is

    (list
       'e
       '(b c d)
       'a
    )
    

    With deep-reverse it would look something like

    (list
        'e
        (deep-reverse '(b c d))
        'a
    )
    

    Which is

    (list
        'e
        '(d c b)
        'a
    )
    

    Here is another version of deep-reverse, written differently, if that makes it clearer.

    (define (deep-reverse ls)
      (define (deep-reverse-2 ls acc)
        (if (null? ls)
            acc
            (if (list? (car ls))
                (deep-reverse-2 (cdr ls) (cons (deep-reverse (car ls)) acc));  If adding  a list, reverse it first
                (deep-reverse-2 (cdr ls) (cons (car ls) acc)))))
      (deep-reverse-2 ls '()))
    

    This version of deep-copy uses an accumulator and is tail recursive.

    This checks to see if the element is a list before adding it to the list, and if it is, reverses it first. Since it calls itself to revers the inner list, it can handle arbitrary nesting.

    (deep-reverse '(a (b c d) e)) -> '(e (d c b) a)
    

    which is in reverse alphabetical order, despite the fact that there is a nested list. It evaluates as so:

    (deep-reverse-2 '(a (b c d) e) '()); Which calls
    (deep-reverse-2 '((b c d) e)  '(a)); which is the same as
    (deep-reverse-2 '(e) (cons (deep-reverse-2 '(b c d) '()) '(a))); it calls deep-reverse on the list '(b c d) before consing it on.
    (deep-reverse-2 '(e) (cons (deep-reverse-2 '(c d)  '(b)) '(a)))
    (deep-reverse-2 '(e) (cons (deep-reverse-2 '(d)  '(c b)) '(a)))
    (deep-reverse-2 '(e) (cons '(d c b) '(a)))
    (deep-reverse-2 '(e)  '((d c b) a))
    (deep-reverse-2 '() '(e (d c b) a))
    '(e (d c b) a)
    
    0 讨论(0)
  • 2020-12-11 13:52

    Easy, you don't know whether the head is an integer or a list, so you have to apply deep-reverse on it also, then append it to the reversed tail of the current list.

    So:

    ((1 2) 3 4)
    

    has to become

    (4 3 (2 1))
    

    Notice how we had to reverse the head AND the tail.

    0 讨论(0)
提交回复
热议问题