L'arrière-plan du compte officiel enregistre divers indicateurs de lecture des articles publiés, notamment : le titre du contenu, le nombre total de lecteurs, le nombre total de lectures, le nombre total de partageurs, le nombre total de partages, le nombre de followers après lecture, le taux de lecture délivré, le nombre de lectures générées par le partage, le taux de premier partage, le nombre de lectures apportées par chaque partage et le taux d'achèvement des lectures.
Nous essayons d'utiliser l'algorithme de forêt aléatoire dans l'apprentissage automatique pour prédire s'il existe certains indicateurs ou combinaisons d'indicateurs qui peuvent prédire le nombre d'abonnés après la lecture.
Format des données et lecture des données
L'ensemble de données comprend 9 indicateurs statistiques pour 1588 articles.
Lire la matrice de statistiques : WeChatOfficialAccount.txt
Nombre de followers après lecture :
WeChatOfficialAccountFollowers.txt
feature_file <- "data/WeChatOfficialAccount.txt"
metadata_file <- "data/WeChatOfficialAccountFollowers.txt"
feature_mat <- read.table(feature_file, row.names = 1, header = T, sep="\t", stringsAsFactors =T)
# 处理异常的特征名字
# rownames(feature_mat) <- make.names(rownames(feature_mat))
metadata <- read.table(metadata_file, row.names=1, header=T, sep="\t", stringsAsFactors =T)
dim(feature_mat)
## [1] 1588 9
La représentation des statistiques de lecture est la suivante :
feature_mat[1:4,1:5]
## TotalReadingPeople TotalReadingCounts TotalSharingPeople TotalSharingCounts ReadingRate
## 1 8278 11732 937 1069 0.0847
## 2 8951 12043 828 929 0.0979
## 3 18682 22085 781 917 0.0608
## 4 4978 6166 525 628 0.0072
La représentation des métadonnées est la suivante
head(metadata)
## FollowersAfterReading
## 1 227
## 2 188
## 3 119
## 4 116
## 5 105
## 6 100
Criblage et séquençage des échantillons
C'est également une opération qui doit être assurée que l'ordre des échantillons dans la table d'échantillons et la table d'expression sont alignés .
feature_mat_sampleL <- rownames(feature_mat)
metadata_sampleL <- rownames(metadata)
common_sampleL <- intersect(feature_mat_sampleL, metadata_sampleL)
# 保证表达表样品与METAdata样品顺序和数目完全一致
feature_mat <- feature_mat[common_sampleL,,drop=F]
metadata <- metadata[common_sampleL,,drop=F]
Qu'il s'agisse de juger la classification ou la régression
Les paramètres ont été donnés lors de la lecture des données plus tôt stringsAsFactors =T
, cette étape peut donc être ignorée.
Si la colonne correspondant au groupe est un nombre, convertissez-la en type numérique - effectuez une régression
Si la colonne correspondant au groupe est regroupée, convertir en type de facteur - effectuer la classification
# R4.0之后默认读入的不是factor,需要做一个转换
# devtools::install_github("Tong-Chen/ImageGP")
library(ImageGP)
# 此处的FollowersAfterReading根据需要修改
group = "FollowersAfterReading"
# 如果group对应的列为数字,转换为数值型 - 做回归
# 如果group对应的列为分组,转换为因子型 - 做分类
if(numCheck(metadata[[group]])){
if (!is.numeric(metadata[[group]])) {
metadata[[group]] <- mixedToFloat(metadata[[group]])
}
} else{
metadata[[group]] <- as.factor(metadata[[group]])
}
Analyse préliminaire de la forêt aléatoire
library(randomForest)
# 查看参数是个好习惯
# 有了前面的基础概述,再看每个参数的含义就明确了很多
# 也知道该怎么调了
# 每个人要解决的问题不同,通常不是别人用什么参数,自己就跟着用什么参数
# 尤其是到下游分析时
# ?randomForest
# 查看源码
# randomForest:::randomForest.default
Après avoir chargé le package, analysez-le directement et ajustez les paramètres après avoir vu le résultat.
# 设置随机数种子,具体含义见 https://mp.weixin.qq.com/s/6plxo-E8qCdlzCgN8E90zg
set.seed(304)
# 直接使用默认参数
rf <- randomForest(feature_mat, metadata[[group]])
En regardant les résultats préliminaires, le type de forêt aléatoire est jugé au fur et à mesure 分类
de la construction d'un arbre, et la décision optimale est prise 500
à partir 3
d'indicateurs sélectionnés au hasard chaque fois qu'une décision est prise ( mtry
), le résidu carré moyenMean of squared residuals
: 39,82736 et le degré de variation expliqué. % Var explained
: 74.91. Le résultat semble normal.
rf
##
## Call:
## randomForest(x = feature_mat, y = metadata[[group]])
## Type of random forest: regression
## Number of trees: 500
## No. of variables tried at each split: 3
##
## Mean of squared residuals: 39.82736
## % Var explained: 74.91
En observant l'effet de prédiction du modèle sur l'ensemble d'apprentissage, il semble que la cohérence ne soit pas mauvaise.
library(ggplot2)
followerDF <- data.frame(Real_Follower=metadata[[group]], Predicted_Follower=predict(rf, newdata=feature_mat))
sp_scatterplot(followerDF, xvariable = "Real_Follower", yvariable = "Predicted_Follower",
smooth_method = "auto") + coord_fixed(1)
Procédure opérationnelle standard de forêt aléatoire
Diviser les ensembles de formation et de test
library(caret)
seed <- 1
set.seed(seed)
train_index <- createDataPartition(metadata[[group]], p=0.75, list=F)
train_data <- feature_mat[train_index,]
train_data_group <- metadata[[group]][train_index]
test_data <- feature_mat[-train_index,]
test_data_group <- metadata[[group]][-train_index]
dim(train_data)
## [1] 1192 9
dim(test_data)
## [1] 396 9
Sélection des fonctionnalités de Boruta pour identifier les variables catégorielles clés
# install.packages("Boruta")
library(Boruta)
set.seed(1)
boruta <- Boruta(x=train_data, y=train_data_group, pValue=0.01, mcAdj=T,
maxRuns=300)
boruta
## Boruta performed 14 iterations in 5.917085 secs.
## 8 attributes confirmed important: AverageReadingCountsForEachSharing, FirstSharingRate,
## ReadingRate, TotalReadingCounts, TotalReadingCountsOfSharing and 3 more;
## 1 attributes confirmed unimportant: ReadingFinishRate;
Regardez les résultats de l'identification de l'importance des variables (en fait, cela a également été reflété dans le résultat ci-dessus), 8
une variable importante, 0
une variable éventuellement importante ( tentative variable
, le score d'importance n'a pas de différence statistique par rapport au meilleur score de la variable fantôme), 1
l'une est variables peu importantes.
table(boruta$finalDecision)
##
## Tentative Confirmed Rejected
## 0 8 1
Tracez l’importance des variables identifiées. S'il y a peu de variables, vous pouvez utiliser le dessin par défaut. Lorsqu'il y a beaucoup de variables, l'image dessinée ne peut pas être vue clairement et vous devez organiser les données et dessiner vous-même.
Définissez une fonction pour extraire la valeur d’importance correspondant à chaque variable.
library(dplyr)
boruta.imp <- function(x){
imp <- reshape2::melt(x$ImpHistory, na.rm=T)[,-1]
colnames(imp) <- c("Variable","Importance")
imp <- imp[is.finite(imp$Importance),]
variableGrp <- data.frame(Variable=names(x$finalDecision),
finalDecision=x$finalDecision)
showGrp <- data.frame(Variable=c("shadowMax", "shadowMean", "shadowMin"),
finalDecision=c("shadowMax", "shadowMean", "shadowMin"))
variableGrp <- rbind(variableGrp, showGrp)
boruta.variable.imp <- merge(imp, variableGrp, all.x=T)
sortedVariable <- boruta.variable.imp %>% group_by(Variable) %>%
summarise(median=median(Importance)) %>% arrange(median)
sortedVariable <- as.vector(sortedVariable$Variable)
boruta.variable.imp$Variable <- factor(boruta.variable.imp$Variable, levels=sortedVariable)
invisible(boruta.variable.imp)
}
boruta.variable.imp <- boruta.imp(boruta)
head(boruta.variable.imp)
## Variable Importance finalDecision
## 1 AverageReadingCountsForEachSharing 4.861474 Confirmed
## 2 AverageReadingCountsForEachSharing 4.648540 Confirmed
## 3 AverageReadingCountsForEachSharing 6.098471 Confirmed
## 4 AverageReadingCountsForEachSharing 4.701201 Confirmed
## 5 AverageReadingCountsForEachSharing 3.852440 Confirmed
## 6 AverageReadingCountsForEachSharing 3.992969 Confirmed
Seules Confirmed
les variables sont tracées. On peut voir sur la figure que les principales 4
variables du classement d'importance sont toutes liées au « partage » (le nombre de lectures générées par le partage, le nombre total de partageurs, le nombre total de partages, le premier taux de partage), et le partage d’articles est très important pour accroître l’attention.
library(ImageGP)
sp_boxplot(boruta.variable.imp, melted=T, xvariable = "Variable", yvariable = "Importance",
legend_variable = "finalDecision", legend_variable_order = c("shadowMax", "shadowMean", "shadowMin", "Confirmed"),
xtics_angle = 90, coordinate_flip =T)
Extraire les variables importantes et les variables potentiellement importantes
boruta.finalVarsWithTentative <- data.frame(Item=getSelectedAttributes(boruta, withTentative = T), Type="Boruta_with_tentative")
data <- cbind(feature_mat, metadata)
variableFactor <- rev(levels(boruta.variable.imp$Variable))
sp_scatterplot(data, xvariable = group, yvariable = variableFactor[1], smooth_method = "auto")
Parce qu'il n'y a pas beaucoup de variables, vous pouvez également l'utiliser ggpairs
pour voir comment toutes les variables sont liées les unes aux autres et comment elles sont liées à la variable de réponse ?
library(GGally)
ggpairs(data, progress = F)
Validation croisée pour choisir les paramètres et ajuster le modèle
Définissez une fonction pour générer des colonnes à tester mtry
(une série de valeurs ne dépassant pas le nombre total de variables).
generateTestVariableSet <- function(num_toal_variable){
max_power <- ceiling(log10(num_toal_variable))
tmp_subset <- c(unlist(sapply(1:max_power, function(x) (1:10)^x, simplify = F)), ceiling(max_power/3))
#return(tmp_subset)
base::unique(sort(tmp_subset[tmp_subset<num_toal_variable]))
}
# generateTestVariableSet(78)
Sélectionner les données liées aux variables caractéristiques clés
# 提取训练集的特征变量子集
boruta_train_data <- train_data[, boruta.finalVarsWithTentative$Item]
boruta_mtry <- generateTestVariableSet(ncol(boruta_train_data))
Réglage et modélisation avec Caret
library(caret)
if(file.exists('rda/wechatRegression.rda')){
borutaConfirmed_rf_default <- readRDS("rda/wechatRegression.rda")
} else {
# Create model with default parameters
trControl <- trainControl(method="repeatedcv", number=10, repeats=5)
seed <- 1
set.seed(seed)
# 根据经验或感觉设置一些待查询的参数和参数值
tuneGrid <- expand.grid(mtry=boruta_mtry)
borutaConfirmed_rf_default <- train(x=boruta_train_data, y=train_data_group, method="rf",
tuneGrid = tuneGrid, #
metric="RMSE", #metric='Kappa'
trControl=trControl)
saveRDS(borutaConfirmed_rf_default, "rda/wechatRegression.rda")
}
borutaConfirmed_rf_default
## Random Forest
##
## 1192 samples
## 8 predictor
##
## No pre-processing
## Resampling: Cross-Validated (10 fold, repeated 5 times)
## Summary of sample sizes: 1073, 1073, 1073, 1072, 1073, 1073, ...
## Resampling results across tuning parameters:
##
## mtry RMSE Rsquared MAE
## 1 6.441881 0.7020911 2.704873
## 2 6.422848 0.7050505 2.720557
## 3 6.418449 0.7052825 2.736505
## 4 6.431665 0.7039496 2.742612
## 5 6.453067 0.7013595 2.754239
## 6 6.470716 0.6998307 2.758901
## 7 6.445304 0.7020575 2.756523
##
## RMSE was used to select the optimal model using the smallest value.
## The final value used for the model was mtry = 3.
Précision du traçage par rapport aux hyperparamètres
plot(borutaConfirmed_rf_default)
Tracez les 20 variables avec la contribution la plus élevée (l'importance des variables évaluées par Boruta est légèrement différente de l'importance évaluée par le modèle lui-même)
dotPlot(varImp(borutaConfirmed_rf_default))
Extrayez le modèle final sélectionné et évaluez ses performances.
borutaConfirmed_rf_default_finalmodel <- borutaConfirmed_rf_default$finalModel
Tout d'abord, utilisez l'ensemble de données d'entraînement pour évaluer l'effet d'entraînement du modèle construit, RMSE=3.1
, Rsquared=0.944
, ce qui est assez bon.
# 获得模型结果评估参数
predictions_train <- predict(borutaConfirmed_rf_default_finalmodel, newdata=train_data)
postResample(pred = predictions_train, obs = train_data_group)
## RMSE Rsquared MAE
## 3.1028533 0.9440182 1.1891391
Utilisez les données de test pour évaluer l'effet prédictif du modèle, RMSE=6.2
, Rsquared=0.825
, ok. Faites un suivi avec d’autres méthodes pour voir si cela peut être amélioré.
predictions_train <- predict(borutaConfirmed_rf_default_finalmodel, newdata=test_data)
postResample(pred = predictions_train, obs = test_data_group)
## RMSE Rsquared MAE
## 6.2219834 0.8251457 2.7212806
library(ggplot2)
testfollowerDF <- data.frame(Real_Follower=test_data_group, Predicted_Follower=predictions_train)
sp_scatterplot(testfollowerDF, xvariable = "Real_Follower", yvariable = "Predicted_Follower",
smooth_method = "auto") + coord_fixed(1)
Inconvénients de la régression de forêt aléatoire
Les valeurs prédites par le modèle de régression forestière aléatoire ne dépasseront pas la plage de valeurs de la variable de réponse dans l'ensemble d'apprentissage et ne peuvent pas être utilisées pour l'extrapolation.
Les forêts aléatoires améliorées par régression (RERF) peuvent être utilisées comme solution.
Les références
https://medium.com/swlh/random-forest-and-its-implementation-71824ced454f
https://neptune.ai/blog/random-forest-regression-when-does-it-fail-and-why
https://levelup.gitconnected.com/random-forest-regression-209c0f354c84
https://rpubs.com/Isaac/caret_reg
Série de didacticiels sur l'apprentissage automatique
En partant des forêts aléatoires, comprenez les concepts et les pratiques des arbres de décision, des forêts aléatoires, du ROC/AUC, des ensembles de données et de la validation croisée, étape par étape.
Utilisez du texte pour les mots qui peuvent être expliqués clairement, utilisez des images pour l'affichage, des formules pour les descriptions peu claires et écrivez un code simple pour les formules peu claires afin de clarifier chaque lien et concept étape par étape.
Ensuite, pour faire évoluer l'application du code, le réglage du modèle, la comparaison de modèles, l'évaluation de modèles et acquérir les connaissances et les compétences nécessaires à l'ensemble de l'apprentissage automatique.
Une image pour ressentir divers algorithmes d'apprentissage automatique
Algorithme d'apprentissage automatique – Aperçu théorique de la forêt aléatoire
Algorithme d'apprentissage automatique - Une étude préliminaire de forêt aléatoire (1)
Apprentissage automatique – Manuel de forêt aléatoire, validation croisée en 10 volets
Indicateurs d'évaluation du modèle d'apprentissage automatique - Courbe ROC et valeur AUC
Apprentissage automatique - ensemble de formation, ensemble de validation, ensemble de tests
Une fonction unifie 238 packages R d'apprentissage automatique, ce qui est incroyable
Étapes générales pour l'analyse de forêt aléatoire basée sur les packages Caret et RandomForest (1)
4 façons d'ajuster de manière aléatoire les paramètres d'une forêt aléatoire en fonction du caret
Apprentissage automatique, partie 17 – Criblage des variables de fonctionnalités (1)
Apprentissage automatique, partie 18 – Criblage des variables des fonctionnalités de Boruta (2)
Envoyez-vous un site Web d'apprentissage automatique en ligne, si parfumé !
Plusieurs ensembles de données sur l’expression du cancer pour l’apprentissage automatique
Produits antérieurs (cliquez sur l'image pour accéder directement au texte du tutoriel correspondant)
Répondez en arrière-plan avec « La première vague d'avantages de la collection de lettres de vie » ou cliquez pour lire le texte original pour obtenir une collection de didacticiels.