# Define `pred_ra` and `prob_ra` for a linear model.
#
# Copyright (C) 2025, Togaware Pty Ltd.
#
# License: GNU General Public License, Version 3 (the "License")
# https://www.gnu.org/licenses/gpl-3.0.en.html
#
# Time-stamp: <Thursday 2025-03-06 10:14:45 +1100 Graham Williams>
#
# Licensed under the GNU General Public License, Version 3 (the "License");
#
# This program is free software: you can redistribute it and/or modify it under
# the terms of the GNU General Public License as published by the Free Software
# Foundation, either version 3 of the License, or (at your option) any later
# version.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
# details.
#
# You should have received a copy of the GNU General Public License along with
# this program.  If not, see <https://www.gnu.org/licenses/>.
#
# Author: Zheyuan Xu

# Rattle timestamp: TIMESTAMP
#
# References:
#
# @williams:2017:essentials Chapter 7.
# https://survivor.togaware.com/datascience/dtrees.html
# https://survivor.togaware.com/datascience/ for further details.

# 20241220 gjw Save the model to the TEMPLATE variable `model`. This
# will be used below and in the following evaluations as required.

model <- model_glm

# 20250305 gjw Specify the model type and the model description.

mtype <- "linear"
mdesc <- "Linear Model"

# 20250101 gjw Define the template functions to generate the
# predications and the probabilities.
##
## Rattle V5 does this:
##
## crs$pr <- as.vector(ifelse(predict(crs$glm,
##   type    = "response",
##   newdata = crs$dataset[crs$validate, c(crs$input, crs$target)]) > 0.5, "Yes", "No"))
##
## 20250305 gjw This is hard wiring Yes and No. Need to get the actual
## dataset classes.
##
## 20250305 gjw Currently I am getting an EXTRA LEVELS error
##
##   factor wind_dir_9am has new levels SW, WNW

pred_ra <- function(model, data) {
  # Retrieve the vector of possible target levels from the data.

  target_levels <- unique(data[[target]])

  # Get raw numeric probabilities (assuming the model returns a single column
  # or you've already extracted the relevant column.

  prob_vec <- predict(model, newdata=data, type="response")

  # Map probabilities to factor levels.
  # - If the probability is NA, set the label to NA.
  # - If the probability > 0.5, pick target_levels[2].
  # - Otherwise, pick target_levels[1].
  # We immediately convert to character so the ifelse() doesn't
  # accidentally coerce things back to numeric.
##
## 20250306 gjw Why is NA as a character needed?

  mapped_values_char <- ifelse(
    is.na(prob_vec),
    NA_character_,
    ifelse(prob_vec > 0.5,
           as.character(target_levels[2]),
           as.character(target_levels[1]))
  )

  # Convert the character vector to a factor with the same levels as 'target_levels'.
  # This ensures the output is not numeric, but a factor with consistent levels.

  mapped_values_factor <- factor(mapped_values_char, levels=target_levels)

  # Return the factor vector.

  return(mapped_values_factor)
}

prob_ra <- function(model, data) predict(model, newdata=data, type="response")
