创建朴素贝叶斯模型的示例

此示例显示如何定义离散化算法和分级数。

假定您要对客户流失率数据集应用朴素贝叶斯分类器。输入数据可以包含连续属性类型和名义属性类型。可以自动检测所有类型,也可以按用户指定的方法进行检测。要手动定义类型,请使用 incolumncoldeftype 参数。

客户流失率数据集仅包含数字列。但是,需要一个 VARCHAR 列来创建朴素贝叶斯模型。以下调用显示如何创建基于客户流失率数据集且包含 VARCHAR 列的视图。另外,此视图还包含预测所需的列。

CREATE VIEW CUSTOMER_CHURN AS SELECT (CASE WHEN SAMPLES.CUSTOMER_CHURN."CENSOR" = '1' THEN 'YES' ELSE 'NO' END) CHURN, IN_B2B_INDUSTRY, TOTAL_BUY, ANNUAL_REVENUE_MIL, CUST_ID AS ID from SAMPLES.CUSTOMER_CHURN;
朴素贝叶斯预测需要一个包含训练数据的表。以下调用显示如何根据 CUSTOMER_CHURN 视图创建这个表:
CALL IDAX.SPLIT_DATA('intable=customer_churn, traintable=customer_churn_training, testtable=customer_churn_testing, id=id, fraction=0.65');
以下示例显示如何定义离散化算法和分级数:
CALL IDAX.NAIVEBAYES('intable=customer_churn_training, disc=ew, bins=20, id=id, target=churn, model=cc_nb_ewd'); 

CALL IDAX.NAIVEBAYES('intable=customer_churn_training, disc=ef, bins=20, id=id, target=churn, model=cc_nb_efd'); 

CALL IDAX.NAIVEBAYES('intable=customer_churn_training, disc=ewn, id=id, target=churn, model=cc_nb_ewnd'); 

创建的模型由一个表来表示,对于每个“属性-值-类”组合,该表都包含相应一行,并包含以下各列:

attribute
属性
val
class
classvalcount
在训练集中,该类中出现相应属性的相应值的次数
classcount
在训练集中,该类的出现次数
attrclasscount
在训练集中,该类的非 null 出现次数
totalcount
训练集中所有实例的数目

使用这些参数足以计算可用于朴素贝叶斯预测的先验类概率和条件属性值概率。

要生成检验集预测,您可以使用生成的模型,如下所示:

CALL IDAX.PREDICT_NAIVEBAYES('model=cc_nb_ewd, intable=customer_churn_testing, outtable=customer_churn_nb_ewd, outtableprob = customer_churn_nb_ewd_prob'); 

CALL IDAX.PREDICT_NAIVEBAYES('model=cc_nb_efd, intable=customer_churn_testing, outtable=customer_churn_nb_efd, outtableprob = customer_churn_nb_efd_prob');

CALL IDAX.PREDICT_NAIVEBAYES('model=cc_nb_ewnd, intable=customer_churn_testing, outtable=customer_churn_nb_ewnd,outtableprob = customer_churn_nb_ewnd_prob');
注: 如果检验数据中预测过程的标识与训练数据中预测过程的标识完全相同,那么不必进行定义。

用于每一次模型应用的检验集都按相应训练集的区间进行离散化。指定的输出表包含生成的预测。它包含 id 列和 class 列。

另外,还会创建另一个输出表,并在名称中追加 _prob 后缀。对于每个实例和可能的类,这个输出表均包含一行,并包含以下各列:

id
实例标识
class
prob
实例类的贝叶斯分子

分子是根据类概率和条件实例属性值概率而生成。

lnprob
prob 的自然对数

您可以使用这些概率,以便更好地深入了解模型预测,或修改模型操作。可以通过正态化将贝叶斯分子转换为正则概率。正态化表示除以同一实例和所有类的分子之和。

以下查询显示针对第三个模型,将类概率添加到每个实例及其预测类标签的示例,该模型是使用最小熵离散化而生成:

SELECT S.id, S.class, S.prob/S.sump as prob
FROM (SELECT id, class, prob, sum(prob) OVER (PARTITION BY id) AS sump FROM customer_churn_nb_ewnd_prob) S, customer_churn_nb_ewnd P 
WHERE S.id=P.id AND S.class=P.class; 

要评估所获得的预测质量,可以计算误分类误差,如下所示:

CALL IDAX.CERROR('intable=customer_churn_nb_ewd, resulttable=customer_churn_testing, id=id, target=class, resulttarget=churn');

CALL IDAX.CERROR('intable=customer_churn_nb_efd, resulttable=customer_churn_testing, id=id, target=class, resulttarget=churn'); 

CALL IDAX.CERROR('intable=customer_churn_nb_ewnd, resulttable=customer_churn_testing, id=id, target=class, resulttarget=churn'); 

虽然这些模型的行为方式类似,但是第一个模型(基于等频离散化)不如另外两个模型准确。另外,误分类误差水平(对于所有模型均大于 0.37)得出一个结论,即朴素贝叶斯分类器不太适用于客户流失率数据集。

为避免预测期间完全无法获得概率,您可以启用 m 估算技术。

要启用此技术,请对 PREDICT_NAIVEBAYES 过程指定 mestimation=TRUE 参数,如下所示:

CALL IDAX.PREDICT_NAIVEBAYES('model=cc_nb_ewnd, intable=customer_churn_testing, mestimation=TRUE, outtable=customer_churn_nb_ewnd_mest'); 

CALL IDAX.CERROR('pred_table=customer_churn_nb_ewnd_mest, true_table=customer_churn_testing, pred_id=id, true_id=id, pred_column=class, true_column=churn'); 

分析显示此项技术对于针对 customer_churn 数据生成的预测质量影响不大。

要执行更深入的预测质量分析,您可以使用混淆矩阵和衍生的质量指标。对于第三个模型,请按如下所示继续操作:

CALL IDAX.CONFUSION_MATRIX('intable=customer_churn_testing, resulttable=customer_churn_nb_ewnd, id=id, target=churn, matrixTable=cc_churn_nb_ewnd_cm'); 

CALL IDAX.CMATRIX_STATS('matrixTable=cc_churn_nb_ewnd_cm'); 

结果可提供有关客户流失率数据的朴素贝叶斯预测质量的新线索。较高的误分类误差转变为接近 0.55 的较高假正率,但也转变为接近 0.77 的超高真正率,即,肯定客户流失率。

可以按类型和角色定义所有的列,如以下语句所示:

CALL IDAX.NAIVEBAYES('model=cc_nb1, intable=customer_churn_training, id=id, target=churn');

此语句等同于:

CALL IDAX.NAIVEBAYES('model=cc_nb2, intable=customer_churn_training, incolumn=id:id, target=churn');

要手动定义名义属性和连续属性,可以使用 nom 类型和 cont 类型:

CALL IDAX.NAIVEBAYES('model=cc_nb3, intable=customer_churn_training,incolumn=IN_B2B_INDUSTRY:nom;TOTAL_BUY:cont;CHURN:target;ID:id');

另外,还可以创建单列属性定义,并多次将其传递给模型:

CALL IDAX.COLUMN_PROPERTIES('intable=customer_churn_training, outtable=cc_columns, coldeftype=cont, incolumn=IN_B2B_INDUSTRY:nom;TOTAL_BUY:cont;ANNUAL_REVENUE_MIL:cont:ignore;CHURN:nom:target;ID:id');

select * from cc_columns;

CALL IDAX.NAIVEBAYES('model=cc_nb4, intable=customer_churn_training,colPropertiesTable=cc_columns');