# Analysing rank-ordered data using mlogit

I am trying to analyse rank-ordered data using a logit model as described here (more specifically the model in 5.1). Right now I am not interested in the effect of any covariates but only want to asses the item specific differences by looking at the corresponding log odds. If I understand correctly I can achieve this by only including a constant term as the individual specific variable and removing any other intercepts. I am using the mlogit package in R and from what I have gathered from the vignette (especially the example for rank-ordered logit models in 2.8) I tried to do the following:

library(mlogit)
data("Game", package = "mlogit")
G <- mlogit.data(Game, shape="wide", choice="ch", varying=1:12, ranked=TRUE)
summary(mlogit(ch ~ 1 | -1 | -1,G))


This gets me the following error message:

Error in rownames<-(*tmp*, value = c("1.GameBoy", "1.GameCube", "1.PC",  :
attempt to set 'rownames' on an object with no dimensions


It is pretty obvious that I have a misconception about the way the mlogit formula has to be constructed so I tried to play around a bit and the only thing I got which looked like what I wanted was the following:

    Call:
mlogit(formula = ch ~ alt | -1 | -1, data = G, method = "nr",
print.level = 0)

Frequencies of alternatives:
GameBoy    GameCube          PC PlayStation  PSPortable        Xbox
0.13846     0.13407     0.17363     0.18462     0.17363     0.19560

nr method
4 iterations, 0h:0m:0s
g'(-H)^-1g = 0.000575
successive function values within tolerance limits

Coefficients :
Estimate Std. Error t-value  Pr(>|t|)
GameCube:(intercept)    0.058678   0.182572  0.3214  0.747911
PC:(intercept)          1.275749   0.194292  6.5661 5.164e-11 ***
PlayStation:(intercept) 1.273903   0.191226  6.6618 2.705e-11 ***
PSPortable:(intercept)  0.622355   0.181645  3.4262  0.000612 ***
Xbox:(intercept)        1.401230   0.189758  7.3843 1.532e-13 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Log-Likelihood: -546.82


However, this is not very satisfactory since to me it seems strange to include the alternative as an individual specific covariate. Can anyone with experience of how to fit such a model in R using the mlogit package help?

P.S.: I was unsure whether this question is better suited for CV or StackOverflow but since the underlying question is a statistical one I chose to put it here.

• As you believe the underlying question to be statistical, it's best to reduce the R content here and make that question clearer, especially because after a month no one has replied so far except in R terms. More crucially, why not fit a model designed for ordinal responses? Feb 11, 2016 at 10:08

My experience is still rather limited with mlogit package, but if I read Croissant vignette correctly (see the beginning of sec. 1.2 Model description, page 7), the alt variable in your model is specified as alternative specific with a generic coefficient and NOT as an individual specific covariate---those variables are placed between the pipes.

• No need here for salutations or signatures: edited accordingly. We have no desire to be or seem unfriendly; it's just that keeping posts concise and technical is good long-term, just as you wouldn't expect encyclopedia entries to start Hi! and end Hope you found this useful! Feb 11, 2016 at 10:06

I used the model format you mentioned at the end and was able to reproduce the LRS listed for example 8.1 in the J Marden text (Analyzing and Modeling Rank Data):

> exData = t(matrix(c(c(1,2,4,3,5), c(2,1,4,3,5), c(2,3,5,4,1), rep(c(2,1,5,3,4), 3)), nrow=5))
> exData
[,1] [,2] [,3] [,4] [,5]
[1,]    1    2    4    3    5
[2,]    2    1    4    3    5
[3,]    2    3    5    4    1
[4,]    2    1    5    3    4
[5,]    2    1    5    3    4
[6,]    2    1    5    3    4
> exTbl = as.data.table(exData)[, id := 1:.N][, melt(.SD, id.vars='id')][order(id, variable)][, setnames(.SD, 'value', 'ch')][, setnames(.SD, 'variable', 'alt')]
id alt ch
1:  1  V1  1
2:  1  V2  2
3:  1  V3  4
4:  1  V4  3
5:  1  V5  5
6:  2  V1  2
> exLogit = mlogit.data(exTbl, shape='long', ranked=T, choice='ch', alt.var='alt', id.var='id')
id alt    ch
1.V1  1  V1  TRUE
1.V2  1  V2 FALSE
1.V3  1  V3 FALSE
1.V4  1  V4 FALSE
1.V5  1  V5 FALSE
2.V2  1  V2  TRUE
> m1 = summary(mlogit(ch ~ alt | -1 | -1, exLogit, reflevel='V5'))
> m1

Call:
mlogit(formula = ch ~ alt | -1 | -1, data = exLogit, reflevel = "V5",
method = "nr", print.level = 0)

Frequencies of alternatives:
V5     V1     V2     V3     V4
0.1667 0.2500 0.2500 0.0833 0.2500

nr method
6 iterations, 0h:0m:0s
g(-H)^-1g = 4.08E-06
successive function values within tolerance limits

Coefficients :
Estimate Std. Error t-value Pr(>|t|)
V1:(intercept)    4.182      1.465    2.86   0.0043 **
V2:(intercept)    4.689      1.514    3.10   0.0020 **
V3:(intercept)   -0.726      0.867   -0.84   0.4024
V4:(intercept)    2.061      1.133    1.82   0.0690 .
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Log-Likelihood: -14.4
> llNull = -sum(log(1:5)) * 6
> llNull
[1] -28.72
> m1$logLik 'log Lik.' -14.4 (df=4) > LRS = 2 * (m1$logLik - llNull)
> LRS
'log Lik.' 28.64 (df=4)
>
[0] 0:NvimR*


I lifted the method to compute the log likelihood for the null model from another stats package, so it may/may not be correct. Although using it does make the result line up with the example 8.1 in the text, so it's likely correct.

I was surpised that the log likelihood value for the null model is only a function of the number of alternatives and number of subjects, and not influenced by the data observed. The data observed seems to only influence the log likelihood for the alternative model. If someone has an intuitive explanation as to why this is the case, please feel free to add that to this post.

• Not surprising to me that "the null model is only a function of the number of alternatives and number of subjects," but it is related to Frequencies of alternatives in the fitted model print. The null model is one with the (alternative-specific) intercept only. Within mlogit, the null-model formula would be y ~ 0 | 1. Since you used an equivalent parametrization, it is ch ~ alt | 0 or ch ~ alt | -1 in your case. Dec 9, 2023 at 5:00