Masking Values in function

Hi I am trying to create a function for EXPSS table, sample data below

 dput( dataa<-data.frame(
  aa = c("q","r","y","v","g","y","d","s","n","k","y","d","s","t","n","u","l","h","x","c","q","r","y","v","g","y","d","s","n","k","y","d","s","t","n","u","l","h","x","c"),
col1=c(1,2,3,2,1,2,3,4,4,4,5,3,4,2,1,2,5,3,2,1,2,4,2,1,3,2,1,2,3,1,2,3,4,4,4,1,2,5,3,5),
col2=c(2,1,1,7,4,1,2,7,5,7,2,6,2,2,6,3,4,3,2,5,7,5,6,4,4,6,5,6,4,1,7,7,2,7,7,2,3,7,2,4)
)
)

function i created is

  crosstab_sum <- function(dat1,var1,var2)
{
var1 <- rlang::parse_expr(var1)
var2 <- rlang::parse_expr(var2)

dat1 = dat1 %>% select(!!var1,!!var2)
expss::var_lab(dat1[[1]]) <- ""
expss::var_lab(dat1[[2]]) <- ""
tab1 <- expss::cro_cpct(dat1[[1]],dat1[[2]])
tab1 <- as.data.frame(tab1)
tab1[is.na(tab1)] <- 0
tab1 <- tab1 %>% mutate_if(is.numeric,round,digits=1)
tab1 <- flextable:: flextable(tab1)
tab1
}

now i want to add a criteria in this function on total but unable to explore how i can apply the below criteria (max_m) in my above function.

 max_n<-c(3,4,5)
max_m<-function(x,N){
  x= ifelse(N<max_n[1],"--",x)
}

in this function "N" is total number of occurence

also do we have any solution to concatenate "%" in all values except Total

Your code is not fully reproducible. I know full well that functions such as select(), mutate_if() and such are from the dplyr package. But I am not sure about the var_lab() function and cro_cpct() for example. If you make your code fully reproducible, then potential helpers will be better equipped to help you.

Yes its fully reproducible, var_lab() function and cro_cpct() are part of library(EXPSS)

I see that you have edited your code to make it more reproducible by adding expss::. You still need to add the dplyr and flextable packages to make it fully reproducible.

Also, it seems that these two lines of code are problematic in the function (I get an error):

expss::var_lab(dat1[[1]]) <- ""
expss::var_lab(dat1[[2]]) <- ""

you can please ignore these lines i can modify it later, but what kind of error you getting ,because i am not getting

Okay, I was able to make it work. But I have one more question before I can help you. Can you please explain a bit more what you want your function to do? Thanks.

I am trying to create a crosstab summary for expss data, and convert it to flextable to give theme, also i want to introduce masking if number of cases between (3,4,5) then it will not show results is summary will replaced by "-"

so that i can just give (data, var1,var2) and to make my reports dynamically generated

Okay, please try this code and let me know if this is what you are looking for:

library(dplyr)
library(expss)

df <- data.frame(
  aa = c("q","r","y","v","g","y","d","s","n","k","y","d","s","t","n","u","l","h","x","c","q","r","y","v","g","y","d","s","n","k","y","d","s","t","n","u","l","h","x","c"),
  col1=c(1,2,3,2,1,2,3,4,4,4,5,3,4,2,1,2,5,3,2,1,2,4,2,1,3,2,1,2,3,1,2,3,4,4,4,1,2,5,3,5),
  col2=c(2,1,1,7,4,1,2,7,5,7,2,6,2,2,6,3,4,3,2,5,7,5,6,4,4,6,5,6,4,1,7,7,2,7,7,2,3,7,2,4)
)

crosstab_sum <- function(dat1,var1,var2){
  
  var1 <- rlang::parse_expr(var1)
  var2 <- rlang::parse_expr(var2)
  
  dat1 = dat1 %>% select(!!var1,!!var2)
  var_lab(dat1[[1]]) <- ""
  var_lab(dat1[[2]]) <- ""
  tab1 <- cro_cpct(dat1[[1]],dat1[[2]])
  tab1 <- as.data.frame(tab1)
  tab1[is.na(tab1)] <- 0
  tab1 <- tab1 %>% mutate_if(is.numeric,round,digits=1) 
    tab1[nrow(tab1), ] <- ifelse(tab1[nrow(tab1), ] %in% c(3, 4, 5), "---", tab1[nrow(tab1), ])
  tab1[-nrow(tab1), -1] <- sapply(tab1[-nrow(tab1), -1], function(x) paste(x, "%"))
  tab1 <- flextable::flextable(tab1)
  tab1
}

crosstab_sum(dat1 = df, var1 = "col1", var2 = "col2")

Great , Thanks alot, one more thing , i also want to concatenate "%" with all values except total

I made the necessary edit to my solution above. Don't forget to mark it as the solution if it solves your problem. It may help future readers.

Hi this is still not working , giving opposite result as required

i am looking for like below

1	2	3	4	5	6	7

1 19% 12% 15% 17% 18% 19% 15%
2 17% 13% 18% 18% 15% 18% 16%
3 14% 15% 17% 16% 13% 19% 17%
4 19% 15% 12% 18% 17% 15% 18%
5 19% 13% 16% 12% 17% 14% 13%
total 76 87 164 45 53 63 47

Okay, I understand better now. Check the new code. I just made an edit.

Thanks , yay....it works now, but still i required your more help in this in future

Hi Gueyenono , Do we have solution if total falls in (3,4,5) then whole column values will replace with "--" like below

  1. if total falls in (3,4,5) then all column will not show any value (replace by "--")
  2. also if the values are like 2.0 or 44.0 the it also show decimal point 0 rather than 22,44

i have tried but not able to do

Sorry, I did not see this earlier. If you need my help, just write a new question and tag me on it. I'll be glad to help.

I dont know how to tag, but the question is Masking Values for column in function

This topic was automatically closed 7 days after the last reply. New replies are no longer allowed.