本项目完成了 facebook/dinov2-giant 在昇腾 NPU 上的适配与验证,包括推理脚本、性能评测和精度对比。
DINOv2 是 Meta 发布的自监督视觉 Transformer 模型,可用于图像特征提取、密集预测等下游任务。dinov2-giant 为最大尺寸版本,参数量约 11 亿。
本项目基于 transformers 库,通过 model.to("npu") 将模型迁移至昇腾 NPU 执行推理,无需修改第三方库源码。
| 组件 | 版本 |
|---|---|
| PyTorch | 2.9.0+cpu |
| torch-npu | 2.9.0.post1+gitee7ba04 |
| transformers | 最新 |
| Python | 3.11 |
| CANN | 8.5.1 |
| NPU 数量 | 2 |
python3 -m atomgit download hf_mirrors/facebook/dinov2-giant -d /opt/atomgit/weights/facebook/dinov2-giantmodelscope download --model facebook/dinov2-giant --local_dir /opt/atomgit/weights/facebook/dinov2-giant原始权重来源:facebook/dinov2-giant
pip install torch torch-npu transformers Pillow若 pip install 后出现
vllm-ascend兼容性警告,而当前项目不依赖 vllm-ascend,可忽略。
以下为本次推理使用的样例图片,通过 wget 从 COCO 验证集下载:
wget http://images.cocodataset.org/val2017/000000039769.jpg -O assets/000000039769.jpg
inference.py 完整代码如下:
import torch
from PIL import Image
from transformers import AutoImageProcessor, AutoModel
device = "npu"
model_name = "/opt/atomgit/weights/facebook/dinov2-giant"
url = "./assets/000000039769.jpg"
image = Image.open(url)
processor = AutoImageProcessor.from_pretrained(model_name)
model = AutoModel.from_pretrained(model_name)
model.eval()
model = model.to(device)
print(f"Model loaded to device({device})")
inputs = processor(images=image, return_tensors="pt").to(device)
with torch.no_grad():
outputs = model(**inputs)
last_hidden_states = outputs.last_hidden_state
cls_token = last_hidden_states[:, 0, :] # [1, 1536]
patch_tokens = last_hidden_states[:, 1:, :] # [1, 256, 1536]
print(f"{cls_token.shape=}")
print(f"{patch_tokens.shape=}")python3 inference.pyUsing a slow image processor as `use_fast` is unset and a slow processor was saved with this model. `use_fast=True` will be the default behavior in v4.52, even if the model was saved with a slow processor. This will result in minor differences in outputs. You'll still be able to use a slow processor with `use_fast=False`.
Model loaded to device(npu)
cls_token.shape=torch.Size([1, 1536])
patch_tokens.shape=torch.Size([1, 256, 1536])模型成功加载到 NPU 并完成图像特征提取,输出 CLS token 形状为 [1, 1536],patch tokens 形状为 [1, 256, 1536]。
运行 benchmark.py:
python3 benchmark.py每个 batch size 均运行 100 次,结果如下:
| Batch Size | 总耗时 (s) | 单图延迟 (ms/img) | 吞吐率 (img/s) |
|---|---|---|---|
| 1 | 2.335 | 23.352 | 42.82 |
| 2 | 3.658 | 18.291 | 54.67 |
| 4 | 5.409 | 13.522 | 73.95 |
| 8 | 10.449 | 13.061 | 76.56 |
单图延迟 = 总耗时 / 运行次数 / batch_size * 1000
吞吐率 = 运行次数 * batch_size / 总耗时
运行 accuracy.py,对比 NPU 与 CPU 推理输出:
python3 accuracy.py本次精度对比采用相对误差(Relative Error),计算公式为:
Relative Error = mean(|output_cpu - output_npu|) / mean(|output_cpu|) * 100%其中:
output_cpu 为 CPU 推理输出(float32)output_npu 为 NPU 推理输出转回 CPU 后的结果(float32)CLS token 和 patch tokens 独立计算| 对比项 | 相对误差 |
|---|---|
| CLS token | 0.108461% |
| Patch tokens | 0.730139% |
| 最大误差 | 0.730139% |
结论:精度验证通过(最大误差 < 1%)
use_fast 相关提示,可按照提示在 AutoImageProcessor.from_pretrained 中显式传入 use_fast=False 或 use_fast=True。torch.compile,无需设置 TORCH_COMPILE_DISABLE 环境变量。output/ 目录下的 inference.log、benchmark.log 和 accuracy.log。