matlab实现数字识别

任务简介

给了70000个数字,60000个训练样本,10000个测试样本,完成对数字0~9的识别。使用matlab实现。

特征提取

  1. 使用田字划分分辨率来进行特征提取,代码:
function feature=Get_Feature(A,n,m)
%依照分辨率n*m,则矩阵A维数为m*n
A=im2bw(A,0.5);
a1=A(1:floor(m/2),1:floor(n/2));
a2=A(1:floor(m/2),floor(n/2)+1:n);
a3=A(floor(m/2)+1:m,1:floor(n/2));
a4=A(floor(m/2)+1:m,floor(n/2)+1:n);

f1=nnz(a1);
f2=nnz(a2);
f3=nnz(a3);
f4=nnz(a4);

feature=[f1 f2 f3 f4]';

此处注意分辨率的维数表示和矩阵是反的。
2. 把所有的像素点都作为一列向量特征

function feature=Get_Feature2(A,n,m)
%依照分辨率n*m,则矩阵A维数为m*n
A=im2bw(A,0.5);
array=A(:);
feature=array;

KNN法

  1. 采用田字特征提取
    主函数:
clc
clear all
close all
%% 获取训练样本
Path = 'C:\杂七杂八杂货铺\模式识别\数字识别\手写体数字70000\';
path_train=strcat([Path,'训练图像\']);%训练样本文件夹的路径
file_struct=dir([path_train,'*.bmp']);%列出当前目录下符合'.bmp'的文件并放在文件结构体中
n_train=length(file_struct);%获取训练样本个数
for j=1:n_train
        sample=imread([path_train,file_struct(j).name]);%打开第j个训练样本
        X_train(:,j)=Get_Feature2(sample,28,28);%获取该样本特征,图片分辨率为20*20
        class_train(j)=file_struct(j).name(1);%获取该训练样本的类别,为字符型 
      
end
class_train=str2num(class_train(:))';%将字符型转化为数组
%% 获取测试样本
path_test=strcat([Path,'测试图像\']);%测试样本文件夹的路径
file_struct=dir([path_test,'*.bmp']);%列出当前目录下符合'.bmp'的文件并放在文件结构体中
n_test=length(file_struct);%获取测试样本个数
for j=1:n_test
        sample=imread([path_test,file_struct(j).name]);%打开第j个训练样本
        X_test(:,j)=Get_Feature2(sample,28,28);%获取该样本特征,图片分辨率为28*28
        class_test(j)=file_struct(j).name(1);%获取该测试样本的类别
       
end
class_test=str2num(class_test(:))';%将字符型转化为数组
%% KNN法
for K=1:2:9
[topK,class_judge]=knn(X_train,X_test,class_train,class_test,K);
%校验错误率
error=class_judge-class_test;
ro(K)=(nnz(error)/n_test)*100;%计算错误率
disp(strcat('K=',num2str(K),'时,错误率为',num2str(ro(K)),'%'));
end

子函数:Get_Feature()和Get_Feature2()见上特征提取
knn:

function [topK,class_judge]=knn(X_train,X_test,class_train,class_test,K)
%X_train为训练样本,test为测试样本
%class_train为每个训练样本对应的类别,class_test为每个测试样本对应的类别
n_train=size(X_train,2);
n_test=size(X_test,2);
for i=1:n_test
    X_test_mat=repmat(X_test(:,i),1,n_train);%将测试集扩展至训练集维度
    Z=(X_test_mat-X_train).^2;
    d=sum(Z,1);%计算空间距离
    [list,temp_index]=sort(d);%对空间距离排序并取标号
    topK=temp_index(1:K);%前K个近邻点的标号
    for a=1:K
        class_topK(a)=class_train(topK(a));%前K个近邻点的类别
    end
    array=tabulate(class_topK);%计算前K个近邻点各类别出现的频数等
    [~,xuhao]=max(array(:,2));%找出最大频数和频数对应的序号
    class_judge(i)=array(xuhao,1);%依照最大频数序号去找类别,确定该测试集的类别
end
end

在KNN法中,田字特征提取识别率(50%~60%)远低于所有特征的识别率(95%~96%),但是采集所有特征之后在进行KNN运算时,需要消耗大量的计算时间。

神经网络工具箱

clc
clear all
close all
%% 获取训练样本
Path = 'C:\杂七杂八杂货铺\模式识别\数字识别\手写体数字70000\';
path_train=strcat([Path,'训练图像\']);%训练样本文件夹的路径
file_struct=dir([path_train,'*.bmp']);%列出当前目录下符合'.bmp'的文件并放在文件结构体中
n_train=length(file_struct);%获取训练样本个数
for j=1:n_train
        sample=imread([path_train,file_struct(j).name]);%打开第j个训练样本
        X_train(:,j)=Get_Feature2(sample,28,28);%获取该样本特征,图片分辨率为20*20
        class_train(j)=file_struct(j).name(1);%获取该训练样本的类别,为字符型 
      
end
class_train=str2num(class_train(:))';%将字符型转化为数组
%% 获取测试样本
path_test=strcat([Path,'测试图像\']);%测试样本文件夹的路径
file_struct=dir([path_test,'*.bmp']);%列出当前目录下符合'.bmp'的文件并放在文件结构体中
n_test=length(file_struct);%获取测试样本个数
for j=1:n_test
        sample=imread([path_test,file_struct(j).name]);%打开第j个训练样本
        X_test(:,j)=Get_Feature2(sample,28,28);%获取该样本特征,图片分辨率为28*28
        class_test(j)=file_struct(j).name(1);%获取该测试样本的类别
       
end
class_test=str2num(class_test(:))';%将字符型转化为数组

%% 将类别按照概率表示,训练样本类别变成10*60000
for i=1:n_train
    switch class_train(:,i)
        case 0
            class(:,i)=[1 0 0 0 0 0 0 0 0 0]';
        case 1
            class(:,i)=[0 1 0 0 0 0 0 0 0 0]';
        case 2
            class(:,i)=[0 0 1 0 0 0 0 0 0 0]';
        case 3
            class(:,i)=[0 0 0 1 0 0 0 0 0 0]';
        case 4
            class(:,i)=[0 0 0 0 1 0 0 0 0 0]';
        case 5
            class(:,i)=[0 0 0 0 0 1 0 0 0 0]';
        case 6
            class(:,i)=[0 0 0 0 0 0 1 0 0 0]';
        case 7
            class(:,i)=[0 0 0 0 0 0 0 1 0 0]';
        case 8
            class(:,i)=[0 0 0 0 0 0 0 0 1 0]';
        case 9
            class(:,i)=[0 0 0 0 0 0 0 0 0 1]';
    end
end

%% 测试
class_judge_temp=sim(net1,X_test);
for i=1:n_test
    [~,index]=max(class_judge_temp(:,i));
    class_judge(i)=index-1;
end
error=class_judge-class_test;
ro=(nnz(error)/n_test)*100;
disp(strcat('错误率为',num2str(ro),'%'));

在测试的代码前,需要手动点击神经网络的拟合工具箱,由于数字识别不涉及深度学习,所以使用工具箱完成操作(PS:好像工具箱可改的参数并不多,只能用一个隐含层,只能修改隐含层个数,好在默认值也能拟合的很好),这里设置了128个隐含层神经元,10个输出层神经元,准确率大概能达到94%左右,用时相对较短。

  • 6
    点赞
  • 127
    收藏
    觉得还不错? 一键收藏
  • 17
    评论
评论 17
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值