Search code examples
rplotsjplot

sjp.likert command in sjplot, factor or numeric?, why two different results?


I am obtaining 2 different results from my data using the sjp.likert command, this is my code:

library(sjPlot)

l <- c(1,2,2,2,3,3,4,4,5,5,5,4,3,2,2)

lab <- c("strongly not agree",
         "not agree",
         "Neutral",
         "Agree",
         "Strongly agree")


sjp.likert(items       = l,
           cat.neutral = 3,
           catcount    = 4,
           legend.labels = lab)

notice that i am working with a numeric variable not factor, at this point everything looks ok, but sometimes i prefer to work with factor to omit the legend.labels parameter. So i use this

l.factor <- factor(x = l,labels = lab)

sjp.likert(items       = l.factor,
           cat.neutral = 3,
           catcount    = 4)

But this is where i get the problem, for example: the "neutral" response is not longer 20%, now is 6.7%. As far i can see the package is reading the "neutral" response as neutral, because the grey color in right side.

You can see that the proper number is 20% using this

prop.table(table(l.factor))
prop.table(table(l))

What i am doing wrong? is this a bug?


Solution

  • The problem is that re-ordering the values inside the sjp-likert()-function (if you have a neutral category) is based on numeric indices - which does not work with factors with character levels. So you have to re-order your factor levels before calling the function:

    l.factor <- factor(x = l,labels = lab[c(1,2,4,5,3)])
    
    sjp.likert(items       = l.factor,
               cat.neutral = 5,
               catcount    = 4)
    

    Another way is to convert factors into numeric values and set the factor levels as label-attribute. You can do this with sjmisc::to_value() with argument keep.labels = TRUE. Taking your example, and modifying it slighlty:

    l <- c(1,2,2,2,3,3,4,4,5,5,5,4,3,2,2)
    
    lab <- c("strongly not agree",
             "not agree",
             "Neutral",
             "Agree",
             "Strongly agree")
    
    l.factor <- factor(x = l,labels = lab)
    
    l.factor <- to_value(l.factor, keep.labels = T)
    
    sjp.likert(items       = l.factor,
               cat.neutral = 3,
               catcount    = 4)
    

    to_value() works both on vectors and data frame, so you can easily convert factors in your data frame into numeric, keeping the value labels:

    to_value(my_data_frame, keep.labels = T)