# 构建一个美食推荐网页应用
在本课中,您将使用之前课程中学到的一些技术以及贯穿整个系列的美食数据集,构建一个分类模型。此外,您还将构建一个小型网页应用来使用保存的模型,并利用 Onnx 的网页运行时。
机器学习最实用的用途之一是构建推荐系统,今天您可以迈出这一方向的第一步!
[](https://youtu.be/17wdM9AHMfg "应用机器学习")
> 🎥 点击上方图片观看视频:Jen Looper 使用分类美食数据构建网页应用
## [课前测验](https://ff-quizzes.netlify.app/en/ml/)
在本课中,您将学习:
- 如何构建模型并将其保存为 Onnx 模型
- 如何使用 Netron 检查模型
- 如何在网页应用中使用您的模型进行推理
## 构建您的模型
构建应用型机器学习系统是将这些技术应用于业务系统的重要部分。通过使用 Onnx,您可以在网页应用中使用模型(因此在需要时也可以离线使用)。
在[之前的课程](../../3-Web-App/1-Web-App/README.md)中,您构建了一个关于 UFO 目击事件的回归模型,将其“pickle”保存,并在 Flask 应用中使用。虽然这种架构非常有用,但它是一个全栈 Python 应用,而您的需求可能包括使用 JavaScript 应用。
在本课中,您可以构建一个基于 JavaScript 的基础推理系统。不过,首先需要训练一个模型并将其转换为 Onnx 格式。
## 练习 - 训练分类模型
首先,使用我们之前清理过的美食数据集训练一个分类模型。
1. 首先导入有用的库:
```python
!pip install skl2onnx
import pandas as pd
```
您需要 '[skl2onnx](https://onnx.ai/sklearn-onnx/)' 来帮助将 Scikit-learn 模型转换为 Onnx 格式。
1. 然后,像之前课程中一样使用 `read_csv()` 读取 CSV 文件来处理数据:
```python
data = pd.read_csv('../data/cleaned_cuisines.csv')
data.head()
```
1. 删除前两列不必要的数据,并将剩余数据保存为 'X':
```python
X = data.iloc[:,2:]
X.head()
```
1. 将标签保存为 'y':
```python
y = data[['cuisine']]
y.head()
```
### 开始训练流程
我们将使用具有良好准确性的 'SVC' 库。
1. 从 Scikit-learn 导入相关库:
```python
from sklearn.model_selection import train_test_split
from sklearn.svm import SVC
from sklearn.model_selection import cross_val_score
from sklearn.metrics import accuracy_score,precision_score,confusion_matrix,classification_report
```
1. 分离训练集和测试集:
```python
X_train, X_test, y_train, y_test = train_test_split(X,y,test_size=0.3)
```
1. 像之前课程中一样构建一个 SVC 分类模型:
```python
model = SVC(kernel='linear', C=10, probability=True,random_state=0)
model.fit(X_train,y_train.values.ravel())
```
1. 现在,测试您的模型,调用 `predict()`:
```python
y_pred = model.predict(X_test)
```
1. 打印分类报告以检查模型质量:
```python
print(classification_report(y_test,y_pred))
```
如我们之前所见,准确性很好:
```output
precision recall f1-score support
chinese 0.72 0.69 0.70 257
indian 0.91 0.87 0.89 243
japanese 0.79 0.77 0.78 239
korean 0.83 0.79 0.81 236
thai 0.72 0.84 0.78 224
accuracy 0.79 1199
macro avg 0.79 0.79 0.79 1199
weighted avg 0.79 0.79 0.79 1199
```
### 将模型转换为 Onnx
确保使用正确的张量数量进行转换。此数据集列出了 380 种食材,因此您需要在 `FloatTensorType` 中注明该数量:
1. 使用张量数量 380 进行转换。
```python
from skl2onnx import convert_sklearn
from skl2onnx.common.data_types import FloatTensorType
initial_type = [('float_input', FloatTensorType([None, 380]))]
options = {id(model): {'nocl': True, 'zipmap': False}}
```
1. 创建 onx 并保存为文件 **model.onnx**:
```python
onx = convert_sklearn(model, initial_types=initial_type, options=options)
with open("./model.onnx", "wb") as f:
f.write(onx.SerializeToString())
```
> 注意,您可以在转换脚本中传递[选项](https://onnx.ai/sklearn-onnx/parameterized.html)。在本例中,我们将 'nocl' 设置为 True,将 'zipmap' 设置为 False。由于这是一个分类模型,您可以选择移除 ZipMap,它会生成一个字典列表(不必要)。`nocl` 指的是模型中是否包含类别信息。通过将 `nocl` 设置为 'True' 来减小模型的大小。
运行整个笔记本后,您将构建一个 Onnx 模型并将其保存到此文件夹中。
## 查看您的模型
Onnx 模型在 Visual Studio Code 中不太直观,但有一个非常好的免费软件,许多研究人员使用它来可视化模型,以确保模型构建正确。下载 [Netron](https://github.com/lutzroeder/Netron) 并打开您的 model.onnx 文件。您可以看到您的简单模型被可视化,包含 380 个输入和分类器:

Netron 是一个查看模型的有用工具。
现在您可以在网页应用中使用这个简洁的模型了。让我们构建一个应用,当您查看冰箱并试图决定如何利用剩余食材制作某种美食时,它会派上用场。
## 构建推荐网页应用
您可以直接在网页应用中使用您的模型。这种架构还允许您在本地运行,甚至在需要时离线运行。首先,在存储 `model.onnx` 文件的同一文件夹中创建一个 `index.html` 文件。
1. 在此文件 _index.html_ 中,添加以下标记:
```html