手写识别KNN(java)

本文介绍了如何使用KNN算法进行手写识别,详细阐述了欧氏距离和余弦距离的概念,以及在数据存储、KNN计算过程中的实现细节。通过IO流处理图像数据,实现了学习样本和识别样本的存储。尽管1.0版本存在每次识别前需录入新样本的问题,但展示了手写识别的基本流程和技巧。
摘要由CSDN通过智能技术生成

起初以为手写识别仅与机器学习有关,做了这个才知道有KNN算法。

KNN:

概念摘自百度

邻近算法,或者说K最近邻(kNN,k-NearestNeighbor)分类算法是数据挖掘分类技术中最简单的方法之一。所谓K最近邻,就是k个最近的邻居的意思,说的是每个样本都可以用它最接近的k个邻居来代表。

kNN算法的核心思想是如果一个样本在特征空间中的k个最相邻的样本中的大多数属于某一个类别,则该样本也属于这个类别,并具有这个类别上样本的特性。该方法在确定分类决策上只依据最邻近的一个或者几个样本的类别来决定待分样本所属的类别。 kNN方法在类别决策时,只与极少量的相邻样本有关。由于kNN方法主要靠周围有限的邻近的样本,而不是靠判别类域的方法来确定所属类别的,因此对于类域的交叉或重叠较多的待分样本集来说,kNN方法较其他方法更为适合。

 

为了判断距离最近,引入欧氏距离余弦距离。(可以自己再查查)

欧氏距离:

将两点之间距离公式拓展到N维,即抽象出来两物体距离为两点间距离公式的延展....emmm公式打不出来了

余弦距离

个人觉得余弦距离与其说是距离不如理解为趋势,余弦距离是空间两个向量夹角的余弦值来作为比较依据。

IO流

按操作数据类型分为字符流和字节流

按流分为输入流和输出流

字符流处理文本数据,字节流处理媒体数据

FileInputStream  FileOutputStream  纯文本输入输出最为方便,这里的输入输出参考于程序

流使用后一定关闭

思路

1.数据存储

数据存储分两类:“学习”样本数据的存储,识别样本的存储;

在我点击“学习”按钮后,在界面画数字“1”,它会被截图保存,然后转为灰度,保存在二维数组中,输出到文本文档。

在我点击“识别”按钮后,在界面画数字“1”,它会被截图保存,然后转为灰度,保存在二维数组中,输出到文本文档。

2.knn,计算欧氏距离

我们需要从学习文档中得到所有的数组数据,在与得到的一组测试数据比较,欧氏距离最小的极为同类。输出就好

源代码(1.0版本,它的问题是每次识别前都要录入新的样本)



import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import java.awt.AWTException;

import java.awt.Rectangle;

import java.awt.Robot;

import java.awt.image.BufferedImage;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

import javax.imageio.ImageIO;
public class DrawFrame extends JFrame{

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		DrawFrame h=new DrawFrame();
		h.show();
		
		
	}

	public void show(){
		JFrame jf=new JFrame();
		jf.setTitle("手写识别");
		jf.setSize(400,400);
		jf.getContentPane().setBackground(Color.white);
		//jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		jf.setDefaultCloseOperation(3);
  • 3
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,我可以为您提供一些关于手写数字识别KNN算法的代码实现。 K近邻算法(KNN)是一种基本的机器学习算法,它可以用于分类和回归问题。在数字识别中,KNN可以用于分类问题。以下是实现手写数字识别KNN算法的C++代码示例: 1. 定义一个结构体来表示样本数据。 ```c++ struct Sample { int label; // 标签 vector<int> features; // 特征向量 }; ``` 2. 定义一个函数来计算两个样本之间的距离。 ```c++ double distance(const Sample& a, const Sample& b) { double dist = 0; for (int i = 0; i < a.features.size(); i++) { dist += (a.features[i] - b.features[i]) * (a.features[i] - b.features[i]); } return sqrt(dist); } ``` 3. 定义一个函数来预测测试样本的标签。 ```c++ int predict(const vector<Sample>& train, const Sample& test, int k) { vector<pair<double, int>> distances; // 存储距离和标签 for (const auto& sample : train) { double dist = distance(sample, test); distances.emplace_back(dist, sample.label); } sort(distances.begin(), distances.end()); // 按照距离从小到大排序 unordered_map<int, int> count; // 存储标签和出现次数 for (int i = 0; i < k; i++) { count[distances[i].second]++; } int max_count = 0; int pred_label = -1; for (const auto& p : count) { if (p.second > max_count) { max_count = p.second; pred_label = p.first; } } return pred_label; } ``` 4. 加载训练数据和测试数据,并进行预测。 ```c++ int main() { // 加载训练数据 vector<Sample> train; ifstream train_file("train.txt"); string line; while (getline(train_file, line)) { stringstream ss(line); Sample sample; ss >> sample.label; int feature; while (ss >> feature) { sample.features.push_back(feature); } train.push_back(sample); } // 加载测试数据 vector<Sample> test; ifstream test_file("test.txt"); while (getline(test_file, line)) { stringstream ss(line); Sample sample; ss >> sample.label; int feature; while (ss >> feature) { sample.features.push_back(feature); } test.push_back(sample); } // 预测测试数据 int k = 5; // K值 int correct_count = 0; for (const auto& sample : test) { int pred_label = predict(train, sample, k); if (pred_label == sample.label) { correct_count++; } } cout << "Accuracy: " << (double)correct_count / test.size() << endl; return 0; } ``` 以上就是一个简单的手写数字识别KNN算法的C++实现。需要注意的是,KNN算法的效果很大程度上依赖于选择的特征和K值的大小。希望能对您有所帮助!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值