How to replace first instance of value in a list

I have a list where i would like to replace first instance of 1 with 'xyz'.

list1 = list(
    x=c(1,2,3,1,2),
    y=c(-1,-2,1,2,1)
)

My expected op:

list1 = list(
    x=c('xyz',2,3,1,2),
    y=c(-1,-2,'xyz',2,1)
)

I can't use ifelse as it would replace all the instance of 1.

I tried finding the index. Then use mapply, but it doesn't work either.

list2=lapply(list1, function(x) which(x==1)[1])
mapply(function(x,y){x[y]='xyz'}, list1, list2)

How do we replace values in a list based on other list?


Solution 1:

We can use match to return the index of the first match to replace that position with 'xyz'

lapply(list1, function(x) replace(x, match(1, x, nomatch = 0), "xyz"))
#$x
#[1] "xyz" "2"   "3"   "1"   "2"  

#$y
#[1] "-1"  "-2"  "xyz" "2"   "1"  

As it is a list of vectors, by changing numeric value with character changes the class to character

If we have two lists, i.e. one an index index, use Map or mapply

Map(function(x, y) replace(x, y, "xyz"), list1, list2)

Or in a more compact way

Map(`[<-`, list1, list2, "xyz")
#$x
#[1] "xyz" "2"   "3"   "1"   "2"  

#$y
#[1] "-1"  "-2"  "xyz" "2"   "1"  

If the values to change would also be different, it can be a vector or list with the same length as the other lists

Map(`[<-`, list1, list2, c("xyz", "zyx"))