How to Create an Empty R Vector to Add New Items

How do I create an empty vector in r?

There are several ways to create empty vector in r. For example,

v2<-NULL

or

v2<-c()

Try this:

v2 <- NULL

for (i in 1:length(df)){
if (df$Texture[i] == 'Silt Loam'){
new_val <- df$`pH 1:1`[i]}
v2[i] <- new_val
}

Append value to empty vector in R?

Appending to an object in a for loop causes the entire object to be copied on every iteration, which causes a lot of people to say "R is slow", or "R loops should be avoided".

As BrodieG mentioned in the comments: it is much better to pre-allocate a vector of the desired length, then set the element values in the loop.

Here are several ways to append values to a vector. All of them are discouraged.

Appending to a vector in a loop

# one way
for (i in 1:length(values))
vector[i] <- values[i]
# another way
for (i in 1:length(values))
vector <- c(vector, values[i])
# yet another way?!?
for (v in values)
vector <- c(vector, v)
# ... more ways

help("append") would have answered your question and saved the time it took you to write this question (but would have caused you to develop bad habits). ;-)

Note that vector <- c() isn't an empty vector; it's NULL. If you want an empty character vector, use vector <- character().

Pre-allocate the vector before looping

If you absolutely must use a for loop, you should pre-allocate the entire vector before the loop. This will be much faster than appending for larger vectors.

set.seed(21)
values <- sample(letters, 1e4, TRUE)
vector <- character(0)
# slow
system.time( for (i in 1:length(values)) vector[i] <- values[i] )
# user system elapsed
# 0.340 0.000 0.343
vector <- character(length(values))
# fast(er)
system.time( for (i in 1:length(values)) vector[i] <- values[i] )
# user system elapsed
# 0.024 0.000 0.023

Cannot create an empty vector and append new elements in R

append does something that is somewhat different from what you are thinking. See ?append.

In particular, note that append does not modify its argument. It returns the result.

You want the function c:

> a <- numeric()
> a <- c(a, 1)
> a
[1] 1

R: Adding an empty vector to a list

Using things like vector() (logical) and character() assigns a specific class to an element you'd like to remain "empty". I would use the NULL class. You can assign a NULL list element by using [<- instead of [[<-.

a <- list()
a[1] <- list(NULL)
a
# [[1]]
# NULL
length(a)
# [1] 1

How to populate an empty vector in R using a function?

You should initialize empty_vec within func and return it (so you should put empty_vec at the bottom as well), e.g.,

func <- function(num) {
empty_vec <- c()
for (numbers in num) {
i <- sqrt(numbers)
empty_vec <- c(empty_vec, i)
}
empty_vec
}

such that

> func(c(4, 5, 6, 7))
[1] 2.000000 2.236068 2.449490 2.645751

Since what you are doing is to calculate sqrt, you can do it just via

> sqrt(c(4,5,6,7))
[1] 2.000000 2.236068 2.449490 2.645751

How to insert an element at a specific position of an empty vector?

You need to do this in two steps:

  1. First resize the vector or create a vector with an appropriate size.
  2. Next set the elements accordingly.

Since you are coming from R I assume you want the vector to be initially filled with missing values. Here is the way to do this.

In my example I assume you want to store integers in the vector. Before both options load the Missings.jl package:

using Missings

Option 1. Start with an empty vector

julia> x = missings(Int, 0)
Union{Missing, Int64}[]

julia> resize!(x, 4)
4-element Vector{Union{Missing, Int64}}:
missing
missing
missing
missing

julia> x[1] = 10
10

julia> x[4] = 40
40

julia> x
4-element Vector{Union{Missing, Int64}}:
10
missing
missing
40

Option 2. Preallocate a vector

julia> x = missings(Int, 4)
4-element Vector{Union{Missing, Int64}}:
missing
missing
missing
missing

julia> x[1] = 10
10

julia> x[4] = 40
40

The reason why Julia does not resize the vectors automatically is for safety. Sometimes it would be useful, but most of the time if x is an empty vector and you write x[4] = 40 it is a bug in the code and Julia catches such cases.



EDIT

What you can do is:

function setvalue(vec::Vector, idx, val)
@assert idx > 0
if idx > length(vec)
resize!(vec, idx)
end
vec[idx] = val
return vec
end

Turning a character vector into an empty list with names from the character vector

1) Base R No packages are used.

Map(function(x) NULL, myvec)

2) gsubfn At the expense of using a package we can slightly shorten it further:

library(gsubfn)
fn$Map(. ~ NULL, myvec)

3) purrr or using purrr (at the expense of a package and a few more characters in code length). This is similar to the approach in the question but simplifies it by eliminating the as.list which is not needed.

library(purrr)
map(set_names(myvec), ~ NULL)

Note

A comment below this answer points out that NULL can be replaced with {}.
That will save two characters and applies to any of the above.



Related Topics



Leave a reply



Submit