概述

CP/M-80(兼容)神经网络手写字符识别LSX-道奇队和 MSX-DOS)。
Z-80 是 1976 年开发的 8 位 CPU,可以识别 28 x 28 像素的数字 (0-9) 的类型。

(2022-10-05 在 MZ-700 上添加了执行示例)

执行方式

具有训练有素的网络和样本数据的 GitHub磁盘映像对公众开放,因此您可以轻松地将其与 X1 仿真器或 MSX 仿真器一起使用。关于使用 X1 模拟器和 LSX-Dosgers 时的环境构建设置 X1 模拟器环境请参阅

磁盘镜像中的MNIST.COM是可执行文件,MNMODEL.BIN是MNIST是在数据集上训练的网络的权重数据。
MNMODEL.BIN 必须放在当前驱动器中(可以使用分层目录的操作系统上的当前目录)。

MNIST.COM [画像ファイル名]

图像文件格式

它是一个 28×28 像素的 256 级灰度图像,是一个 784 字节的未压缩、无标题的二进制文件。具体来说,格式如下。

[ピクセルの階調 1byte][ピクセルの階調 1byte]...[ピクセルの階調 1byte] ← 1ライン目 28byte
[ピクセルの階調 1byte][ピクセルの階調 1byte]...[ピクセルの階調 1byte] ← 2ライン目 28byte
     ・
     ・
     ・
[ピクセルの階調 1byte][ピクセルの階調 1byte]...[ピクセルの階調 1byte] ← 28ライン目 28byte

使用 model_training/make_mnist_beta.rb 从 MNIST 数据集(train-images-idx3-ubyte 和 train-labels-idx1-ubyte)中提取二进制格式的图像。

图像文件查看器

包括一个用于 LSX-Dodgers 的程序(由于直接访问工作区,仅限于 1.40 版),它以上一节中描述的格式抖动和显示图像文件。 2个像素有16个渐变,用8x4点表示,但是将2个像素组合的8x8点定义为PCG,用14行文字显示28行图像。

SETPCG.COM DITHER.PCG
MNVIEW.COM IMG_0_5.BIN

SETPCG.COM的来源是https://github.com/meister68k/setpcg_X1

执行示例

CP/M-80のニューラルネットワークで手書き文字認識
目标图像预览。

CP/M-80のニューラルネットワークで手書き文字認識
在执行第一层(卷积层)期间。让我们在这里花点时间。

CP/M-80のニューラルネットワークで手書き文字認識
第一层的输出结果是 13 x 13,其中的数字像 ASCII 艺术一样排列。其下,10个数字是最后一层的输出结果,准确率从左起依次为0到9。在这种情况下,数字 5 是 188,这是最有可能的,数字 7 是 63,这是时间点。

最后一行显示识别结果,正确识别为“result = 5”,即数字5。
我认为识别率约为90%。

CP/M-80のニューラルネットワークで手書き文字認識
“没有什么是不可能的” MZ-700 也有效。 35 年前,您会因为在 Oh!MZ 上发帖而获得一块金子。
(使用 LSX-Dodgers 1.43(适用于 MZ-700/1500 v0.01))

技术细节

基本策略

量化在 MNIST 手写数字数据集上训练的网络并在定点上运行。

重要的是尽可能减少网络参数的数量,以适应​​ 8 位 CPU 可以执行的大小,并以 8 到 16 位完成计算。

网络结构

网络配置如下表所示。由输入层、卷积层和全连接层组成的三层神经网络。卷积层的核大小为 3×3×8。

输出形状 参数# 激活
输入 (28, 28) 0 没有任何
二维卷积 (13, 13, 8) 80 ReLU
全连接 (10) 13520 ReLU (Softmax)

参数总数为13600个,由于1个参数用1个字节表示,数据量超过13K字节。

作为减少参数数量的一种手段,将卷积层的步幅设置为2,并将输入图像的大小调整为1/2左右。我们还省略了全连接层的偏差。

对于全连接层的激活函数,Softmax只在训练时使用,ReLU在CP/M推理时使用。

学习

使用 Google Colab 使用 Python + TensorFlow 实现训练网络,并以 JSON 格式输出权重。我们在 10 个 epoch 内完成了训练。

model_training/MNIST_minimum.ipynb 是训练网络源。
以 json 格式输出学习到的网络权重。

量化

以双精度实数格式训练的网络权重被量化为具有 1 位符号、2 位整数精度和 5 位小数精度的 8 位定点格式。卷积层的输出也有 5 位小数精度,但是由于它是无符号的,所以它有 3 位整数精度。分层计算为 16 位,以防止溢出。

输入图像是一个介于 0 和 255 之间的值,对应于 0.0 和 1.0 之间的亮度。因此,需要将输入值减小到 1/255 的处理,但是为了加速将其替换为 1/256,卷积层的权重提前乘以 256/255。

符号 整数 分数
输入 0 0 8位
Conv2D(重量) 1 位 2位 5位
Conv2D(输出) 0 3位 5位
F.C.(重量) 1 位 2位 5位
FC(输出) 0 3位 5位

在 model_training/NNSS-V_MNIST.rb 中,json 格式的权重被读取、量化,并以 json 格式再次输出。

权重的二进制格式

我将量化权重存储在二进制文件中。它只是一个包含 8 位整数的文件,没有任何特定的标题。偏移值如下表所示。

抵消 包含 形状
0 Conv2D 偏差 “8”
8 Conv2D 内核 “3” “3” “8”
80 F.C.内核 “1352” “10”

在 model_training/make_weights.rb 中加载量化的 json 格式权重并以二进制格式输出。使用 CP/M 上的输出二进制文件。

使用的编译器

z88dk用过的。
您可以在 C99 扩展的块中使用变量声明、单行注释 (//) 和 stdint.h。但是,虽然可以声明多维数组的类型,但实际访问行为是可疑的,所以将其转换为一维数组并进行访问。

void example(uint8_t hoge[][SIZE], int x, int y)
{
    uint8_t a = hoge[y][x];             // NG?
    uint8_t b = hoge[0][y * SIZE + x];  // OK
}

这是一种可以完成的技术,因为它不检查下标范围。

开发时的执行环境(CP/M模拟器)

开发中Win32 CP/M 播放器确认它可以在 8 位机器上使用通用源代码项目的X1模拟器eX1,LSX-Dodgers 1.23版的修改版(围绕SP修改,体现在原版1.40),CP/M V2.2(夏普型号Language Master CZ-128SF)。

在最后

我想我第一次实现神经网络是在 1991 年夏天。一开始Hu-BASIC for X1太慢了,所以我用αFORTRAN重写了。我终于完成了我 30 岁的作业。

参考

  1. 挑战神经计算机,Satoru Shiono,Agne Shofusha,1990,ISBN 4-900508-03-9
  2. 介绍性神经计算机,Toyohiko Kikuchi,Ohmsha,1990,ISBN 4-274-07547-8

原创声明:本文系作者授权爱码网发表,未经许可,不得转载;

原文地址:https://www.likecs.com/show-308627044.html

相关文章:

  • 2021-12-14
  • 2021-10-17
  • 2021-12-14
  • 2021-08-15
  • 2021-12-14
  • 2021-12-06
  • 2021-11-03
  • 2022-01-12
猜你喜欢
  • 2021-12-16
  • 2021-12-29
  • 2021-09-19
  • 2021-12-15
  • 2021-09-27
  • 2022-01-01
  • 2021-12-10
  • 2021-12-06
相关资源
相似解决方案