databaaz
databaaz

Reputation: 33

frequency count of multiple variables in R

I have multiple variables in my dataframe. I want to check the individual frequency counts of some of the selected variables more from QA perspective of large datasets.e.g

ID Q1 Q2 Q3
1  1  2  3
2  2  1  2 
3  3  2  1
4  1  2  3
5  2  3  1

So, I should get the frequency count of Q1 & Q2, my selected variables, as the output below

Q1 1 - 2
   2 - 2
   3 - 1

Q2 1 - 1
   2 - 3
   3 - 1

I tried table(), but it seeems like I would have to write this function multiple times which I want to avoid.

table(df$Q1)
table(df$Q2)

Is there any other way to achieve this?

Upvotes: 3

Views: 45950

Answers (5)

jzadra
jzadra

Reputation: 4314

freq_tibble <- function(data, var1, var2) {
  var1 <- rlang::enquo(var1)
  var2 <- rlang::enquo(var2)

  data %>%
    dplyr::count(!!var1, !!var2) %>%
    tidyr::spread(!!var2, n, fill = 0) %>%
    dplyr::mutate(Total := rowSums(dplyr::select(., -!!var1))) %>%
    dplyr::bind_rows(dplyr::bind_cols(!!rlang::quo_name(var1) := "Total", dplyr::summarize_if(., is.numeric, sum)))
}

Upvotes: 0

Ann Rajaram
Ann Rajaram

Reputation: 61

A simpler implementation of count function from the plyr package is:

library(plyr) 
var_select = c("Q1", "Q2")
count_freq = count(table, var_select)

Similar results are also obtained by using subset inside the table function:

var_select = c("Q1", "Q2")
freq_table = as.data.frame(table(subset(table, select = var_select)))

Both methods will create a freq table with 3 columns - Q1, Q2, Freq. You could easily add more variable names to var_select without having to change anything in the next command.

Upvotes: 2

akrun
akrun

Reputation: 887891

We can use lapply to loop over the columns 2 and 3, and get the table.

lapply(df1[paste0("Q", 1:2)], table)
#$Q1

#1 2 3 
#2 2 1 

#$Q2

#1 2 3 
#1 3 1 

Or without any loop, replicate the names of the dataset 2 and 3 by nrow of the dataset, unlist the 2nd and 3rd columns, and apply the table.

table(rep(names(df1)[names(df1) %in% c("Q1", "Q2")],nrow(df1)), 
                    unlist(df1[paste0("Q", 1:2)]))    
#    1 2 3
# Q1 2 2 1
# Q2 1 3 1

Upvotes: 2

989
989

Reputation: 12935

You could do:

library(plyr)
r <- apply(df[-1],2,count)

r$Q1

# $Q1
  # x freq
# 1 1    2
# 2 2    2
# 3 3    1

r$Q2

# $Q2
  # x freq
# 1 1    1
# 2 2    3
# 3 3    1

You could also do:

cols <- c("Q1","Q2")
apply(df[cols],2,count)

Which will give you the same result.

data

df <- structure(list(ID = 1:5, Q1 = c(1L, 2L, 3L, 1L, 2L), Q2 = c(2L, 
1L, 2L, 2L, 3L), Q3 = c(3L, 2L, 1L, 3L, 1L)), .Names = c("ID", 
"Q1", "Q2", "Q3"), class = "data.frame", row.names = c(NA, -5L
))

Upvotes: 2

Ronak Shah
Ronak Shah

Reputation: 389265

You can use apply with table

apply(df[-1], 2, table)

#  Q1 Q2 Q3
#1  2  1  2
#2  2  3  1
#3  1  1  2

Or if you want it for selected rows only which you want to specify using their names you can use,

apply(df[c("Q1", "Q2")], 2, table)


#  Q1 Q2
#1  2  1
#2  2  3
#3  1  1

Upvotes: 5

Related Questions