I'm using coxph from Therneau et al's survival package to model a multi-state system. Transitions include:

  1. Baseline -> Disease
  2. Disease -> Disease (re-hospitalization)
  3. Baseline -> Death
  4. Disease -> Death

(Death is an absorbing state.)

A key variable for predicting the Disease->Disease transition (re-hospitalization) is the number of days since the last hospitalization. (This is a time-varying model, and I increment time in 30-day increments until the next disease recurrence, final censoring, or death.)

As you can imagine, days since the last hospitalization doesn't even exist for people in the Baseline state. This is a problem for the survival package's multi-state model, because (at least as far as I understand its implementation), it wants to use the same variables to predict all of the transitions. (A slight caveat is that it can be forced to set the same coefficients for a variable for multiple transitions.)

Ideally, I'd like to be able to remove the days since the last hospitalization component of the model for the Baseline->Disease transition prediction. There are hacks to get around this, somewhat: I can set it to 0 (but then I'll get singularities, e.g., when I check cox.zph: Error in solve.default(imat, u): system is computationally singular). And sure, I can then set it to 0 +/- noise to prevent those singularities. But both of these approaches feel like technical workarounds that aren't strictly defensible.

Is there a way to remove a variable for a specific transition (or set of transitions)? If not, is there a generally accepted way of handling variables that only apply for some initial states and not others?


1 Answer 1


This is not a direct solution to your issue, but you could try using the mstate package.

After transforming data in long format with msprep, using expcovs you can create and add to the dataset transition-specific covariates, which you can then separately include in your model.

Considering the 4 transitions reported above, your Cox model should look something like this: coxph(Surv(Tstart, Tstop, status) ~ cov.1 + cov.2 + cov.3 + cov.4 + dayslasthosp.2 + dayslasthosp.4 + strata(trans), data=msdata), where .j identifies covariates specific to transition j. The covariate 'days since last hospitalization' (dayslasthosp) is included only for transitions 2 and 4.

The vignettes and tutorials available with the package are very informative, and guide you step-by-step through cases like this.

  • 1
    $\begingroup$ Very cool, I will take a look. Especially given my understanding that mstate uses survival under the hood, I think this implies that I may be able to dig through the mstate code to achieve this. Thanks! $\endgroup$ Commented Oct 13, 2021 at 19:10
  • $\begingroup$ Actually digging through their description, "... Then it will take the value 0 for all rows in the long format dataframe for which trans does not equal s". So it seems to be the case that setting the value to 0 is reasonable. I guess my problem may actually be that cox.zph does not like this approach (perceives singularities). Maybe that's where I need to dig in further. $\endgroup$ Commented Oct 13, 2021 at 19:14
  • 1
    $\begingroup$ Indeed. I have actually used cox.zph to test the PH assumption on a similar Cox model (different transition-specific covariates for different transitions), and I had no problems. Again, I am not sure what's the specific issue triggering the singularities error... Do you set to 0 missing values of that specific covariate and then just keep it in the model? This is all very experimental, but maybe you could try creating an 'expanded covariate' as you would do with mstate and then include this bundle of transition-specific 'pieces' in the model, just to see what happens. $\endgroup$
    – Alessandro
    Commented Oct 13, 2021 at 20:12
  • 1
    $\begingroup$ Yes agreed, I can usually use cox.zph just fine with multi-state models. The issue mostly comes up with highly time-dependent covariates such as age, and time-since-event. I have a large dataset and it basically needs a 10-degree-of-freedom spline on starting age to avoid violating the PH assumption. The problem is that "time since event" seems to need that too, which leads to 10 degrees of "0" for the state that hasn't yet had an event. I think this is what makes the matrix non-invertible, causing problems for cox.zph, but this is just intuition. $\endgroup$ Commented Oct 13, 2021 at 20:19
  • 1
    $\begingroup$ To conclude - thanks to your pointer to the mstate package, I was able to see that having values that do not vary (within a particular state) is an accepted way of achieving the goal of transition-specific covariates, so your post answers my question. $\endgroup$ Commented Oct 13, 2021 at 21:02

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.