Este projeto utiliza dados de acelerômetros de 6 participantes realizando exercícios com halteres. O objetivo é prever a classe do exercício (A, B, C, D, E) – que representa a qualidade do movimento – com base em variáveis de sensores.
Os dados foram obtidos da fonte: http://groupware.les.inf.puc-rio.br/har.
# URLs dos dados
train_url <- "https://d396qusza40orc.cloudfront.net/predmachlearn/pml-training.csv"
test_url <- "https://d396qusza40orc.cloudfront.net/predmachlearn/pml-testing.csv"
# Carregar dados
train_raw <- read.csv(train_url, na.strings = c("NA", "#DIV/0!", ""))
test_raw <- read.csv(test_url, na.strings = c("NA", "#DIV/0!", ""))# Remover colunas com mais de 90% de valores NA
na_threshold <- 0.9
# IMPORTANTE: a seleção de colunas é feita SOMENTE com base no conjunto de
# treino, e depois aplicada ao teste. Fazer essa seleção separadamente em
# train_raw e test_raw pode gerar conjuntos de colunas diferentes entre os
# dois, o que quebra (ou distorce) a previsão final do modelo.
cols_to_keep <- names(train_raw)[colMeans(is.na(train_raw)) < na_threshold]
train_clean <- train_raw[, cols_to_keep]
# "classe" não existe no conjunto de teste (é a variável a ser prevista)
cols_to_keep_test <- setdiff(cols_to_keep, "classe")
test_clean <- test_raw[, cols_to_keep_test]
# Remover colunas irrelevantes
col_irrelevantes <- c(
"X",
"user_name",
"raw_timestamp_part_1",
"raw_timestamp_part_2",
"cvtd_timestamp",
"new_window",
"num_window"
)
train_clean <- train_clean[, !(names(train_clean) %in% col_irrelevantes)]
test_clean <- test_clean[, !(names(test_clean) %in% col_irrelevantes)]
# Remover problem_id do conjunto de teste
test_clean <- test_clean[, names(test_clean) != "problem_id"]
# Transformar a variável resposta em fator
train_clean$classe <- as.factor(train_clean$classe)
# Conferir as classes
print(levels(train_clean$classe))## [1] "A" "B" "C" "D" "E"
##
## A B C D E
## 5580 3797 3422 3216 3607
## [1] 19622 53
## [1] 20 52
## 'data.frame': 19622 obs. of 10 variables:
## $ roll_belt : num 1.41 1.41 1.42 1.48 1.48 1.45 1.42 1.42 1.43 1.45 ...
## $ pitch_belt : num 8.07 8.07 8.07 8.05 8.07 8.06 8.09 8.13 8.16 8.17 ...
## $ yaw_belt : num -94.4 -94.4 -94.4 -94.4 -94.4 -94.4 -94.4 -94.4 -94.4 -94.4 ...
## $ total_accel_belt: int 3 3 3 3 3 3 3 3 3 3 ...
## $ gyros_belt_x : num 0 0.02 0 0.02 0.02 0.02 0.02 0.02 0.02 0.03 ...
## $ gyros_belt_y : num 0 0 0 0 0.02 0 0 0 0 0 ...
## $ gyros_belt_z : num -0.02 -0.02 -0.02 -0.03 -0.02 -0.02 -0.02 -0.02 -0.02 0 ...
## $ accel_belt_x : int -21 -22 -20 -22 -21 -21 -22 -22 -20 -21 ...
## $ accel_belt_y : int 4 4 5 3 2 4 3 4 2 4 ...
## $ accel_belt_z : int 22 22 23 21 24 21 21 21 24 22 ...
## roll_belt pitch_belt yaw_belt total_accel_belt
## Min. :-28.90 Min. :-55.8000 Min. :-180.00 Min. : 0.00
## 1st Qu.: 1.10 1st Qu.: 1.7600 1st Qu.: -88.30 1st Qu.: 3.00
## Median :113.00 Median : 5.2800 Median : -13.00 Median :17.00
## Mean : 64.41 Mean : 0.3053 Mean : -11.21 Mean :11.31
## 3rd Qu.:123.00 3rd Qu.: 14.9000 3rd Qu.: 12.90 3rd Qu.:18.00
## Max. :162.00 Max. : 60.3000 Max. : 179.00 Max. :29.00
## gyros_belt_x gyros_belt_y gyros_belt_z accel_belt_x
## Min. :-1.040000 Min. :-0.64000 Min. :-1.4600 Min. :-120.000
## 1st Qu.:-0.030000 1st Qu.: 0.00000 1st Qu.:-0.2000 1st Qu.: -21.000
## Median : 0.030000 Median : 0.02000 Median :-0.1000 Median : -15.000
## Mean :-0.005592 Mean : 0.03959 Mean :-0.1305 Mean : -5.595
## 3rd Qu.: 0.110000 3rd Qu.: 0.11000 3rd Qu.:-0.0200 3rd Qu.: -5.000
## Max. : 2.220000 Max. : 0.64000 Max. : 1.6200 Max. : 85.000
## accel_belt_y accel_belt_z
## Min. :-69.00 Min. :-275.00
## 1st Qu.: 3.00 1st Qu.:-162.00
## Median : 35.00 Median :-152.00
## Mean : 30.15 Mean : -72.59
## 3rd Qu.: 61.00 3rd Qu.: 27.00
## Max. :164.00 Max. : 105.00
# Distribuição da variável resposta (classe)
ggplot(train_clean, aes(x = classe)) +
geom_bar(fill = "steelblue") +
labs(title = "Distribuição da Classe", x = "Classe", y = "Frequência")# Correlação entre variáveis numéricas
num_vars <- train_clean[, sapply(train_clean, is.numeric)]
cor_matrix <- cor(num_vars, use = "pairwise.complete.obs")
corrplot(cor_matrix, method = "color", type = "upper", tl.cex = 0.4, number.cex = 0.5)set.seed(123)
# Garantir que classe seja fator
train_clean$classe <- factor(train_clean$classe)
# Dividir em 70% treino e 30% validação
inTrain <- createDataPartition(
train_clean$classe,
p = 0.7,
list = FALSE
)
training <- train_clean[inTrain, ]
validation <- train_clean[-inTrain, ]
# Verificar dimensões
print(dim(training))## [1] 13737 53
## [1] 5885 53
##
## A B C D E
## 3906 2658 2396 2252 2525
##
## A B C D E
## 1674 1139 1026 964 1082
# Previsão na validação
pred_rf <- predict(model_rf, validation)
# Matriz de confusão
confusionMatrix(pred_rf, validation$classe)## Confusion Matrix and Statistics
##
## Reference
## Prediction A B C D E
## A 1674 4 0 0 0
## B 0 1131 2 0 0
## C 0 4 1024 8 4
## D 0 0 0 956 4
## E 0 0 0 0 1074
##
## Overall Statistics
##
## Accuracy : 0.9956
## 95% CI : (0.9935, 0.9971)
## No Information Rate : 0.2845
## P-Value [Acc > NIR] : < 2.2e-16
##
## Kappa : 0.9944
##
## Mcnemar's Test P-Value : NA
##
## Statistics by Class:
##
## Class: A Class: B Class: C Class: D Class: E
## Sensitivity 1.0000 0.9930 0.9981 0.9917 0.9926
## Specificity 0.9991 0.9996 0.9967 0.9992 1.0000
## Pos Pred Value 0.9976 0.9982 0.9846 0.9958 1.0000
## Neg Pred Value 1.0000 0.9983 0.9996 0.9984 0.9983
## Prevalence 0.2845 0.1935 0.1743 0.1638 0.1839
## Detection Rate 0.2845 0.1922 0.1740 0.1624 0.1825
## Detection Prevalence 0.2851 0.1925 0.1767 0.1631 0.1825
## Balanced Accuracy 0.9995 0.9963 0.9974 0.9954 0.9963
# Erro fora da amostra (out-of-sample error)
oos_error <- mean(pred_rf != validation$classe)
cat("Erro fora da amostra estimado:", round(oos_error * 100, 2), "%")## Erro fora da amostra estimado: 0.44 %
## Acurácia esperada: 99.56 %
# Erro dentro da amostra (in-sample)
insample_error <- mean(predict(model_rf, training) != training$classe)
cat("Erro dentro da amostra:", round(insample_error * 100, 2), "%")## Erro dentro da amostra: 0 %
## 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
## B A B A A E D B A A B C B A E E A B B B
## Levels: A B C D E