使用HuggingFace Spaces和Gradio部署图像分类模型
我从事数据分析工作已经将近十年了。我时常使用机器学习技术从数据中获取洞见,并且对于使用经典的机器学习方法感到很舒服。
虽然我参加过几门关于神经网络和深度学习的慕课,但我从未在工作中使用过它们,而且这个领域对我来说似乎相当具有挑战性。我有以下这些偏见:
- 要开始使用深度学习,你需要学习很多东西:数学,不同的框架(我至少听说过三个:PyTorch、TensorFlow和Keras)和网络架构。
- 需要大量的数据集来训练模型。
- 没有强大的计算机(还必须具有Nvidia GPU)几乎无法取得良好的结果,所以很难进行设置。
- 要建立一个以机器学习为动力的服务,需要处理前端和后端。
我相信分析的主要目标是帮助产品团队基于数据做出正确的决策。现如今,神经网络肯定可以改进我们的分析,例如NLP可以从文本中获取更多的洞见。因此,我决定再次尝试利用深度学习的力量。
这就是我开始Fast.AI课程的原因(该课程在2022年初进行了更新,所以我认为内容已经有所改变,与此前在TDS上的评论不同)。我意识到使用深度学习解决任务并不那么困难。
这门课程采用自上而下的方法。所以你是从构建一个可工作的系统开始的,只有在之后才会深入了解所有所需的基础知识和细节。
在第二周,我制作了我的第一个以机器学习为动力的应用(你可以在这里尝试一下)。它是一个图像分类模型,可以识别我最喜欢的狗品种。令人惊讶的是,即使我的数据集中只有几千张图像,它也工作得很好。对我来说,我们现在可以轻松构建一个在十年前还是完全神奇的服务,这真是令人鼓舞。

因此,在本文中,您将找到一个初学者级别的教程,教您如何构建和部署第一个由机器学习驱动的服务。
什么是深度学习?
深度学习是机器学习的一个特定应用案例,我们使用多层神经网络作为模型。
神经网络非常强大。根据通用逼近定理,神经网络可以逼近任何函数,这意味着它们能够解决任何任务。
目前,您可以将这个模型简单地看作是一个黑盒子,它接受输入(在我们的例子中是一张狗的图像)并返回输出(在我们的例子中是一个标签)。

构建模型
您可以在Kaggle上找到此阶段的完整代码。
我们将使用Kaggle Notebooks来构建我们的深度学习模型。如果您还没有Kaggle账号,建议您先完成注册流程。Kaggle是一个流行的数据科学家平台,您可以在上面找到数据集、参加竞赛并运行和分享您的代码。
您可以在Kaggle上创建一个Notebook,并像在本地的Jupyter Notebook一样执行代码。Kaggle甚至提供GPU,因此我们将能够快速训练神经网络模型。

让我们首先导入所有的包,因为我们将使用许多Fast.AI工具。
from fastcore.all import *from fastai.vision.all import *from fastai.vision.widgets import *from fastdownload import download_url
加载数据
毋庸置疑,我们需要一个数据集来训练我们的模型。获取一组图像的最简单方法是使用搜索引擎。
DuckDuckGo搜索引擎有一个易于使用的API和方便的Python包duckduckgo_search
(更多信息),所以我们将使用它。
让我们试着搜索一张狗的图片。我们已经指定license_image = any
以仅使用具有Creative Commons许可的图像。
from duckduckgo_search import DDGSimport itertoolswith DDGS() as ddgs: res = list(itertools.islice(ddgs.images('photo samoyed happy', license_image = 'any'), 1))
在输出中,我们得到了关于图像的所有信息:名称、URL和大小。
{ "title": "Happy Samoyed dog photo and wallpaper. Beautiful Happy Samoyed dog picture", "image": "http://www.dogwallpapers.net/wallpapers/happy-samoyed-dog-wallpaper.jpg", "thumbnail": "https://tse2.mm.bing.net/th?id=OIP.BqTE8dYqO-W9qcCXdGcF6QHaFL&pid=Api", "url": "http://www.dogwallpapers.net/samoyed-dog/happy-samoyed-dog-wallpaper.html", "height": 834, "width": 1193, "source": "Bing"}
现在我们可以使用Fast.AI工具下载图像并显示缩略图。

我们看到了一只快乐的萨摩耶,这意味着它正在工作。所以让我们加载更多的照片。
我打算识别五种不同的狗品种(我最喜欢的品种)。我将为每个品种加载图片并将它们存储在单独的目录中。
breeds = ['siberian husky', 'corgi', 'pomeranian', 'retriever', 'samoyed']path = Path('dogs_breeds') # 定义路径for b in tqdm.tqdm(breeds): dest = (path/b) dest.mkdir(exist_ok=True, parents=True) download_images(dest, urls=search_images(f'photo {b}')) sleep(10) download_images(dest, urls=search_images(f'photo {b} puppy')) sleep(10) download_images(dest, urls=search_images(f'photo {b} sleep')) sleep(10) resize_images(path/b, max_size=400, dest=path/b)
运行这段代码后,您将在Kaggle的右侧面板上看到所有加载的照片。

下一步是将数据转换为适合Fast.AI模型的格式 – DataBlock
。
有一些参数您需要为此对象指定,但我只会强调最重要的几个:
splitter=RandomSplitter(valid_pct=0.2, seed=18)
:Fast.AI要求您选择一个验证集。验证集是一个保留数据,用于估计模型质量。验证数据在训练过程中不使用,以防止过拟合。在我们的案例中,验证集是我们数据集的随机20%。我们指定了seed
参数,以便下次能够精确重现相同的拆分。item_tfms=[Resize(256, method=’squish’)]
:神经网络以批处理方式处理图像。这就是为什么我们必须有相同大小的图片。有不同的图像调整大小方法,我们现在使用的是squish,但我们将在后面详细讨论它。
我们定义了一个数据块。函数show_batch
可以显示带有标签的随机图像集。

数据看起来还不错,所以让我们继续进行训练。
训练模型
你可能会感到惊讶,但下面的两行代码将完成所有工作。
我们使用了一个预训练模型(具有18个深层的卷积神经网络——Resnet18
)。这就是为什么我们调用了函数fine_tune
。
我们将模型训练了三个周期,这意味着模型看到了整个数据集三次。
我们还指定了指标——accuracy
(正确标记图片的比例)。您可以在每个周期后的结果中看到这个指标(它仅使用验证集计算,以免结果偏差)。然而,它不参与优化过程,仅供您参考。
整个过程大约花了30分钟,现在我们的模型可以以94.45%的准确率预测狗的品种。干得好!但我们能提高这个结果吗?
提高模型的准确率:数据清理和增强
如果您想尽快看到您的第一个模型工作,请随时将本节留给以后再看,继续进行模型的部署。
首先,让我们看看模型的错误:它能否将柯基与哈士奇或博美与金毛区分开来。我们可以使用confusion_matrix
来进行计算。注意,混淆矩阵也仅使用验证集计算。
Fast.AI课程中还分享了另一个技巧,即模型可以用来清理我们的数据。为此,我们可以查看损失最高的图像:这可能是模型以高置信度错误或以低置信度正确的情况。

显然,第一张图片的标签是错误的,而第二张图片包含了哈士奇和柯基。所以还有改进的空间。
幸运的是,Fast.AI提供了一个方便的ImageClassifierCleaner
小部件,可以帮助我们快速解决数据问题。您可以在笔记本中初始化它,然后就能够更改数据集中的标签。
cleaner = ImageClassifierCleaner(learn)cleaner
在每个类别之后,您可以运行以下代码来修复问题:删除图片或将其移动到正确的文件夹中。
for idx in cleaner.delete(): cleaner.fns[idx].unlink()for idx,breed in cleaner.change(): shutil.move(str(cleaner.fns[idx]), path/breed)
现在我们可以再次训练我们的模型,并看到准确率提高了:95.4%对比94.5%。
正确识别柯基的比例已经从88%增加到96%。真是太棒了!
改进我们的模型的另一种方法是改变我们的调整大小方法。我们使用的是压缩方法,但是正如你所见,它会改变自然物体的比例。让我们试着更有想象力一些,使用增强功能。
增强功能是对图像进行的更改(例如,对比度改进,旋转或裁剪)。这将为我们的模型提供更多变量的数据,希望能提高其质量。
像往常一样,使用Fast.AI,您只需要更改一些参数即可添加增强功能。

此外,由于在每个时期,通过增强功能,模型将看到略有不同的图像,我们可以增加时期的数量。经过六个时期,我们获得了95.65%的准确率-稍微好一点的结果。整个过程大约需要一个小时。
下载模型
最后一步是下载我们的模型。这非常简单。
learn.export('cuttest_dogs_model.pkl')
然后,您将获得一个标准的pickle
文件(常见的Python格式,用于存储对象)。只需在Kaggle笔记本的右侧面板上选择文件旁边的更多操作
,即可将模型下载到计算机上。
现在我们有了训练好的模型,让我们部署它,以便与世界分享结果。
部署您的模型
我们将使用HuggingFace Spaces和Gradio来构建我们的Web应用程序。
设置HuggingFace Space
HuggingFace是一家提供便利工具的公司,例如,流行的transformers库或共享模型和数据集的工具。今天,我们将使用他们的Spaces来托管我们的应用程序。
首先,如果您还没有注册,请创建一个帐户。这只需要几分钟的时间。请按照此链接。
现在是时候创建一个新的Space了。转到Spaces选项卡,点击“创建”按钮。您可以在文档中找到更详细的说明。
然后,您需要指定以下参数:
- 名称(它将用于您的应用程序URL,所以请谨慎选择),
- 许可证(我选择了开源Apache 2.0许可证),
- SDK(在此示例中,我将使用Gradio)。
然后,用户友好的HuggingFace会向您显示说明。 TL;DR现在您有了一个Git存储库,您需要将代码提交到那里。
Git有一个细微之处。由于您的模型很可能很大,最好设置Git LFS(大文件存储),这样Git就不会跟踪此文件的所有更改。有关安装,请按照网站上的说明进行操作。
-- 克隆存储库git clone https://huggingface.co/spaces/<your_login>/<your_app_name>cd <your_app_name>-- 设置git-lfsgit lfs installgit lfs track "*.pkl"git add .gitattributesgit commit -m "update gitattributes to use lfs for pkl files"
Gradio
Gradio是一个允许您仅使用Python构建令人愉快和友好的Web应用程序的框架。这就是为什么它对于原型设计非常有价值的工具(特别是对于像我这样没有深入的JavaScript知识的人)。
在Gradio中,我们将定义我们的接口,指定以下参数:
- input — 一个图像,
- output — 具有五个可能类别的标签,
- title、description 和一组示例图像(我们还需要将它们提交到代码库中),
enable_queue=True
可以帮助应用程序处理大量的流量,如果它变得非常受欢迎,- function 用于处理输入图像。
为了获取输入图像的标签,我们需要定义预测函数,该函数加载我们的模型并返回每个类别的概率字典。
最终,我们将在 app.py
中使用以下代码:
import gradio as grfrom fastai.vision.all import *learn = load_learner('cuttest_dogs_model.pkl')labels = learn.dls.vocab # 模型类别的列表def predict(img): img = PILImage.create(img) pred,pred_idx,probs = learn.predict(img) return {labels[i]: float(probs[i]) for i in range(len(labels))}gr.Interface( fn=predict, inputs=gr.inputs.Image(shape=(512, 512)), outputs=gr.outputs.Label(num_top_classes=5), title="最可爱的狗狗分类器 🐶🐕🦮🐕🦺", description="使用 HuggingFace Spaces 和 Gradio 创建的深度学习应用的演示。分类器训练于哈士奇、金毛犬、博美犬、柯基和萨摩耶的图像。", examples=['husky.jpg', 'retriever.jpg', 'corgi.jpg', 'pomeranian.jpg', 'samoyed.jpg'], enable_queue=True).launch()
如果您想了解更多关于 Gradio 的内容,请阅读文档。
我们还需要创建一个 requirements.txt
文件,并在其中添加 fastai
,这样该库就会在我们的服务器上安装。
所以现在只剩下将所有内容推送到 HuggingFace Git 仓库。
git add * git commit -am 'Cuttest Dogs 应用的第一个版本'git push
您可以在 GitHub 上找到完整的代码。
在推送文件之后,返回到 HuggingFace Space,您将看到类似的图片显示构建过程。如果一切正常,您的应用程序将在几分钟内运行起来。
如果出现任何问题,您将看到一个堆栈跟踪。然后您需要返回到您的代码中,修复错误,推送一个新版本,并等待几分钟。
它正在运行
现在我们可以使用真实的照片来使用这个模型,例如,验证我的家人的狗是否真的是柯基犬。

今天我们经历了构建深度学习应用的整个过程:从获取数据集和训练模型到编写和部署 Web 应用程序。希望您能够完成本教程,并且现在可以在生产环境中测试您的精彩模型。
非常感谢您阅读本文。希望对您有所启发。如果您有任何后续问题或评论,请在评论区留言。同时,欢迎分享您的应用链接。