SVM算法实现光学字符识别

简介: SVM算法实现光学字符识别

目录

1、数据来源


2、数据预处理


3、模型训练


4、模型性能评估


5、模型性能提升


5.1、核函数的选取


5.2、惩罚参数C的选取


OCR (Optical Character Recognition,光学字符识别)是指电子设备(例如扫描仪或数码相机)检查纸上打印的字符,通过检测暗、亮的模式确定其形状,然后用字符识别方法将形状翻译成计算机字符的过程;即,针对印刷体字符,采用光学的方式将纸质文档中的文字转换成为黑白点阵的图像文件,并通过字符识别模型将图像中的文字处理成文本格式。


光学字符识别是OCR的核心,然而对于许多类型的机器学习算法来说,这种图像处理都是一项艰巨的任务。 将像素模式连接到更高概念的关系是极其复杂的,而且很难定义。 例如,让一个人识别一张面孔、一只猫或字母A是容易的,但用严格的规则来定义这些模式是很困难的。 此外,图像数据往往是噪声数据,对于光学字符图像,灯光、定位和对象的位置都能影响最终的图像数据。


支持向量机非常适合处理图像数据,它能够学习复杂的图案而不需要对噪声数据过度敏感,能够以较高的准确度识别光学图案。


1、数据来源

本博文中,将使用UCI公开的光学字符识别数据集(http://archive.ics.uci.edu/ml/datasets/Letter+Recognition),利用支持向量机(SVM)来构建光学字符识别模型。


该数据集包含了26个英文大写字母的20000个样本。 每一个样本代表光学图像中的一个矩形区域,该区域只包含单一字符。 每一个样本包含16个自变量和letter目标变量,letter指示当前样本是哪一个字母。每一个特征变量的具体含义如下:


letter 字符 (取值为A,B,...,Z)

x-box 字符所在矩形区域的水平位置

y-box 字符所在矩形区域的竖直位置

width 矩形区域的宽度

high 矩形区域的高度

onpix 矩阵区域的黑色像素数

x-bar 矩形区域内黑色像素的平均x值

y-bar 矩形区域内黑色像素的平均y值

x2bar x平均方差

y2bar y平均方差

xybar x和y的平均相关性

x2ybr x * x * y 均值

xy2br x * y * y 均值

x-ege 从左到右的边缘数目

xegvy x边缘与y的相关性

y-ege 从下到上的边缘数目

yegvx y边缘与x的相关性

2、数据预处理

光学字符识别数据集中包含16个特征变量,这些变量用字符矩形区域的水平位置和竖直位置、黑色像素比例、黑色像素的平均水平和竖直位置来度量一个字符。


首先,使用pandas中的read_csv()函数将数据导入,实现代码如下所示:


import pandas as pd
letters = pd.read_csv("./input/letterecognition.csv")
letters.head(10)

前10行数据格式如下所示:

image.png



接下来使用pandas中Series的value_counts()函数,观察数据集中每一种字符的数量分布。


sort_index()函数可以让结果按照字母排序展示结果,实现代码如下所示:


letters["letter"].value_counts().sort_index()

效果如下所示:

image.png



可见,各个字符的样本数量分布相对均衡。


现在,进一步观察每一个自变量的取值分布,实现代码如下所示:


letters.iloc[:,1:].describe()

数据取值分布如下所示:


 xbox ybox width height onpix xbar ybar x2bar y2bar xybar x2ybar xy2bar xedge xedgey yedge yedgex

count 20000.000000 20000.000000 20000.000000 20000.00000 20000.000000 20000.000000 20000.000000 20000.000000 20000.000000 20000.000000 20000.00000 20000.000000 20000.000000 20000.000000 20000.000000 20000.00000

mean 4.023550 7.035500 5.121850 5.37245 3.505850 6.897600 7.500450 4.628600 5.178650 8.282050 6.45400 7.929000 3.046100 8.338850 3.691750 7.80120

std 1.913212 3.304555 2.014573 2.26139 2.190458 2.026035 2.325354 2.699968 2.380823 2.488475 2.63107 2.080619 2.332541 1.546722 2.567073 1.61747

min 0.000000 0.000000 0.000000 0.00000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.00000 0.000000 0.000000 0.000000 0.000000 0.00000

25% 3.000000 5.000000 4.000000 4.00000 2.000000 6.000000 6.000000 3.000000 4.000000 7.000000 5.00000 7.000000 1.000000 8.000000 2.000000 7.00000

50% 4.000000 7.000000 5.000000 6.00000 3.000000 7.000000 7.000000 4.000000 5.000000 8.000000 6.00000 8.000000 3.000000 8.000000 3.000000 8.00000

75% 5.000000 9.000000 6.000000 7.00000 5.000000 8.000000 9.000000 6.000000 7.000000 10.000000 8.00000 9.000000 4.000000 9.000000 5.000000 9.00000

max 15.000000 15.000000 15.000000 15.00000 15.000000 15.000000 15.000000 15.000000 15.000000 15.000000 15.00000 15.000000 15.000000 15.000000 15.000000 15.00000

观察发现16个自变量的取值范围都在0~15之间,因此对于该数据集不需要对变量进行标准化操作。


此外,数据集作者已经将样本随机排列,所以也不需要我们对数据进行随机打散。 此处,直接取前14000个样本(70%)作为训练集,后6000个样本(30%)作为测试集,实现代码如下所示:


letters_train = letters.iloc[0:14000,]
letters_test = letters.iloc[14000:20000,]

3、模型训练

接下来使用sklearn.svm包中的相关类来实现来构建基于支持向量机的光学字符识别模型。


在sklearn.svm包中,有三个类均实现了支持向量机算法:SVC, NuSVC 和 LinearSVC。 SVC 和 NuSVC接受的参数有细微差别,且底层的数学形式不一样。 而 LinearSVC 则是使用简单的线性核函数,其实现基于liblinear (https://www.csie.ntu.edu.tw/~cjlin/liblinear/), 对于大规模的样本训练速度会更快。 这三个支持向量机的具体介绍参考sklearn官方文档:http://scikit-learn.org/stable/modules/svm.html


本案例中,选用 SVC 来进行模型构建。 SVC 有两个主要的参数可以设置:核函数参数 kernel 和约束惩罚参数C。 核函数参数 kernel的常用取值及其对应含义如下:


"linear":线性核函数

"poly":多项式核函数

"rbf":径向基核函数

"sigmoid": sigmoid核函数

约束惩罚参数C为对超过约束条件的样本的惩罚项。C值越大,惩罚越大,支持向量机的决策边界越窄。


现在,可以使用训练集构建分类模型了,选用最简单的线性核函数,C采用默认值1。实现代码如下所示:


from sklearn.svm import SVC
letter_recognition_model = SVC(C = 1, kernel = "linear")
letter_recognition_model.fit(letters_train.iloc[:,1:],letters_train['letter'])

设置成功后,SVC配置参数效果如下所示:


SVC(C=1, cache_size=200, class_weight=None, coef0=0.0,
  decision_function_shape=None, degree=3, gamma='auto', kernel='linear',
  max_iter=-1, probability=False, random_state=None, shrinking=True,
  tol=0.001, verbose=False)

4、模型性能评估

接下来,使用predict()函数得到上一节训练的支持向量机模型在测试集合上的预测结果,然后使用 sklearn.metrics中的相关函数对模型的性能进行评估,实现代码如下所示:


from sklearn import metrics
letters_pred = letter_recognition_model.predict(letters_test.iloc[:,1:])
print(metrics.classification_report(lettters_test["letter"], letters_pred))
print(pd.DataFrame(metrics.confusion_matrix(lettters_test["letter"], letters_pred),\
                  columns = letters["letter"].value_counts().sort_index().index,\
                  index = letters["letter"].value_counts().sort_index().index))

效果如下所示:


         

precision    recall  f1-score   support
          A       0.92      0.92      0.92       245
          B       0.78      0.87      0.82       207
          C       0.82      0.84      0.83       202
          D       0.77      0.91      0.83       251
          E       0.80      0.86      0.83       230
          F       0.77      0.89      0.82       240
          G       0.73      0.75      0.74       235
          H       0.65      0.70      0.67       210
          I       0.89      0.86      0.87       243
          J       0.83      0.88      0.86       216
          K       0.79      0.84      0.81       214
          L       0.95      0.86      0.90       250
          M       0.89      0.94      0.92       224
          N       0.95      0.88      0.91       246
          O       0.87      0.71      0.78       216
          P       0.92      0.80      0.86       246
          Q       0.85      0.75      0.80       252
          R       0.81      0.84      0.82       242
          S       0.75      0.67      0.71       240
          T       0.89      0.90      0.90       226
          U       0.91      0.92      0.92       248
          V       0.91      0.91      0.91       212
          W       0.90      0.92      0.91       216
          X       0.89      0.84      0.86       230
          Y       0.93      0.88      0.90       223
          Z       0.86      0.83      0.84       236
avg / total       0.85      0.84      0.84      6000
     A    B    C    D    E    F    G    H    I    J ...     Q    R    S    T  \
A  225    1    0    2    0    0    2    0    0    1 ...     0    2    1    0   
B    0  181    0    4    1    0    1    2    1    1 ...     0   10    4    0   
C    1    0  169    0    8    0    7    0    0    0 ...     0    0    0    0   
D    1    9    0  228    0    1    1    2    0    1 ...     0    0    0    0   
E    0    2    5    0  197    2   11    0    0    0 ...     1    1    1    5   
F    0    1    3    1    3  213    1    2    2    3 ...     0    0    0    4   
G    0    2   14    2    1    4  177    2    0    0 ...     9    3    5    0   
H    1    4    2   12    0    5    4  147    0    1 ...     3    9    0    1   
I    0    1    2    4    0    7    0    0  208   12 ...     0    0    2    0   
J    2    0    0    2    0    2    0    3   11  190 ...     0    0    2    0   
K    0    0    2    5    4    0    1    5    0    0 ...     0   12    0    0   
L    0    0    5    5    6    0    3    2    0    0 ...     4    1    3    1   
M    1    3    0    0    0    0    0    3    0    0 ...     0    2    0    0   
N    1    0    0    7    0    0    0   10    0    0 ...     0    2    0    0   
O    3    0    3    7    0    0    2   26    0    1 ...     5    1    0    0   
P    0    2    0    3    0   25    5    0    1    1 ...     1    1    0    0   
Q    5    5    0    1    7    1   14    3    0    4 ...   190    1   13    0   
R    0   11    0    4    0    0    2    6    0    0 ...     0  203    0    0   
S    1    8    0    1   10    7    7    0    4    1 ...     9    1  160    3   
T    1    0    0    0    0    3    2    5    0    0 ...     0    1    2  204   
U    1    0    0    1    0    0    0    1    0    0 ...     0    0    0    1   
V    0    2    0    0    0    2    0    4    0    0 ...     0    1    0    0   
W    1    0    0    0    0    0    0    0    0    0 ...     0    0    0    0   
X    0    1    0    5    5    1    1    0    6    3 ...     0    0    2    2   
Y    0    0    0    3    0    4    0    3    1    0 ...     2    0    0    5   
Z    1    0    0    1    4    1    0    0    1    9 ...     0    0   18    3   
     U    V    W    X    Y    Z  
A    2    0    0    0    3    3  
B    0    0    0    1    0    0  
C    4    0    0    0    0    0  
D    3    0    0    0    0    0  
E    0    0    0    2    0    2  
F    0    0    0    0    1    0  
G    0    6    1    0    0    0  
H    2    3    0    2    0    0  
I    0    0    0    4    0    3  
J    0    0    0    0    0    2  
K    2    0    0    4    0    0  
L    0    0    0    6    0    0  
M    1    0    4    0    0    0  
N    1    2    0    0    0    0  
O    3    1    4    1    0    0  
P    1    0    0    0    5    0  
Q    0    1    0    0    0    0  
R    0    1    0    1    0    0  
S    0    0    0    2    1   20  
T    0    0    0    0    3    3  
U  228    0    6    0    0    0  
V    0  193    6    0    1    0  
W    2    2  199    0    0    0  
X    1    0    0  193    1    0  
Y    0    4    1    1  196    0  
Z    0    0    0    1    0  196  
[26 rows x 26 columns]

上述混淆矩阵中对角线的元素表示模型正确预测数,对角元素之和表示模型整体预测正确的样本数。


而非对角线元素上的值则可以反映模型在哪些类的预测上容易犯错,例如第P行第F列的取值为25,说明模型有25次将“P”字符错误地识别为“F”字符。直观来看,“P”和“F”相似度比较高,对它们的区分也更具有挑战性。 现在,来通过这个来计算模型在测试集中的预测正确率。代码如下所示:


agreement = lettters_test["letter"] == letters_pred
print(agreement.value_counts())
print("Accuracy:", metrics.accuracy_score(lettters_test["letter"], letters_pred))

预测正确率,效果如下所示:


True     5068
False     932
dtype: int64
Accuracy: 0.844666666667

可见,初步模型在6000个测试样本中,正确预测5068个,整体正确率(Accuaray)为84.47%。


5、模型性能提升

对于支持向量机,有两个主要的参数能够影响模型的性能:一是核函数的选取,二是惩罚参数C的选择。 下面,期望通过分别尝试这两个参数来进一步改善模型的预测性能。


5.1、核函数的选取

在 SVC 中,核函数参数kernel可选值为"rbf"(径向基核函数)、“poly”(多项式核函数)、"sigmoid"(sigmoid核函数)和"linear"(线性核函数)。我们的初始模型选取的是线性核函数,下面我们观察在其他三种核函数下模型正确率的改变。实现代码如下所示:


kernels = ["rbf","poly","sigmoid"]
for kernel in kernels:
    letters_model = SVC(C = 1, kernel = kernel)
    letters_model.fit(letters_train.iloc[:,1:],letters_train['letter'])
    letters_pred = letters_model.predict(letters_test.iloc[:,1:])
    print("kernel = ", kernel , ", Accuracy:",\
    metrics.accuracy_score(lettters_test["letter"], letters_pred))

效果如下所示:


kernel =  rbf , Accuracy: 0.971166666667
kernel =  poly , Accuracy: 0.943166666667
kernel =  sigmoid , Accuracy: 0.0376666666667

从结果可以看到,当选取RBF核函数时:


模型正确率由84.47%提高到97.12%

多项式核函数下模型正确率为94.32%

sigmoid核函数下模型的正确率只有3.77%

5.2、惩罚参数C的选取

我们将分别测试 𝐶=0.01,0.1,1,10,100C=0.01,0.1,1,10,100时字符识别模型正确率的变化。


核函数选取径向基核函数(即"rbf"),实现代码如下所示:


c_list = [0.01, 0.1, 1, 10, 100]
for C in c_list:
    letters_model = SVC(C = C, kernel = "rbf")
    letters_model.fit(letters_train.iloc[:,1:],letters_train['letter'])
    letters_pred = letters_model.predict(letters_test.iloc[:,1:])
    print("C = ", C , ", Accuracy:",\
    metrics.accuracy_score(lettters_test["letter"], letters_pred))

效果如下所示:


C =  0.01 , Accuracy: 0.059
C =  0.1 , Accuracy: 0.886333333333
C =  1 , Accuracy: 0.971166666667
C =  10 , Accuracy: 0.976166666667
C =  100 , Accuracy: 0.976333333333

可见,当惩罚参数C设置为10和100时,模型正确率进一步提升,分别达到97.62%和97.63%。


相关文章
|
1月前
|
机器学习/深度学习 算法 数据库
KNN和SVM实现对LFW人像图像数据集的分类应用
KNN和SVM实现对LFW人像图像数据集的分类应用
34 0
|
4月前
|
机器学习/深度学习 算法 Python
Python高级算法——支持向量机(Support Vector Machine,SVM)
Python高级算法——支持向量机(Support Vector Machine,SVM)
92 2
|
7月前
|
机器学习/深度学习 算法 测试技术
机器学习SVM算法数字识别器
机器学习SVM算法数字识别器
104 0
|
7月前
|
机器学习/深度学习 算法 API
机器学习SVM算法入门
机器学习SVM算法入门
60 0
|
5月前
|
机器学习/深度学习 算法
基于相空间重构的混沌背景下微弱信号检测算法matlab仿真,对比SVM,PSO-SVM以及GA-PSO-SVM
基于相空间重构的混沌背景下微弱信号检测算法matlab仿真,对比SVM,PSO-SVM以及GA-PSO-SVM
|
1月前
|
机器学习/深度学习 人工智能 算法
探索机器学习中的支持向量机(SVM)算法
【2月更文挑战第20天】 在数据科学与人工智能的领域中,支持向量机(SVM)是一种强大的监督学习算法,它基于统计学习理论中的VC维理论和结构风险最小化原理。本文将深入探讨SVM的核心概念、工作原理以及实际应用案例。我们将透过算法的数学原理,揭示如何利用SVM进行有效的数据分类与回归分析,并讨论其在处理非线性问题时的优势。通过本文,读者将对SVM有更深层次的理解,并能够在实践中应用这一算法解决复杂的数据问题。
19 0
|
1月前
|
机器学习/深度学习 数据采集 算法
Python基础算法解析:支持向量机(SVM)
Python基础算法解析:支持向量机(SVM)
35 0
Python基础算法解析:支持向量机(SVM)
|
1月前
|
机器学习/深度学习 数据采集 运维
高效处理异常值的算法:One-class SVM模型的自动化方案
高效处理异常值的算法:One-class SVM模型的自动化方案
34 1
|
7月前
|
机器学习/深度学习 移动开发 算法
机器学习SVM算法原理
机器学习SVM算法原理
74 0
|
7月前
|
机器学习/深度学习 数据采集 自然语言处理
基于机器学习的情绪识别算法matlab仿真,对比SVM,LDA以及决策树
基于机器学习的情绪识别算法matlab仿真,对比SVM,LDA以及决策树

热门文章

最新文章