0

I am trying to determine effect size for each column in a dataframe with ~700 columns. A representative dataset looks like this:

subjects <- c('1', '2', '3', '4', '5', '6')
obs1 <- c(828.4, 632.7, 616.0, 732.0, 886.7, 901.9)
obs2 <- c(9084.5, 10388.8, 11941.5, 8903.4, 9066.6, 10648.5)
obs3 <- c(1293.5, 1648.6, 873.0, 1406.7, 2050.1, 1069.7)
df <- data.frame(subjects, obs1, obs2, obs3)
df

I accomplished calculating cohen's d for each column this like so:

z <- mapply(effsize::cohen.d, df[1:3,], df[4:6,])

This results in a list with my results. I want to extract and return a list or vector of the 'estimate' attribute for each object within this list. I can access them individually like so:

z[[3]]

After looking at other stack overflow questions, I found some useful advice (e.g., access attributes of objects stored in lists). After trying the following method:

lapply(z, function(x) x[[3]])

I get a subscript out of bounds error. What am I missing here? There must be something I am not understanding about accessing attributes. If I remove a pair of brackets I can see some of the attribute names, but none of the values.

EDIT: As per @Roland's suggestion, I used Map rather than mapply and now the lapply function works.

bhumm
  • 33
  • 7
  • 1
    Please [make this question reproducible](https://stackoverflow.com/questions/5963269/how-to-make-a-great-r-reproducible-example) by including a small representative dataset in a plain text format - for example the output from `dput(df)`, if that is not too large. Also include all the relevant code including libraries - where does `cohen.d` come from? – neilfws Mar 21 '23 at 02:31
  • when you type `is.matrix(z)` what is the output? `TRUE` or `FALSE`? – S-SHAAF Mar 21 '23 at 03:01
  • @SALAR the output is TRUE – bhumm Mar 21 '23 at 03:25
  • Can you also update your `z` code based on your example `df`? – S-SHAAF Mar 21 '23 at 03:41
  • Why are you using `cbind` and then `as.data.frame`? You should never, ever do that. Use `data.frame` instead. Your approach turns all numbers into character strings (because `cbind` returns a matrix and a matrix can only contain one data type). – Roland Mar 21 '23 at 08:44
  • You probably should use `Map` instead if `mapply`. – Roland Mar 21 '23 at 08:47
  • @Roland I did not create my dataframe this way, this was just a method to provide a representative dataset of a very large df. That being said, this method is much better, thanks for the advice. Also your `Map` suggestions worked beautifully, thank you! – bhumm Mar 21 '23 at 14:49

1 Answers1

1

Here's a solution with purrr:

library(purrr)

z <- map2(dat[, 1:2], dat[, 3:4], effsize::cohen.d)

map(z, 3)

$dv1
[1] -1.62089

$dv2
[1] -1.45319

Example data

set.seed(123)
n <- 10
dat <- data.frame(dv1 = rnorm(n), 
                  dv2 = rnorm(n), 
                  iv1 = sample(c(1:2), size = n, replace = TRUE),
                  iv2 = sample(c(1:2), size = n, replace = TRUE))
andrew_reece
  • 20,390
  • 3
  • 33
  • 58