1

For a given n I would like to enumerate all 2^(n) - 1 possible subsets (excluding the null set).

So for n = 3 items (A, B, C) I have 8 - 1 combinations: {A}, {B}, {C}, {A, B}, {A, C}, {B, C}, and {A, B, C}.

To enumerate these subsets I would like to define a binary grid. For n = 3:

> expand.grid(0:1, 0:1, 0:1)[ -1, ]

  Var1 Var2 Var3
2    1    0    0
3    0    1    0
4    1    1    0
5    0    0    1
6    1    0    1
7    0    1    1
8    1    1    1

However, n is itself a random variable that changes from one simulation to the next.

It is easy to programmatically generate the string I need to pass to the function call. For instance, for n = 7, I can run:

> gsub(", $", "", paste(rep("0:1, ", 7), collapse = ""))

[1] "0:1, 0:1, 0:1, 0:1, 0:1, 0:1, 0:1"

But when I try to pass this string to expand.grid() I get an error. Surely there is a function that can coerce this string to a usable expression?

2
  • Have you considered these solutions : stackoverflow.com/questions/27953588/… ? Commented Oct 31, 2020 at 1:35
  • Since R supports so many functions for combinations and permutations, I am not surprised there is a more direct solution. However, there are other times I wanted to pass a string to a function: for example, when iterating through many combinations of model parameters. The combinations example is for the sake of a reproducible prototype. Commented Oct 31, 2020 at 1:40

2 Answers 2

1

Running string as code is not recommended and should be avoided in general.

In this case, you can use replicate to repeat a vector n times and then use expand.grid with do.call.

n <- 3
do.call(expand.grid, replicate(n, list(0:1)))

#  Var1 Var2 Var3
#1    0    0    0
#2    1    0    0
#3    0    1    0
#4    1    1    0
#5    0    0    1
#6    1    0    1
#7    0    1    1
#8    1    1    1
Sign up to request clarification or add additional context in comments.

Comments

1

We can use crossing

library(dplyr)
library(tidyr)
library(stringr)
library(purrr)
n <- 3
replicate(n, list(0:1)) %>%
    set_names(str_c('Var', seq_along(.))) %>% 
    invoke(crossing, .)
# A tibble: 8 x 3
#   Var1  Var2  Var3
#  <int> <int> <int>
#1     0     0     0
#2     0     0     1
#3     0     1     0
#4     0     1     1
#5     1     0     0
#6     1     0     1
#7     1     1     0
#8     1     1     1
    

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.