Splitting a vector into two - r

How can I split a vector into two such that it selects a random sample for each new vector. But I always want to split in half. For instance
x <- 1:10
obj <- splitMyVector(x)
obj$a
> 5 3 9 7 10
obj$b
> 8 4 1 6 2
Note: the purpose for this is to do a split half reliability.

split(sample(x),letters[seq(length(x))%%2+1])
$a
[1] 9 7 10 4 2
$b
[1] 6 1 8 3 5

Related

Vector recycling concept in R

I am trying to understand the working of vector recycling in R. I have 2 vectors
c(2,4,6)
and
c(1,2)
And I want to use the rep() to produce an output as follows:
[1] 2 4 6 4 8 12
based on what I understand from ?rep() is that there are times and each parameters which do the operations which I tried.
> rep(c(2,4,6), times=2)
[1] 2 4 6 2 4 6
But I also see the first vector is multiplied by the first element of the second vector and then to the second element of the second vector. Not sure how to proceed with it.
You can use:
rep(c(2,4,6), 2) * rep(c(1,2), each=3)
#[1] 2 4 6 4 8 12
or with auto recycling:
c(2,4,6) * rep(c(1,2), each=3)
#[1] 2 4 6 4 8 12
Alternative outer could be used:
c(outer(c(2,4,6), c(1,2)))
#[1] 2 4 6 4 8 12
Also crossprod could be used:
c(crossprod(t(c(2,4,6)), c(1,2)))
#[1] 2 4 6 4 8 12
Or %*%:
c(c(2,4,6) %*% t(c(1,2)))
#[1] 2 4 6 4 8 12

R shuffle lists with repeated elements

I have multiple lists in R, each list has unique elements but some elements are in multiple lists. I want to shuffle the lists but also have each list have only unique elements. Here is something but this doesn't end up with unique lists at the end
x<-list()
x[[1]]<-c(1,2,3,4,5)
x[[2]]<-c(1,2,6,7,8)
u<-unlist(x)
x2<-relist(u[sample(length(u))],skeleton=x)
> x
[[1]]
[1] 1 2 3 4 5
[[2]]
[1] 1 2 6 7 8
> x2
[[1]]
[1] 4 8 3 5 6
[[2]]
[1] 2 1 2 1 7
Trying to figure out extra step to make sure each list has five unique numbers.
In your example the vectors already contain only unique values, so I think the solution can be as simple as:
x <- list(c(1,2,3,4,5), c(1,2,6,7,8))
lapply(x, sample)
# [[1]]
# [1] 3 2 5 1 4
#
# [[2]]
# [1] 1 6 7 2 8

Generate sequence between each element of 2 vectors

I have a for loop that generate each time 2 vectors of the same length (length can vary for each iteration) such as:
>aa
[1] 3 5
>bb
[1] 4 8
I want to create a sequence using each element of these vectors to obtain that:
>zz
[1] 3 4 5 6 7 8
Is there a function in R to create that?
We can use Mapto get the sequence of corresponding elements of 'aa' , 'bb'. The output is a list, so we unlist to get a vector.
unlist(Map(`:`, aa, bb))
#[1] 3 4 5 6 7 8
data
aa <- c(3,5)
bb <- c(4, 8)
One can obtain a sequence by using the colon operator : that separates the beginning of a sequence from its end. We can define such sequences for each vector, aa and bb, and concatenate the results with c() into a single series of numbers.
To avoid double entries in overlapping ranges we can use the unique() function:
zz <- unique(c(aa[1]:aa[length(aa)],bb[1]:bb[length(bb)]))
#> zz
#[1] 3 4 5 6 7 8
with
aa <- c(3,5)
bb <- c(4,8)
Depending on your desired output, here are a few more alternatives:
> do.call("seq",as.list(range(aa,bb)))
[1] 3 4 5 6 7 8
> Reduce(seq,range(aa,bb)) #all credit due to #BrodieG
[1] 3 4 5 6 7 8
> min(aa,bb):max(aa,bb)
[1] 3 4 5 6 7 8

Recursive looping in r

I am new in R but I want to loop through elements of a given list recursively, to be presice I have alist of vectors where the first vector is given by (1,2,3,4), then I now want to loop through this vector and append the second vector obtained to the original list, again loop thorugh second vector in the list and get the third vector which is also appended on the original list and so on. I have this code to start with`
occlist <- list()
occ_cell <- c(1,2,3,4)
for(i in occ_cell){
occ_cell <- seq(i,4*i, by = 1)
occlist[[i]] <- occ_cell
}
`
gives the following list
#[[1]]
#[1] 1 2 3 4
#[[2]]
#[1] 2 3 4 5 6 7 8
#[[3]]
# [1] 3 4 5 6 7 8 9 10 11 12
#[[4]]
# [1] 4 5 6 7 8 9 10 11 12 13 14 15 16
I think to be more clear, lets have the following figure
recOcc <- function(i) {
if (i == 0) return ( NULL )
append( recOcc(i-1), list(seq(i, 4*i)) )
}
And, call with (to reproduce your output)
recOcc(4)
# [[1]]
# [1] 1 2 3 4
#
# [[2]]
# [1] 2 3 4 5 6 7 8
#
# [[3]]
# [1] 3 4 5 6 7 8 9 10 11 12
#
# [[4]]
# [1] 4 5 6 7 8 9 10 11 12 13 14 15 16
You can also use Recall to name your recursive function in the recursive call, which allows for the function name to change.
Edit
For the tree structure, you could try this
## i is the number to start the sequence
## depth determines how deep to recurse
recOcc2 <- function(i, depth=3, cur.depth=0) {
if (depth==cur.depth) return(seq(i, 4*i))
acc <- as.list(seq(i, 4*i))
for (ii in seq_along(acc))
acc[[ii]] <- recOcc2(acc[[ii]], depth, cur.depth+1)
acc
}
## To recreate the simple list
res <- recOcc2(1, depth=1)
## For nested lists
res <- recOcc2(1, depth=2)

How to assign a name to an object when the name is stored in a different vector

Given these two objects:
v <- "new.name"
w <- 1:10
How can I tell R to rename w as new.name, so I can have this
> new.name
[1] 1 2 3 4 5 6 7 8 9 10
Thanks
You could do
assign(v, w)
new.name
# [1] 1 2 3 4 5 6 7 8 9 10
But it is considered a very bad practice in R, so read this first

Resources