英特尔oneAPI人工智能黑客松 - 机器视觉挑战案例

简介: 英特尔oneAPI人工智能黑客松 - 机器视觉挑战案例

英特尔oneAPI人工智能黑客松 - 机器视觉挑战案例

本文关键字:英特尔、oneAPI、人工智能、机器视觉

一、活动介绍

前一阵英特尔和C站官方联合举办了oneAPI的人工智能黑客松活动,也就是使用英特尔的官方套件去解决一些计算机视觉领域的问题,活动分为3个赛道:

  • 计算机视觉挑战:检测并清除杂草
  • 机器学习:预测淡水质量
  • oneAPI开放创新:使用oneAPI人工智能分析工具包实现任何创意

活动主办方提供了源码案例以及公开课视频教程,并且整体的实现流程也描述的十分清楚,可以方便大家快速上手。笔者虽然一直在人工智能领域工作,但是在机器视觉方面还是接触的比较少,但是查看了相关资料后也能在比较短的时间内实现自己的构想,并且感觉自己也get了新技能,不得不由衷点个赞!

二、环境准备

1. 硬件要求

因为是基于英特尔的套件进行机器视觉方面的工作,所以会用到CPU个GPU资源,需要在Intel的机器上进行开发。当然,如果没有合适的机器,也可以使用官方提供的云环境,小编也是尝试了一下,可以免费申请到半年的使用权,并且配置并不低,可以说是十分良心了。

2. 软件环境

如果想要尽快开始,只需要自行安装一些基础的python环境,能够构建官方的案例即可:https://github.com/idz-cn/2023hackathon/tree/main/computer-vision-track

我们可以参考相关的代码,并且可以下载到需要的数据集:https://www.mvtec.com/company/research/datasets/mvtec-ad,里面包含了很多场景的训练图片,可以直接使用。

三、方案实现

笔者使用的数据集是cable,也就是电缆切面。我们可以通过训练学习让模型知道什么样的情况是合格的,而什么样的是不合规的。以下将列出部分代码和步骤,详细的可以参考官方案例:

1. 数据集准备

首先要准备好训练集 - train测试集 - test,并且两者都需要挑选出可以被认可的 - good不被认可的 - bad,这些图片我们可以从数据集中手动跳转,也可以随机抽取几张,或者参考案例中的数据准备步骤:https://github.com/oneapi-src/visual-quality-inspection#2-data-preparation

2. 训练和预测

  • 对比显示两组图片

在模型训练阶段,我们先从训练集中抽取一些图片来做对比显示:

import cv2
train_dir = './data/train' # image folder
# get the list of jpegs from sub image class folders
good_imgs = [fn for fn in os.listdir(f'{train_dir}/good') if fn.endswith('.png')]
bad_imgs = [fn for fn in os.listdir(f'{train_dir}/bad') if fn.endswith('.png')]
# randomly select 3 of each
select_norm = np.random.choice(good_imgs, 3, replace = False)
select_pneu = np.random.choice(bad_imgs, 3, replace = False)
# plotting 2 x 3 image matrix
fig = plt.figure(figsize = (10,10))
for i in range(6):
    if i < 3:
        fp = f'{train_dir}/good/{select_norm[i]}'
        label = 'Acceptable Cable'
    else:
        fp = f'{train_dir}/bad/{select_pneu[i-3]}'
        label = 'Defective Cable'
    ax = fig.add_subplot(2, 3, i+1)
    # to plot without rescaling, remove target_size
    fn = cv2.imread(fp)
    fn_gray = cv2.cvtColor(fn, cv2.COLOR_BGR2GRAY)
    plt.imshow(fn, cmap='Greys_r')
    plt.title(label)
    plt.axis('off')
plt.show()

  • 接下来需要将图片以数据的形式读取,也就是矩阵或数组的形式
# making n X m matrix
def img2np(path, list_of_filename, size = (64, 64)):
    # iterating through each file
    for fn in list_of_filename:
        fp = path + fn
        current_image = cv2.imread(fp)
        current_image = cv2.cvtColor(current_image, cv2.COLOR_BGR2GRAY)
        # turn that into a vector / 1D array
        img_ts = [current_image.ravel()]
        try:
            # concatenate different images
            full_mat = np.concatenate((full_mat, img_ts))
        except UnboundLocalError: 
            # if not assigned yet, assign one
            full_mat = img_ts
    return full_mat
# run it on our folders
good_images = img2np(f'{train_dir}/good/', good_imgs)
bad_images = img2np(f'{train_dir}/bad/', bad_imgs)
def find_stat_img(full_mat, title, size = (1024, 1024)):
    # calculate the average
    mean_img = np.mean(full_mat, axis = 0)
    mean_img = mean_img.reshape(size)
    var_img = np.var(full_mat, axis = 0)
    var_img = var_img.reshape(size)
    max_img = np.amax(full_mat, axis = 0)
    max_img = max_img.reshape(size)
    min_img = np.amin(full_mat, axis = 0)
    min_img = min_img.reshape(size)
    figure, (ax1, ax2, ax3, ax4) = plt.subplots(1, 4, sharey=True, figsize=(15, 15))
    ax1.imshow(var_img, vmin=0, vmax=255, cmap='Greys_r')
    ax1.set_title(f'Variance {title}')
    ax2.imshow(mean_img, vmin=0, vmax=255, cmap='Greys_r')
    ax2.set_title(f'Average {title}')
    ax3.imshow(max_img, vmin=0, vmax=255, cmap='Greys_r')
    ax3.set_title(f'Max {title}')
    ax4.imshow(min_img, vmin=0, vmax=255, cmap='Greys_r')
    ax4.set_title(f'Min {title}')
    plt.show()
    return mean_img, var_img

此处的传参需要根据图片尺寸来调整,这里可以看到简单分析后的效果:

  • 模型定义

接下来进行模型的定义,这里直接引用了官方代码:

class CustomVGG(nn.Module):
    def __init__(self, n_classes=2):
        super().__init__()
        self.feature_extractor = models.vgg16(pretrained=True).features[:-1]
        self.classification_head = nn.Sequential(
            nn.MaxPool2d(kernel_size=2, stride=2),
            nn.AvgPool2d(
                kernel_size=(INPUT_IMG_SIZE[0] // 2 ** 5, INPUT_IMG_SIZE[1] // 2 ** 5)
            ),
            nn.Flatten(),
            nn.Linear(
                in_features=self.feature_extractor[-2].out_channels,
                out_features=n_classes,
            ),
        )
        self._freeze_params()
    def _freeze_params(self):
        for param in self.feature_extractor[:23].parameters():
            param.requires_grad = False
    def forward(self, x_in):
        """
        forward
        """
        feature_maps = self.feature_extractor(x_in)
        scores = self.classification_head(feature_maps)
        if self.training:
            return scores
        probs = nn.functional.softmax(scores, dim=-1)
        weights = self.classification_head[3].weight
        weights = (
            weights.unsqueeze(-1)
            .unsqueeze(-1)
            .unsqueeze(0)
            .repeat(
                (
                    x_in.size(0),
                    1,
                    1,
                    INPUT_IMG_SIZE[0] // 2 ** 4,
                    INPUT_IMG_SIZE[0] // 2 ** 4,
                )
            )
        )
        feature_maps = feature_maps.unsqueeze(1).repeat((1, probs.size(1), 1, 1, 1))
        location = torch.mul(weights, feature_maps).sum(axis=2)
        location = F.interpolate(location, size=INPUT_IMG_SIZE, mode="bilinear")
        maxs, _ = location.max(dim=-1, keepdim=True)
        maxs, _ = maxs.max(dim=-2, keepdim=True)
        mins, _ = location.min(dim=-1, keepdim=True)
        mins, _ = mins.min(dim=-2, keepdim=True)
        norm_location = (location - mins) / (maxs - mins)
        return probs, norm_location

接下来需要不断的反复调整参数,来查看模型的表现,此处略去。

  • 模型训练

根据定义好的参数训练模型,然后使用测试集查看具体表现。

# model training starts
# Model Training
# Intitalization of DL architechture along with optimizer and loss function
model = CustomVGG()
class_weight = torch.tensor(class_weight).type(torch.FloatTensor).to(DEVICE)
criterion = nn.CrossEntropyLoss(weight=class_weight)
optimizer = optim.Adam(model.parameters(), lr=LR)
# Ipex Optimization
model, optimizer = ipex.optimize(model=model, optimizer=optimizer, dtype=torch.float32)
# Training module
start_time = time.time()
trained_model = train(train_loader, model=model, optimizer=optimizer, criterion=criterion, epochs=EPOCHS,
    device=DEVICE, target_accuracy=TARGET_TRAINING_ACCURACY)
train_time = time.time()-start_time
# Save weights
model_path = f"{subset_name}.pt"
torch.save(trained_model.state_dict(), model_path)

3. 评估和量化

  • 模型评估

评估一个模型有多个指标,可以使用evaluate等方法查看。

y_true, y_pred = evaluate(trained_model, test_loader, DEVICE, labels=True)

  • 模型量化

在模型训练完成后,可以将其量化导出,这样通过十分简短的代码就可以调用。

from neural_compressor.config import PostTrainingQuantConfig, AccuracyCriterion, TuningCriterion
from neural_compressor import quantization
# INC will not quantize some layers optimized by ipex, such as _IPEXConv2d, 
# so we need to create original model object and load trained weights
model = CustomVGG()
model.load_state_dict(torch.load(model_path))
model.to(DEVICE)
model.eval()
# define evaluation function used by INC
def eval_func(model):
    with torch.no_grad():
        y_true = np.empty(shape=(0,))
        y_pred = np.empty(shape=(0,))
        for inputs, labels in train_loader:
            inputs = inputs.to(DEVICE)
            labels = labels.to(DEVICE)
            preds_probs = model(inputs)[0]
            preds_class = torch.argmax(preds_probs, dim=-1)
            labels = labels.to("cpu").numpy()
            preds_class = preds_class.detach().to("cpu").numpy()
            y_true = np.concatenate((y_true, labels))
            y_pred = np.concatenate((y_pred, preds_class))
    return accuracy_score(y_true, y_pred)
# quantize model
conf = PostTrainingQuantConfig(backend='ipex',
                               accuracy_criterion = AccuracyCriterion(
                                   higher_is_better=True, 
                                   criterion='relative',  
                                   tolerable_loss=0.01))
q_model = quantization.fit(model,
                           conf,
                           calib_dataloader=train_loader,
                           eval_func=eval_func)
# save quantized model
# you can also find a json file saved with quantized model, which saved quantization information for each operator
quantized_model_path = './quantized_models'
if not os.path.exists(quantized_model_path):
    os.makedirs(quantized_model_path)
q_model.save(quantized_model_path)
  • 模型预测

从指定路径加载模型后就可以开始预测:

q_model.to(DEVICE)
q_model.eval()
q_model = ipex.optimize(q_model)
y_true, y_pred = evaluate(q_model, test_loader, DEVICE, labels=True)


目录
相关文章
|
6月前
|
机器学习/深度学习 人工智能 算法
基于机器视觉的害虫种类及计数检测研究-人工智能项目-附代码
基于机器视觉的害虫种类及计数检测研究-人工智能项目-附代码
|
1月前
|
人工智能 边缘计算 算法
CDGA|利用人工智能与边缘计算显著提升数据治理效率与效果的实践案例
​ 在当今数字化转型的浪潮中,数据已成为企业最宝贵的资产之一。然而,随着数据量的爆炸性增长,如何高效、安全地治理这些数据成为企业面临的重要挑战。人工智能(AI)与边缘计算技术的融合,为数据治理带来了前所未有的机遇。本文将通过实际案例,探讨如何利用AI与边缘计算显著提升数据治理的效率和效果。
|
3月前
|
人工智能 Java 定位技术
人工智能ChatGPT 体验案例:使用ChatGPT实现java扫雷小游戏
这篇文章通过一个使用ChatGPT实现的Java扫雷小游戏案例,展示了ChatGPT在编程领域的应用能力。文章中包含了扫雷游戏的Java代码实现,代码中初始化了雷区地图,随机放置雷,计算每个格子周围雷的数量,并提供了一个简单的文本界面与用户交互进行游戏。游戏通过控制台输入接受玩家的指令,并给出相应的反馈。
人工智能ChatGPT 体验案例:使用ChatGPT实现java扫雷小游戏
|
3月前
|
机器学习/深度学习 人工智能 数据处理
【人工智能】项目实践与案例分析:利用机器学习探测外太空中的系外行星
探测外太空中的系外行星是天文学和天体物理学的重要研究领域。随着望远镜观测技术的进步和大数据的积累,科学家们已经能够观测到大量恒星的光度变化,并尝试从中识别出由行星凌日(行星经过恒星前方时遮挡部分光线)引起的微小亮度变化。然而,由于数据量巨大且信号微弱,传统方法难以高效准确地识别所有行星信号。因此,本项目旨在利用机器学习技术,特别是深度学习,从海量的天文观测数据中自动识别和分类系外行星的信号。这要求设计一套高效的数据处理流程、构建适合的机器学习模型,并实现自动化的预测和验证系统。
71 1
【人工智能】项目实践与案例分析:利用机器学习探测外太空中的系外行星
|
3月前
|
机器学习/深度学习 人工智能 算法
【人工智能】传统语音识别算法概述,应用场景,项目实践及案例分析,附带代码示例
传统语音识别算法是将语音信号转化为文本形式的技术,它主要基于模式识别理论和数学统计学方法。以下是传统语音识别算法的基本概述
76 2
|
3月前
|
机器学习/深度学习 人工智能 搜索推荐
【人工智能】人工智能在医疗健康中的应用以及实际案例和进展概述
人工智能(Artificial Intelligence, AI)在医疗健康领域的应用日益广泛,为医疗服务的提升和健康管理带来了革命性的变化。以下是人工智能在医疗健康中的主要应用
888 1
|
3月前
|
机器学习/深度学习 人工智能 自然语言处理
【人工智能】TensorFlow简介,应用场景,使用方法以及项目实践及案例分析,附带源代码
TensorFlow是由Google Brain团队开发的开源机器学习库,广泛用于各种复杂的数学计算,特别是涉及深度学习的计算。它提供了丰富的工具和资源,用于构建和训练机器学习模型。TensorFlow的核心是计算图(Computation Graph),这是一种用于表示计算流程的图结构,由节点(代表操作)和边(代表数据流)组成。
76 0
|
4月前
|
人工智能 数据挖掘 大数据
爆赞!GitHub首本标星120K的Python程序设计人工智能案例手册
为什么要学习Python? Python简单易学,且提供了丰富的第三方库,可以用较少的代码完成较多的工作,使开发者能够专注于如何解决问题而只花较少的时间去考虑如何编程。此外,Python还具有免费开源、跨平台、面向对象、胶水语言等优点,在系统编程、图形界面开发、科学计算、Web开发、数据分析、人工智能等方面有广泛应用。尤其是在数据分析和人工智能方面,Python已成为最受开发者欢迎的编程语言之一,不仅大量计算机专业人员选择使用Python进行快速开发,许多非计算机专业人员也纷纷选择Python语言来解决专业问题。 由于Python应用广泛,关于Python的参考书目前已经有很多,但将Pytho
|
5月前
|
人工智能 数据挖掘 大数据
538个代码示例!麻省理工教授的Python程序设计+人工智能案例实践
Python简单易学,且提供了丰富的第三方库,可以用较少的代码完成较多的工作,使开发者能够专注于如何解决问题而只花较少的时间去考虑如何编程。 此外,Python还具有免费开源、跨平台、面向对象、胶水语言等优点,在系统编程、图形界面开发、科学计算、Web开发、数据分析、人工智能等方面有广泛应用。 尤其是在数据分析和人工智能方面,Python已成为最受开发者欢迎的编程语言之一,不仅大量计算机专业人员选择使用Python进行快速开发,许多非计算机专业人员也纷纷选择Python语言来解决专业问题。 由于Python应用广泛,关于Python的参考书目前已经有很多,但将Python编程与数据分析、人工智
|
5月前
|
机器学习/深度学习 人工智能 自然语言处理
【人工智能】第五部分:ChatGPT的实际应用案例和未来发展方向
【人工智能】第五部分:ChatGPT的实际应用案例和未来发展方向
185 3

热门文章

最新文章

下一篇
无影云桌面