schemeracket

Scheme - Replacing elements in a list with its index


I am trying to replace the elements in a scheme list with its position. For example, calling:

(position '((a b) c))

should return:

'((0 1) 2)

So far, my code keeps the list format, but the index is not updating.

(define (position term1)
  (define index 0)
    (cond [(null? term1) '()]
          [(list? term1) (cons (position (car term1)) (position(cdr term1)))]
          [else (+ 1 index) index]))

When (position '((a b) c)) is called, it returns

'((0 0) 0)

Can anybody explain why the index isn't updating?


Solution

  • There are a couple things wrong: first notice that every time you recursively call position, index is bound to zero.

    Second, look at your else branch. (+ 1 index) evaluates to 1 (it does not change any variables) and index evaluates to 0. This branch can only evaluate to one thing, so what happens is the last one is returned and the rest are discarded. This is where your zeroes come from.

    It seems like within your function you are trying to keep a global state (the current index) and modify it each time you label a leaf. The "modifying state" part is not good functional style, but if you are okay with that then take a look at set!.