pixie
pixie

Reputation: 517

Replacing an element into a list Scheme

I need to replace an element from a list with another element in Scheme, but the problem is that the list where I need to replace can be nested.

For example, if I have the list '(1 (2 3 4 5) (6 7)) and I need to replace 5 with 9, my output should be '(1 (2 3 4 9) (6 7)).

Can you please help me with this problem?

Upvotes: 1

Views: 4888

Answers (2)

Damien Mattei
Damien Mattei

Reputation: 384

here is a function:

(define (replace L new old)
   (cond ;;((null? L) L)
         ((list? L)
          (map
              (lambda (lst) (replace lst new old))
              L))
         (else
              (if (equal? L old)
                   new
                   L))))

examples of use:

> (replace '(1 (1 2 3 4 (5 6 3) 3 4)) 7 3)
'(1 (1 2 7 4 (5 6 7) 7 4))

> (replace '() 7 3)
'()

> (replace '(1 (1 2 3 4) 3 4) 7 3)
'(1 (1 2 7 4) 7 4)

or:

(define (replace L new old)

  (if (list? L)
      (map
       (lambda (lst) (replace lst new old))
       L)
      (if (equal? L old)
      new
      L)))

example:

(replace '(1 (1 2 3 4 (5 6 3) 3 4)) 7 3) -> '(1 (1 2 7 4 (5 6 7) 7 4))

Upvotes: 2

C. K. Young
C. K. Young

Reputation: 223013

There is a basic strategy for solving this kind of problem:

  1. First, solve it for a flat list. i.e., write the function so that it works if the input list has no sublists.
  2. Then, add a condition so that if the element you're inspecting is a list, then recurse into your function with that list.

Here's some skeletal code:

(define (replace lst from to)
  (cond ((null? lst) '())                ;; end of input
        ((list? (car lst)) <???>)        ;; encountered a sublist
        ((equal? (car lst) from) <???>)  ;; found the element we're replacing
        (else <???>)))                   ;; everything else

Notice that the second cond clause, (list? (car lst)), is the only thing that's new in your sublist-capable version.

Upvotes: 3

Related Questions