I hate using SO as a way to find simple functions, but I really can't find a function like this anywhere:
Given a list (1 2 3 4 5), I'd like the equivalent of (PHP's, Perl's, Python's)
$a = array(1, 2, 3, 4, 5);
$a[3] = 100;
Which results in (1 2 3 100 5)
Thanks!
You can write list-set!
of Guile, like so:
(define a (list 1 2 3 4)) ; a is '(1 2 3 4)
(define (list-set! list k val)
(if (zero? k)
(set-car! list val)
(list-set! (cdr list) (- k 1) val)))
(list-set! a 2 100) ; a is '(1 2 100 4)
(Tried this in DrRacket.)
Using standard functions without any SRFI:
(set-car! (list-tail lst k) val)
Guile has a built-in function called list-set!
that does exactly what you want, using zero-based indices. For your example, you would have:
(define a '(1 2 3 4 5))
(list-set! a 3 100)
I don't think this is standard Scheme, however, and I don't know if it's really efficient. For a fixed-length array you should probably use a vector:
(define a2 #(1 2 3 4 5))
(vector-set! a2 3 100)
I'm pretty sure this is part of the language standard.
I may be a bit late, but I have a different answer.
Part of the functional-program paradigm seems to be to try to avoid modifying data when possible. For efficiency reasons you may want to go with the other answers here. But otherwise, consider a non-mutating function such as this:
(define (list-with lst idx val)
(if (null? lst)
lst
(cons
(if (zero? idx)
val
(car lst))
(list-with (cdr lst) (- idx 1) val))))
Which passes the following tests:
(describe "a function that returns a list with a 'changed' value"
(it "can modify the edges of lists without having 1-off errors"
(expect (list-with '(1 2 3 4 5) 0 99) (be equal? '(99 2 3 4 5)))
(expect (list-with '(1 2 3 4 5) 4 99) (be equal? '(1 2 3 4 99))))
(it "has something to do with creating new lists"
(expect (list-with '(1 2 3 4 5) 2 99) (be equal? '(1 2 99 4 5))))
(it "doesnt just modify the contents of the original list"
(let ((a '(1 2 3 4 5)))
(list-with a 2 99)
(expect a (be equal? '(1 2 3 4 5))))))
(The code is written in Chicken Scheme and the tests with the "missbehave" library. But it seems like pretty portable Scheme.)