Q:

Deleting the n-th element of a list

Hello I wrote the following procedure to delete the n-th element of a list 
  (define  (delete l n)
     (if (= n 1)
      (begin (set! l (cdr l) )
             l)
      (begin ( set-cdr! (n_sub_list (- n 1 ) l )
                         (cdr (n_sub_list n l )))
          l)))

           (define n_sub_list n l )
                  (if (= n 1) l
                (n_sub_list ( - n 1 ) (cdr l ))))

if I do (define d '(1 2 3 4 )) and (delete! d 2) i get that d is (1 3 4 ) but if I continue and do (delete! d 1 ) I get (1 3 4) which is wrong,any ideas why?

A:

In your code you have two different procedures that mutate something. 
You have set-cdr! which changes what the cdr of the pair in the argument points to. This can only happen on lists that are mutable. '(1 2 3 4) is an immutable list and thus the result is undefined. Doing it on (list 1 2 3 4) is ok since it becomes a mutable list.
You have set! that redefined what a named variable represent. It does not change the value the name actually points to. It's just that the label l means something else than the previous value, which still exists since d still reference it in your case. 
It's like if I call my friend greenhorn and in half a year i stop and start calling another friend greenhorn instead. My original friend doesn't cease to exist or becomes my other friend and the other friend doesn't take over his life. The only real change is what persion is associated with the nickname. This is what set! does.
It only does it with the closest with the same name:
(define a 5)
(define b 10)
(let ((a 10))
  (set! b 20)
  (set! a 20)
  a)
; ==> 20
b
; ==> 20
a
; ==> 5 

The a changed was the local made in let leaving the global a unchanged.
Scheme procedures shouldn't mutate so what you return is what's important:
(define (delete l n)
  (cond ((or (null? l) (< n 1)) l)
        ((= n 1) (cdr l))
        (else (cons (car l)
                    (delete (cdr l)
                            (- n 1))))))

(set! d (delete d 1))

