TensorFlow.js – Nhận diện chữ số viết tay (Phần 1)

Trong bài viết này, hãy cùng học cách sử dụng TensorFlow.js trong nhiệm vụ Nhận dạng chữ số viết tay.

1. Giới thiệu

Trong bài hướng dẫn này, chúng ta hãy cùng xây dựng một mô hình TensorFlow.js để nhận dạng chữ số viết tay sử dụng CNN. Đầu tiên, chúng ta sẽ huấn luyện mô hình bằng cách cho nó “nhìn” vào hàng ngàn hình ảnh của chữ viết tay và nhãn của chúng. Sau đó, chúng ta sẽ đánh giá mô hình sử dụng bộ dữ liệu test mà nó chưa từng nhìn thấy trước đây.

Nhiệm vụ này được gọi là phân lớp (classification) vì chúng ta huấn luyện mô hình để gán cho các hình ảnh đầu vào với một nhóm đại diện cho các chữ số. Chúng ta huấn luyện mô hình bằng cách đưa cho nó các ví dụ của hình ảnh đầu vào cùng với nhãn đúng của chúng.

Bạn sẽ làm được gì?

Bạn sẽ cùng chúng tôi xây dựng một trang web sử dụng TensorFlow.js để huấn luyện mô hình trên chính trình duyệt của bạn. Đầu vào là một ảnh đen trắng, đầu ra là chữ số trong ảnh. Các bước bao gồm:

  • Nạp dữ liệu
  • Định nghĩa kiến trúc của mô hình
  • Huấn luyện mô hình và theo dõi hiệu quả của nó
  • Đánh giá mô hình thông qua các dự đoán của nó

Bạn sẽ học được gì?

  • Cú pháp của TensorFlow.js để tạo một mô hình CNN thông qua API
  • Thiết lập nhiệm vụ phân loại trong TensorFlow.js
  • Cách theo dõi việc huấn luyện mô hình trên trình duyệt sử dụng thư viện tfjs-vis.

Bạn cần những gì?

  • Phiên bản hiện tại của Chrome hoặc một trình duyệt khác hỗ trợ ES6.
  • Trình soạn thảo text trên máy của bạn hoặc trên web như Codepen hay Glitch.
  • Kiến thức về HTML, CSS, JavaScript, và Chrome DevTools.
  • Các khái niệm về mạng nơ ron nhân tạo.

2. Cài đặt

Bước 1: Tạo trang HTML và thêm mã JavaScript

Copy đoạn code sau và dán vào một file html, có thể đặt là index.html

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>TensorFlow.js Tutorial</title>

  <!-- Import TensorFlow.js -->
  <script src="https://cdn.jsdelivr.net/npm/@tensorflow/[email protected]/dist/tf.min.js"></script>
  <!-- Import tfjs-vis -->
  <script src="https://cdn.jsdelivr.net/npm/@tensorflow/[email protected]/dist/tfjs-vis.umd.min.js"></script>

  <!-- Import the data file -->
  <script src="data.js" type="module"></script>

  <!-- Import the main script file -->
  <script src="script.js" type="module"></script>

</head>

<body>
</body>
</html>

Bước 2: Tạo các file JavaScript cho dữ liệu và code

  1. Trong cùng thư mục với file HTML ở trên và tạo một file tên là data.js. Copy nội dung trong đường dẫn này vào file đó.
  2. Tiếp theo, tạo file có tên script.js và chèn đoạn code dưới đây vào file.
console.log('Hello TensorFlow');

Chú ý: Mặc dù code được chạy trên trình duyệt, vì ràng buộc của các giao thức đảm bảo an toàn mạng, bạn buộc phải cài đặt một máy chủ web trên localhost để có thể chạy thử. Nhưng nếu bạn không quen với điều đó, bạn có thể sử dụng Glitch, tạo một project và server đã sẵn sàng cho bạn.

Bước 3: Chạy thử

Bây giờ bạn đã có file HTML và JavaScript. Chạy index.html và mở giao diện devtools (ấn F12) trên trình duyệt của bạn.

Nếu mọi thứ hoạt động đúng, hai biến toàn cục sẽ được tạo là tf trỏ đến thư viện TensorFlow.js và tfvis trỏ đến thư viện tfjs-vis. Ngoài ra bạn sẽ nhận được thông diệp Hello TensorFlow.

3. Nạp dữ liệu

Chúng ta sẽ huấn luyện mô hình để phát hiện các chữ số trong các hình ảnh như phía dưới. Các hình ảnh này là ảnh grayscale có kích thước 28×28 từ dataset MNIST.

Các đoạn mã liên quan đến việc nạp dữ liệu đã được chuẩn bị sẵn để chúng ta có thể tập trung vào phần huấn luyện mô hình. Các bạn có thể tự đào sâu nghiên cứu filedata.js để hiểu cách dữ liệu được nạp. Hoặc kết thúc bài này bạn có thể tự tạo file nạp dữ liệu với cách riêng của mình. Lớp MnistData được dựng sẵn với hai phương thức:

  • nextTrainBatch(batchSize): trả về một batch các hình ảnh ngẫu nhiên và nhãn của chúng từ tập huấn luyện.
  • nextTestBatch(batchSize): trả về một batch các hình ảnh và nhãn của chúng từ bộ test

Lớp MnistData cũng thực hiện các bước quan trọng như xáo trộn và chuẩn hóa dữ liệu.

Có tổng số 65K hình ảnh, ta sẽ sử dụng 55K để huấn luyện và 10K để kiểm tra hiệu quả của mô hình sau đó. Và tất cả được thực hiện trên trình duyệt.

 Thêm các dòng sau vào file script.js

import {MnistData} from './data.js';

async function showExamples(data) {
  // Create a container in the visor
  const surface =
    tfvis.visor().surface({ name: 'Input Data Examples', tab: 'Input Data'});  

  // Get the examples
  const examples = data.nextTestBatch(20);
  const numExamples = examples.xs.shape[0];
  
  // Create a canvas element to render each example
  for (let i = 0; i < numExamples; i++) {
    const imageTensor = tf.tidy(() => {
      // Reshape the image to 28x28 px
      return examples.xs
        .slice([i, 0], [1, examples.xs.shape[1]])
        .reshape([28, 28, 1]);
    });
    
    const canvas = document.createElement('canvas');
    canvas.width = 28;
    canvas.height = 28;
    canvas.style = 'margin: 4px;';
    await tf.browser.toPixels(imageTensor, canvas);
    surface.drawArea.appendChild(canvas);

    imageTensor.dispose();
  }
}

async function run() {  
  const data = new MnistData();
  await data.load();
  await showExamples(data);
}

document.addEventListener('DOMContentLoaded', run);

Tải lại trang và một vài giây sau, bạn sẽ thấy các số như hình phía dưới.

Mục tiêu của chúng ta là huấn luyện mô hình. Với mỗi một hình ảnh, nó cần học ra được xác suất tốt nhất đại diện cho việc ảnh thuộc vào lớp nào trong 10 lớp (các chữ số từ 0 đến 9). Mỗi hình ảnh rộng 28, cao 28 và có 1 kênh màu duy nhất nên kích thước là [28, 28, 1]. Nếu như bạn đã sẵn sàng, chúng ta cùng tiếp tục với Phần 2.

Nguồn developers.google.com