#' Analyze P-Value and Outcome Ratios for Clusters
#'
#' This function performs an analysis of p-values and outcome ratios related to clusters in a dataset. It calculates the ratio of positive outcomes within each cluster and computes p-values for the association between clusters and the outcome variable.
#'
#' @param data_train A list representing the training data. This list must include the following components:
#' \itemize{
#'   \item \code{C}: An integer vector of cluster assignments for each sample.
#'   \item \code{data_v}: A matrix or data frame of additional covariates.
#'   \item \code{data_y}: A binary response vector with values 0 or 1, representing the outcome variable.
#' }
#' @param num_clusters An integer specifying the number of clusters in the data.
#' @param if_check A logical value indicating whether to print intermediate steps for debugging purposes. Default is \code{FALSE}.
#'
#' @return A list containing the following components:
#' \itemize{
#'   \item \code{dict_outcome_ratio}: A numeric vector representing the ratio of positive outcomes (where \code{data_y} equals 1) within each cluster.
#'   \item \code{dict_p_value}: A list of p-values, with each element corresponding to a pair of clusters. The p-values are calculated using a likelihood ratio test for the association between the clusters and the outcome variable.
#' }
#'
#' @details
#' The \code{analysis_p_value_related} function performs the following steps:
#' \enumerate{
#'   \item Converts the cluster assignments into a one-hot encoded matrix and counts the occurrences of each cluster.
#'   \item Calculates the ratio of positive outcomes within each cluster.
#'   \item Combines the cluster one-hot encodings with additional covariates to create a matrix of predictor variables.
#'   \item Iteratively removes one or two clusters from the predictor matrix and calculates the p-value for the remaining clusters using the \code{\link{p_value_calculate}} function.
#' }
#' @examples
#' set.seed(1)
#' n <- 80L
#' data_train <- list(
#'   C      = sample(0:1, n, replace = TRUE),
#'   data_v = matrix(rbinom(n * 3L, 1, 0.5), n, 3L),
#'   data_y = rbinom(n, 1, 0.3)
#' )
#' result <- analysis_p_value_related(data_train, num_clusters = 2L)
#' result$dict_outcome_ratio   # outcome rate per cluster
#' result$dict_p_value          # LRT p-value for the cluster pair
#' @export


analysis_p_value_related <- function(data_train, num_clusters, if_check = FALSE) {
  data_C <- data_train$C
  data_v <- data_train$data_v
  data_y <- data_train$data_y

  list_c <- as.integer(data_C)
  list_onehot <- matrix(0, nrow = length(list_c), ncol = num_clusters)
  dict_c_count <- integer(num_clusters)
  dict_outcome_in_c_count <- integer(num_clusters)

  for (i in seq_along(list_c)) {
    list_onehot[i, list_c[i] + 1] <- 1
    dict_c_count[list_c[i] + 1] <- dict_c_count[list_c[i] + 1] + 1
    if (data_y[i] == 1) {
      dict_outcome_in_c_count[list_c[i] + 1] <- dict_outcome_in_c_count[list_c[i] + 1] + 1
    }
  }

  if (if_check) {
    message("--------")
    message("num_clusters=", num_clusters, "")
    message("")
    message("list_c[0]=", list_c[1], "")
    message("list_onehot[0,]=", list_onehot[1,], "")
    message("")
    message("list_c[1]=", list_c[2], "")
    message("list_onehot[1,]=", list_onehot[2,], "")
    message("--------")
  }
  message("dict_c_count=", dict_c_count, "")
  message("dict_outcome_in_c_count=", dict_outcome_in_c_count, "")

  dict_outcome_ratio <- dict_outcome_in_c_count / dict_c_count
  message("dict_outcome_ratio=", dict_outcome_ratio, "")

  var_c <- list_onehot
  var_v <- data_v
  depend_y <- data_y

  var_cpv <- cbind(var_c, var_v)
  if (if_check) {
    message("var_c.shape=", dim(var_c), ", var_v.shape=", dim(var_v), ", depend_y.shape=", length(depend_y), "")
    message("var_cpv.shape=", dim(var_cpv), "")
  }

  message("analysis done!")
  dict_p_value <- list()
  for (k1 in seq_len(num_clusters) - 1) {
    X_remove_k1 <- var_cpv
    slices_k1 <- setdiff(seq_len(ncol(var_cpv)), k1 + 1)
    X_remove_k1 <- X_remove_k1[, slices_k1, drop = FALSE]

    for (k2 in seq_len(max(0L, num_clusters - k1 - 1L)) + k1 + 1L) {
      X_remove_k1k2 <- var_cpv
      slices_k1k2 <- setdiff(seq_len(ncol(var_cpv)), c(k1 + 1, k2))
      X_remove_k1k2 <- X_remove_k1k2[, slices_k1k2, drop = FALSE]

      message("---------")
      message("k1=", k1, ", k2=", k2 - 1, "")
      message("slices_k1=", slices_k1, "")
      message("slices_k1k2=", slices_k1k2, "")
      p_value_k1k2 <- p_value_calculate(X_remove_k1, depend_y, 0, X_remove_k1k2)
      dict_p_value[[paste(k1, k2 - 1, sep = ",")]] <- p_value_k1k2
    }
  }
  message("dict_p_value=", unlist(dict_p_value), "")
  return(list(dict_outcome_ratio = dict_outcome_ratio, dict_p_value = dict_p_value))
}
