Sometimes subtypes will not be pre-defined, but rather it will be of interest to identify subtypes that differ maximally with respect to risk heterogeneity based on some number of disease markers.
This tutorial will introduce you to the
optimal_kmeans_d() function, which will run \(k\)-means clustering, using the
kmeans() function, on disease marker data and identify the
subtype solution that maximizes \(D\).
When \(k\)-means clustering is run with
multiple random starts, it will return a variety of class solutions, as
the algorithm typically reaches a local rather than global maxima. Then
for each candidate class solution, \(D\) can be computed and the solution that
maximizes \(D\), a measure of etiologic
heterogeneity, can be identified. This function is currently for use
with case-control data only. See Tutorial:
Estimate the extent of etiologic heterogeneity for details on the
calculation of the \(D\) value.
This tutorial will make use of a simulated example dataset named
subtype_data. This simulated dataset contains 1200 case
subjects and 800 control subjects. There are 30 continuous disease
markers available on the cases. There are two continuous risk factors
and one binary risk factor available on all subjects.
Say for example that interest was in identifying the optimally
etiologically heterogeneous 3-subtype solution based on all 30 markers
y30 available in
using all three risk factors
x3. We use the default of 100 random starts of the \(k\)-means clustering algorithm, and set a
seed so that results would be reproduced if we were to run this code
again on a later date. Note that this function is currently a bit slow
to run due to the fitting of numerous models, so please be patient.
library(riskclustr) res <- optimal_kmeans_d( markers = c(paste0("y", seq(1:30))), M = 3, factors = list("x1", "x2", "x3"), case = "case", data = subtype_data, nstart = 100, seed = 81110224) #> Warning: `data_frame()` was deprecated in tibble 1.1.0. #> Please use `tibble()` instead.
The function returns a list with one element for the optimal \(D\) value and one element that is the original data frame with a column added for the optimal \(D\) class solution.
First let’s look at a tabulation of
optimal_d_data object to see how each case was
classified into a subtype:
table(res[["optimal_d_data"]]$optimal_d_label) #> #> 0 1 2 3 #> 800 301 300 599
These subtype labels could now be used as the outcome in a polytomous
logistic regression model fit with
obtain measures of risk factor association as well as heterogeneity
\(p\)-values. See Tutorial: test for etiologic heterogeneity in a
case-control study for details.
Next we can see the \(D\) value that goes long with the optimal subtype solution:
res[["optimal_d"]] #>  0.3385876
We see that this optimal 3-subtype solution based on clustering the 30 disease markers results in \(D=0.339\).