1. Trang chủ
  2. » Luận Văn - Báo Cáo

báo cáo bài tập nhóm nhận diện khuôn mặt bằng ai dự đoán tuổi và giới tính

12 18 0
Tài liệu đã được kiểm tra trùng lặp

Đang tải... (xem toàn văn)

Tài liệu hạn chế xem trước, để xem đầy đủ mời bạn chọn Tải xuống

THÔNG TIN TÀI LIỆU

Thông tin cơ bản

Tiêu đề Nhận diện khuôn mặt bằng AI dự đoán tuổi và giới tính
Tác giả Phan Thu Huyền, Chu Tú Trinh, Nguyễn Thị Thảo Uyên, Trương Điệp Y
Người hướng dẫn TS Bùi Hà Đức
Trường học Trường Đại học Sư phạm Kỹ thuật TP. HCM
Chuyên ngành Trí Tuệ Nhân Tạo
Thể loại Báo cáo bài tập nhóm
Năm xuất bản 2023
Thành phố Tp. Hồ Chí Minh
Định dạng
Số trang 12
Dung lượng 238,1 KB

Nội dung

LÝ DO CHỌN ĐỀ TÀI Chúng em thực hiện bài tập nhóm lần này theo yêu cầu thầy đưa ra, qua đó có thể tích lũy cho bản thân một số điều sau: - Sử dụng thuần thục các thư viện, thuật toán - G

Trang 1

BỘ GIÁO DỤC VÀ ĐÀO TẠO TRƯỜNG ĐẠI HỌC SƯ PHẠM KỸ THUẬT TP HCM

KHOA CƠ KHÍ CHẾ TẠO MÁY

BÁO CÁO BÀI TẬP NHÓM NHẬN DIỆN KHUÔN MẶT BẰNG AI

DỰ ĐOÁN TUỔI VÀ GIỚI TÍNH

MÔN HỌC: TRÍ TUỆ NHÂN TẠO GVHD: TS BÙI HÀ ĐỨC

SVTH: Phan Thu Huyền 21104014 Chu Tú Trinh 21104088 Nguyễn Thị Thảo Uyên 21104053 Trương Điệp Y 21104093

Tp Hồ Chí Minh, tháng 11 năm 2023

Trang 2

MỤC LỤC

1 LÝ DO CHỌN ĐỀ TÀI 1

2 TỔNG QUAN SƠ BỘ 1

3 PHÂN TÍCH CODE 1

4 KHÓ KHĂN VÀ GIẢI QUYẾT 10

Trang 3

1

1 LÝ DO CHỌN ĐỀ TÀI

Chúng em thực hiện bài tập nhóm lần này theo yêu cầu thầy đưa ra, qua đó có thể tích lũy cho bản thân một số điều sau:

- Sử dụng thuần thục các thư viện, thuật toán

- Giúp nhận biết được gương mặt, dự đoán được tuổi và giới tính của người ngồi trước camera, sau đó xem người đó có tập trung vào trong quảng cáo đang chiếu ra trên màn hình hay không Từ đó xác định được các nhóm đối tượng phù hợp để xuất hiện quảng cáo, tăng hiệu quả của công việc

- Cải thiện và phát triển các kỹ năng làm việc nhóm, khả năng research,

2 TỔNG QUAN SƠ BỘ

Thừa hưởng những thành tựu của nền khoa học kỹ thuật phát triển Nhận diện khuôn mặt

là một công nghệ được ứng dụng rộng rãi trong đời sống hằng ngày của con người như các hệ thống giám sát tại các tòa nhà, sân bay, trạm ATM, hệ thống chấm công, camera chống trộm, xác thực danh tính, …có rất nhiều các phương pháp nhận dạng khuôn mặt để nâng cao hiệu suất, bảo mật hiệu quả, cải thiện độ chính xác, tích hợp dễ dàng hơn Hệ thống nhận dạng khuôn mặt được sử dụng trong các trường hợp như đăng nhập ID, phát hiện gian lận, an ninh mạng, kiểm soát sân bay và biên giới, ngân hàng, chăm sóc sức khỏe Tuy nhiên dù ít hay nhiều thì những phương pháp này đang gặp phải những khó khăn, thử thách như về độ sáng, hướng nghiêng, kích thước hình ảnh, hay ảnh hưởng của tham số môi trường

3 PHÂN TÍCH CODE

Đầu tiên, chúng em import các thư viện và mô đun cần thiết để chạy code

import tensorflow as tf

from tensorflow.keras.utils import load_img

from keras.models import Sequential, Model

from keras.layers import Dense, Conv2D, Dropout, Flatten, MaxPooling2D, Input

import numpy as np

import random

import matplotlib pyplot as plt

import os

import seaborn as sns

import warnings

from tqdm notebook import tqdm

warnings filterwarnings ( 'ignore' )

Sau đó, kết nối với GG Drive và giải nén dữ liệu tệp zip UTKFace.zip

from google.colab import drive

drive.mount( '/content/drive' )

! unzip '/content/drive/MyDrive/UTKFace.zip'

Tiếp theo, cần tạo ra ba danh sách để lưu trữ độ tuổi, giới tính và đường dẫn hình ảnh Trích

Trang 4

xuất tên tệp hình ảnh bằng cách sử dụng thư mục os.list cung cấp tất cả tên tệp bên trong UTKFace và xáo trộn các tên tệp đó vì dữ liệu khi nhận diện là ngẫu nhiên, không tuần tự BASE_DIR = '/content/UTKFace'

age_labels = []

gender_labels = []

image_paths = []

image_filenames = os listdir ( BASE_DIR )

random shuffle ( image_filenames )

Đoạn code dưới đây đang duyệt qua danh sách các hình ảnh để lấy thông tin và giới tính từ tên tệp:

for image in tqdm ( image_filenames ):

image_path = os path join ( BASE_DIR , image )

img_components = image split ( '_' )

age_label = int ( img_components [ 0 ])

gender_label = int ( img_components [ 1 ])

# Append the image_path, age_label, and gender_label

age_labels append ( age_label )

gender_labels append ( gender_label )

image_paths append ( image_path )

Sau đó in ra để xác định xem số lượng nhãn độ tuổi, nhãn giới tính và đường dẫn hình ảnh có giống nhau hay không

print ( 'Number of age_labels: { len ( age_labels ) } , Number of gender_labels: { len ( gender_labels ) } , Number of image_paths: { len ( image_paths ) } ' )

Tiếp theo tạo một từ điển đơn giản, 0 là Male, 1 là Female

gender_mapping = {

1 : 'Female' ,

0 : 'Male'

}

Chuyển đổi từng danh sách đã tạo thành từng cột riêng để khung dữ liệu ngắn gọn và đẹp mắt hơn

import pandas as pd

df = pd DataFrame ()

df [ 'image_path' ], df [ 'age' ], df [ 'gender' ] = image_paths , age_labels , gender_labels

df head ( 5 )

Trang 5

3

Và chúng em có đoạn code cho hiển thị một hình ảnh ngẫu nhiên, phân tích dữ liệu và cho ra tuổi cùng giới tính của tấm hình ấy

from PIL import Image

rand_index = random randint ( 0 , len ( image_paths ))

age = df [ 'age' ][ rand_index ]

gender = df [ 'gender' ][ rand_index ]

IMG = Image open ( df [ 'image_path' ][ rand_index ])

plt title ( 'Age: { age } Gender: { gender_mapping [ gender ] } ' )

plt axis ( 'off' )

plt imshow ( IMG )

Dưới đây là code tạo biểu đồ phân phối tuổi và giới tính trong tệp dữ liệu

sns distplot( df [ 'age' ])

sns countplot( df [ 'gender' ])

Sau đó, sẽ cho xuất hiện một loạt các hình ảnh trong tệp với các thông tin như độ tuổi và giới tính tương ứng

for index , sample , age , gender in samples itertuples ():

plt subplot ( 4 , 4 , index + 1 )

img = load_img( sample )

img = np array ( img )

plt axis ( 'off' )

plt title ( 'Age: { age } Gender: { gender_mapping [ gender ] } ' )

plt imshow ( img )

def extract_image_features ( images ):

features = list () Đây là khai báo hàm Python có tên là ‘extract_image_features’, nhận một tham số là

images Tham số này là một danh sách chứa đường dẫn đến các hình ảnh hoặc nội dung hình ảnh

features = list(): Tạo một biến features là một danh sách rỗng được sử dụng để lưu trữ các đặc trưng của hình ảnh sau khi được xử lý

for image in tqdm ( images ):

img = load_img( image , grayscale = True ) img = img resize(( 128 , 128 ), Image ANTIALIAS) img = np array ( img )

features append ( img ) features = np array ( features ) features = features reshape ( len ( features ), 128 , 128 , 1 ) return features

Trang 6

Thực hiện việc xử lý từng hình ảnh trong danh sách ‘images’, duyệt và thay đổi hình ảnh sau

đó thay đổi kích thước ảnh thành 128x128 pixel, chuyển đổi thành Numpy thêm vào danh sách ‘features’

X = extract_image_features ( df [ 'image_path' ])

X shape

X = X 255.0 Gán kết quả trả về chứa các đặc trưng của tất cả hình ảnh

y_gender = np array ( df [ 'gender' ])

y_age = np array ( df [ 'age' ] ) Đoạn code này giúp chuyển đổi dữ liệu từ cột của DataFrame thành các mảng NumPy để thuận tiện cho việc xử lý và tính toán

input_shape = ( 128 , 128 , ) Dòng code này định nghĩa biến input_shape là một tuple có giá trị là (128, 128, 1)

inputs = Input( (input_shape) )

conv_1 = Conv2D( 32 , kernel_size =( 3 , 3 ), activation = 'relu' )( inputs )

max_1 = MaxPooling2D( pool_size =( 2 , 2 ))( conv_1 )

conv_2 = Conv2D( 64 , kernel_size =( 3 , 3 ), activation = 'relu' )( max_1 )

max_2 = MaxPooling2D( pool_size =( 2 , 2 ))( conv_2 )

conv_3 = Conv2D( 128 , kernel_size =( 3 , 3 ), activation = 'relu' )( max_2 )

max_3 = MaxPooling2D( pool_size =( 2 , 2 ))( conv_3 )

conv_4 = Conv2D( 256 , kernel_size =( 3 , 3 ), activation = 'relu' )( max_3 )

max_4 = MaxPooling2D( pool_size =( 2 , 2 ))( conv_4 )

flatten = Flatten()( max_4 )

Định nghĩa đầu vào của mô hình với kích thước là input_shape Sau đó, Tích chập đầu vào với 32 bộ lọc kích thước (3, 3) và hàm kích hoạt ReLU, Lấy giá trị lớn nhất từ các vùng 2x2, giúp giảm kích thước của đầu ra Lớp Flatten được sử dụng để biến đổi đầu ra của lớp pooling cuối cùng (max_4) thành một vector 1 chiều Nó "làm phẳng" dữ liệu, giữ nguyên thông tin từ các bức ảnh đã được trích xuất các đặc trưng

dense_1 = Dense( 256 , activation = 'relu' )( flatten )

dense_2 = Dense( 256 , activation = 'relu' )( flatten )

dropout_1 = Dropout( 0.3 )( dense_1 )

dropout_2 = Dropout( 0.3 )( dense_2 )

output_1 = Dense( 1 activation = 'sigmoid' , name = 'gender_out' )( dropout_1 )

output_2 = Dense( 1 activation = 'relu' , name = 'age_out' )( dropout_2 )

model = Model( inputs =[ inputs ], outputs =[ output_1 , output_2 ])

model compile( loss =[ 'binary_crossentropy' , 'mae' ],

optimizer = 'adam' , metrics =[ 'accuracy' ])

Đoạn code đang xây dựng một mô hình mạng nơ-ron sâu (deep learning) để thực hiện hai nhiệm vụ: dự đoán giới tính và tuổi từ ảnh đầu vào

from tensorflow.keras.utils import plot_model

plot_model( model )

Sau khi chạy đoạn mã trên sẽ vẽ biểu đồ cấu trúc của mô hình Biểu đồ này sẽ mô tả mối quan hệ giữa các lớp trong mô hình, giúp hiểu cấu trúc tổng quan của mô hình nhanh chóng

history = model fit( x = X , y =[ y_gender , y_age ],

batch_size = 32 , epochs = 50 , validation_split = 0.2 )

Tiến hành training

Trang 7

5

# plot results for gender

acc = history history[ 'gender_out_accuracy' ]

val_acc = history history[ 'val_gender_out_accuracy' ]

epochs = range ( len ( acc ))

plt plot ( epochs , acc , 'b' , label = 'Training Accuracy' )

plt plot ( epochs , val_acc , 'r' , label = 'Validation Accuracy' )

plt title ( 'Accuracy Graph' )

plt legend ()

plt figure ()

Dòng code này giúp theo dõi sự phát triển của độ chính xác trên cả tập training và tập kiểm thử qua các epoch, giúp đánh giá hiệu suất của mô hình và phát hiện hiện tượng overfitting hoặc underfitting

loss = history history[ 'gender_out_loss' ]

val_loss = history history[ 'val_gender_out_loss' ]

Lấy thông tin về giá trị mất mát trên tập training từ lịch sử training (history) Trong đoạn mã này, "gender_out_loss" là mất mát của lớp đầu ra dự đoán giới tính và lấy thông tin về giá trị mất mát trên tập kiểm thử từ lịch sử training

plt plot ( epochs , loss , 'b' , label = 'Training Loss' )

plt plot ( epochs , val_loss , 'r' , label = 'Validation Loss' )

plt title ( 'Loss Graph' )

plt legend ()

plt show ()

- 'b' và 'r' trong ‘plt.plot’ chỉ định màu của các đường ('b' cho màu xanh lam và 'r' cho màu đỏ)

- Tham số ‘label’ trong ‘plt.plot’ được sử dụng để gắn nhãn cho các dòng cho chú giải

- ‘plt.title’ đặt tiêu đề cho plot

- ‘plt.legend()’ hiển thị chú giải, rất hữu ích khi vẽ nhiều dòng để phân biệt giữa chúng

Mã này thường được sử dụng trong đào tạo machine learning model trong đó 'epochs' biểu thị số lần thuật toán học sẽ hoạt động thông qua toàn bộ tập dữ liệu đào tạo 'Training Loss'

và 'Validation Loss' là các số liệu được sử dụng để đánh giá mức độ hoạt động của mô hình trong quá trình đào tạo và trên dữ liệu không nhìn thấy tương ứng Plot giúp hình dung các giá trị mất mát này thay đổi như thế nào qua các giai đoạn huấn luyện

# plot results for age

loss = history history[ 'age_out_loss' ]

val_loss = history history[ 'val_age_out_loss' ]

epochs = range ( len ( loss ))

- Vẽ đồ thị các giá trị tổn thất huấn luyện và xác thực cho đầu ra 'age' của mô hình

'age_out_loss' và 'val_age_out_loss' là các phần giữ chỗ cho các khóa thực tế trong đối tượng 'history' của bạn để lưu trữ các giá trị tổn thất trong quá trình đào tạo và xác thực cho đầu ra 'age'

- Đảm bảo điều chỉnh mã theo các khóa thực tế được sử dụng trong đối tượng 'history' của bạn Ngoài ra, việc cung cấp nhãn trục với ‘plt.xlabel’ và ‘plt.ylabel’ có thể nâng cao khả năng diễn giải biểu đồ của bạn

plt plot ( epochs , loss , 'b' , label = 'Training Loss' )

plt plot ( epochs , val_loss , 'r' , label = 'Validation Loss' )

plt title ( 'Loss Graph' )

Trang 8

plt legend ()

plt show ()

Sử dụng lại đoạn mã để vẽ sơ đồ mất dữ liệu đào tạo và xác thực qua các epochs Mã này được sử dụng để trực quan hóa xu hướng mất đi quá trình đào tạo và xác thực trong quá trình đào tạo

def get_image_features ( image ):

img = load_img( image , grayscale = True )

img = img resize(( 128 , 128 ), Image ANTIALIAS)

img = np array ( img )

img = img reshape ( 1 , 128 , 128 , 1 )

img = img 255.0

return img

- Load Image:Hàm sử dụng hàm Load_img từ Keras để tải hình ảnh ở thang độ xám

- Resize Image: Nó thay đổi kích thước hình ảnh thành kích thước cố định 128x128 pixel bằng cách sử dụng tính năng khử răng cưa để thay đổi kích thước mượt mà

- Convert to NumPy Array: Hình ảnh được chuyển đổi thành mảng NumPy bằng np.array

- Reshape: Mảng được định hình lại để có kích thước (1, 128, 128, 1) Các kích thước bổ sung thường được sử dụng khi làm việc với mạng nơ ron tích chập (CNN)

- Normalization: Các giá trị pixel được chuẩn hóa thành phạm vi [0, 1] bằng cách chia mỗi giá trị pixel cho 255,0

Kết quả có thể được sử dụng làm đầu vào cho mô hình mong đợi hình ảnh có kích thước 128x128 pixel

img_to_test = '/content/drive/MyDrive/2.png'

features = get_image_features ( img_to_test )

pred = model predict( features )

gender = gender_mapping [ round ( pred [ 0 ][ 0 ][ 0 ])]

age = round ( pred [ 1 ][ 0 ][ 0 ])

plt title ( 'Predicted Age: { age } Predicted Gender: { gender } ' )

plt axis ( 'off' )

plt imshow ( np array (load_img( img_to_test )))

- Sử dụng hàm ‘get_image_features’ để xử lý trước hình ảnh rồi đưa ra dự đoán bằng mô hình Sau khi nhận được dự đoán, bạn sẽ hiển thị hình ảnh gốc cùng với độ tuổi và giới tính được dự đoán

- Giới tính dự đoán được lấy từ ‘gender_mapping’, có lẽ là mapping từ các giá trị số sang nhãn giới tính

- Độ tuổi dự đoán được làm tròn, giả sử đó là dự đoán hồi quy

- ‘plt.title’, ‘plt.axis('off')’ và ‘plt.imshow’ được sử dụng để hiển thị hình ảnh gốc với độ tuổi

và giới tính được dự đoán

from IPython display import display , Javascript, Image

from google.colab.output import eval_js

from base64 import b64decode , b64encode

import cv2

import numpy as np

import PIL

import io

import html

import time

Trang 9

7

Import các thư viện cần thiết

def js_to_image ( js_reply ):

"""

Params:

js_reply: JavaScript object containing image from webcam

Returns:

img: OpenCV BGR image

"""

# decode base64 image

image_bytes = b64decode ( js_reply split( ',' )[ 1 ])

# convert bytes to numpy array

jpg_as_np = np frombuffer ( image_bytes , dtype = np uint8 )

# decode numpy array into OpenCV BGR image

img = cv2 imdecode( jpg_as_np , flags = 1 )

return img

- Decode Base64 Image: Hàm lấy hình ảnh được mã hóa base64 từ đối tượng JavaScript (‘js_reply’), phân tách nó để lấy nội dung được mã hóa base64 thực tế, sau đó giải mã nó bằng ‘b64decode’ Bước này chuyển đổi hình ảnh được mã hóa base64 thành byte

- Convert Bytes to NumPy Array: Các byte được giải mã sau đó được chuyển đổi thành mảng NumPy bằng cách sử dụng ‘np.frombuffer’

- Decode NumPy Array into OpenCV BGR Image: Mảng NumPy được giải mã thành hình ảnh OpenCV BGR bằng ‘cv2.imdecode’ Tham số ‘flags=1’ chỉ ra rằng hình ảnh phải được đọc ở dạng màu

Kết quả là hình ảnh OpenCV BGR có thể được xử lý hoặc hiển thị thêm bằng các hàm OpenCV

# function to convert OpenCV Rectangle bounding box image into base64 byte string to be overlayed on video stream

def bbox_to_bytes ( bbox_array ):

"""

Params:

bbox_array: Numpy array (pixels) containing rectangle to overlay on video stream

Returns:

bytes: Base64 image byte string

"""

# convert array into PIL image

bbox_PIL = PIL Image.fromarray( bbox_array , 'RGBA' )

iobuf = io BytesIO ()

# format bbox into png for return

bbox_PIL save( iobuf , format = 'png' )

# format return string

bbox_bytes = 'data:image/png;base64, {} ' format (( str ( b64encode ( iobuf getvalue ()), 'utf-8' )))

return bbox_bytes

- Convert Array to PIL Image: Hàm chuyển đổi mảng NumPy đầu vào (được giả sử ở định dạng RGBA) thành Hình ảnh PIL với chế độ 'RGBA'

- Create Binary Stream: Một luồng nhị phân trong bộ nhớ (‘io.BytesIO()’) được tạo

- Save Image to Binary Stream:: Hình ảnh PIL được lưu vào luồng nhị phân ở định dạng PNG

Trang 10

- Convert to Base64 Byte String: Luồng nhị phân sau đó được chuyển đổi thành chuỗi byte được mã hóa base64

Kết quả ‘bbox_byte’ có thể được sử dụng để phủ hình chữ nhật trên luồng video bằng cách nhúng nó vào HTML hoặc sử dụng nó trong ứng dụng web

face_cascade = cv2 CascadeClassifier( cv2 samples.findFile( cv2 data.haarcascades +

'haarcascade_frontalface_default.xml' ))

def take_photo ( filename = 'photo.png' , quality = 0.8 ):

js = Javascript( '''

async function takePhoto(quality) {

const div = document.createElement('div');

const capture = document.createElement('button');

capture.textContent = 'Capture';

div.appendChild(capture);

const video = document.createElement('video');

video.style.display = 'block';

const stream = await navigator.mediaDevices.getUserMedia( {video: true} );

document.body.appendChild(div);

div.appendChild(video);

video.srcObject = stream;

await video.play();

// Resize the output to fit the video element

google.colab.output.setIframeHeight(document.documentElement.scrollHeight, true);

// Wait for Capture to be clicked

await new Promise((resolve) => capture.onclick = resolve);

const canvas = document.createElement('canvas');

canvas.width = video.videoWidth;

canvas.height = video.videoHeight;

canvas.getContext('2d').drawImage(video, 0, 0);

stream.getVideoTracks()[0].stop();

div.remove();

return canvas.toDataURL('image/jpeg', quality);

}

''' )

display ( js )

Ở bước này, chúng ta cung cấp một chức năng để chụp ảnh từ webcam của người dùng bằng môi trường Google Colab Hàm này được đặt tên là takePhoto và nhận hai tham số tùy chọn như sau: tên tệp mặc định là 'photo.png' và chất lượng mặc định là 0,8 Chức năng này thiết lập một nút để chụp ảnh, khởi tạo thành phần video để hiển thị nguồn cấp dữ liệu webcam

và trả về hình ảnh đã chụp dưới dạng URL dữ liệu ở định dạng JPEG Để sử dụng hàm này trong Jupyter, có thể gọi nó từ ô mã sau khi chạy mã được cung cấp

Thao tác này sẽ hiển thị nút "Chụp" và khi nhấp vào nút này, nó sẽ chụp ảnh từ webcam và trả về URL dữ liệu của hình ảnh Chúng ta có thể tùy chỉnh tên tệp và thông số chất lượng nếu cần Mã này được thiết kế cho môi trường Google Colab và dựa trên các tính năng dành riêng cho môi trường đó, chẳng hạn như google.colab.output.setIframeHeight Nếu sử dụng một môi trường khác, ta cần phải điều chỉnh code

Ngày đăng: 28/04/2024, 17:39

TỪ KHÓA LIÊN QUAN

TÀI LIỆU CÙNG NGƯỜI DÙNG

TÀI LIỆU LIÊN QUAN

w