数据挖掘入门系列教程(二)之分类问题OneR算法


GitHub

在上一篇中,我们通过分析亲和性来寻找数据集中数据与数据之间的相关关系。这篇博客我们会讨论简单的分类问题。

https://www.saedsayad.com/oner.htm,在里面最后识别的结果只有yes和no。

具体的训练步骤是怎么样的呢?

首先我们假设有x,y,z三个特征,每个特征的特征值为0和1,同时有A,B两个类。因此我们可以得到下面的统计。

对于每一个特征值,统计它在各个类别中的出现次数:


既然我们得到了统计,这时候,我们就开始来计算错误率。首先我们找到某个特征值(如 $X = 0$)出现次数最多的类别。在下图中,被框框圈住的部分就是出现次数最多的特征值(如果有三个类别,任然是选择次数最多的类别)。


再然后我们就是计算出每一个特征的错误率了,下面以$X$为例


同理,我们可以得到$Y$,$Z$的错误错误率,然后选择最小的错误率作为分类标准即可。

说了这么多,现在来写代码了。

下面是train_feature函数,目的是得到指定特征特征值得到错误率最小的类别。也就是上面图中的$b_{x0},a_{x1}$等等。


from collections import defaultdict
from operator import itemgetter

def train_feature(data_train,target_train,index,value):
    """
        data_train:训练集特征
        target_train:训练集类别
        index:特征值的索引
        value :特征值
    """
    count = defaultdict(int)
    for sample,class_name in zip(data_train,target_train):
        if(sample[index] ==value):
            count[class_name] += 1
            
   	# 进行排序
    sort_class = sorted(count.items(),key=itemgetter(1),reverse = True)
    # 拥有该特征最多的类别
    max_class = sort_class[0][0]
    max_num = sort_class[0][1]
    all_num = 0
    
    for class_name,class_num in sort_class:
        all_num += class_num
#     print("{}特征,值为{},错误数量为{}".format(index,value,all_num-max_num))
    # 错误率
    error = 1 - (max_num / all_num)
    return max_class,error

在train函数中,我们对所有的特征和特征值进行计算,得到最小的特征错误率。


def train():
    errors = defaultdict(int)
    class_names = defaultdict(list)
    # 遍历特征
    for i in range(data_train.shape[1]):
       # 遍历特征值 
        for j in range(0,2):
            class_name,error = train_feature(data_train,target_train,i,j)
            errors[i] += error
            class_names[i].append(class_name)            
    return errors,class_names

errors,class_names = train()
# 进行排序
sort_errors = sorted(errors.items(),key=itemgetter(1))
best_error = sort_errors[0]
# 得到最小错误率对应的特征
best_feature = best_error[0]
# 当特征值取 0 ,1对应的类别。
best_class = class_names[best_feature]
print("最好的特征是{}".format(best_error[0]))
print(best_class)

训练完成后,我们就可以进行predict了。predict就是那测试集中数据进行测试,使用自己的模型进行预测,在与正确的作比较得到准确度。看下图predict的流程:


下面是预测代码以及准确度检测代码:

# 进行预测
def predict(data_test,feature,best_class):
    return np.array([best_class[int(data[feature])] for data in data_test])

result_predict = predict(data_predict,best_feature,best_class)

print("预测准确度{}".format(np.mean(result_predict == target_predict) * 100))
print("预测结果{}".format(result_predict))
GitHub

参考书籍:Python数据挖掘入门与实践

感谢蒋少华老师为我解惑。