Search code examples
rmachine-learningr-caretnaivebayes

Naive Bayees in klaR and caret


I do apply Naive Bayes to a toy dataset using the package klaR and everything works fine.

Next, I want to replicate the same analysis with caret using method="nb", which is indeed only a wrapper for the NaiveBayes function in the klaR package.

However, the latter estimation does not work. I do get an error message.

Error in NaiveBayes.default(x, y, usekernel = FALSE, fL = param$fL, ...) : 
  Zero variances for at least one class in variables: x1_disc_46, x1_disc_810, x2_disc_46
Timing stopped at: 0.01 0 0.02

I am aware of the limitations of the toy dataset. However as the analysis with the klaR package does run through, I wonder how to replicate the exact same analysis with caret?

Here is the code:

# Data
d <- structure(list(Y = structure(c(1L, 1L, 1L, 1L, 2L, 2L, 2L, 2L, 
2L, 1L), .Label = c("0", "1"), class = "factor"), x1_disc = structure(c(1L, 
2L, 1L, 2L, 3L, 4L, 4L, 5L, 2L, 4L), .Label = c("_02", "_24", 
"_46", "_68", "_810"), class = "factor"), x2_disc = structure(c(1L, 
1L, 1L, 1L, 2L, 3L, 3L, 3L, 1L, 2L), .Label = c("_02", "_24", 
"_46"), class = "factor")), .Names = c("Y", "x1_disc", "x2_disc"
), row.names = c(NA, -10L), class = "data.frame")



# Works(klaR)
library(klaR)
fit2 <- NaiveBayes(Y ~ x1_disc + x2_disc, usekernel = FALSE, fL = 0, data=d)
predict(fit2, d, threshold = 0)


# Does not work (caret)
library(caret)
model2 <- train(form=Y ~ x1_disc + x2_disc, 
                data=d,
                method="nb",  
                # Uses package klaR 
                # (see: http://topepo.github.io/caret/train-models-by-tag.html)
                trControl=trainControl(method="none"),
                tuneGrid = data.frame(fL=0, usekernel=F, adjust=1))

predict(model2, d, type="prob")

Solution

  • I make my comment into an answer since it solved your issue partially. I came across this Cross Validated answer that suggested to run the caret model without the S3 formula interface which would be in your case:

    model2 <- train(y=d$Y, x=d[, 2:3], ...)
    

    I don't know the exact reason why this makes the trick, and it's probably a different explanation than for the CV question since they didn't have the error.