首页
/ TensorFlow Models / DELF 地标检测快速上手:用预训练 Faster-RCNN 检测器在 Oxford 数据集上定位地标

TensorFlow Models / DELF 地标检测快速上手:用预训练 Faster-RCNN 检测器在 Oxford 数据集上定位地标

2026-09-06 18:15:10作者:翟萌耘Ralph

本文是 TensorFlow Model Garden 中 DELF(Deep Local and Global Image Features)项目的地标检测(landmark detection)实践指南。它以仓库中的 DETECTION.md 为主干,讲解如何安装 DELF 库、准备 Oxford 建筑图像、下载在 Google Landmark Boxes 上预训练的检测器,并借助 extract_boxes.py 一键完成地标区域检测与可视化。读完本文,你将能够在自己的图像清单上运行基于 Faster-RCNN 或 MobileNet-SSD 的检测模型,输出归一化坐标的检测框文件(.boxes),并生成带框标注的 _viz.jpg 预览图,为后续的 DELF 特征提取、区域聚合检索(Detect-to-Retrieve)等任务打好前置准备。

一、地标检测在 DELF 生态中的位置

research/delf/README.md 可知,DELF 项目围绕四篇论文的研究成果构建代码:DELF(ICCV'17)、Detect-to-Retrieve(CVPR'19)、DELG(ECCV'20)以及 Google Landmarks Dataset v2(CVPR'20)。其中**检测(detection)**是 Detect-to-Retrieve 方法的基础环节——先用目标检测模型在查询图像中定位"地标"出现的区域,再针对这些区域做局部/全局特征提取与聚合,从而提升实例级识别与图像检索的效果。

该项目发布了两个在 Google Landmark Boxes 数据集上预训练的检测器模型(见 README 的 Pre-trained models 小节):

  • Faster-RCNN 检测器:下载包为 d2r_frcnn_20190411.tar.gz,这是 DETECTION.md 默认使用的模型;
  • MobileNet-SSD 检测器:下载包为 d2r_mnetssd_20190411.tar.gz,更轻量,README 中说明两者的使用指令完全通用,可无缝切换。

DETECTION.md 描述的就是"快速开始(Quick start):地标检测"——它是一个端到端的最小可运行示例:用两张来自 Oxford buildings 数据集的图片,验证上述检测器能输出高质量的地标框。

二、环境准备:安装 DELF 库

要运行本示例,首先需要正确安装 DELF 库。仓库中的 research/delf/INSTALL_INSTRUCTIONS.md 提供了两种方式。

2.1 一键安装脚本

官方推荐在 64 位 Linux 上使用一键脚本:

# From models/research/delf/delf/python/training
bash install_delf.sh

脚本依次完成:安装 TensorFlow 2.2(CPU/GPU)、从源码安装 TF-Slim、下载 protoc 并编译 DELF 的 Protocol Buffers、安装 matplotlib/numpy/scikit-image/scipy/python3-tk、安装 TensorFlow Object Detection API、最后安装 DELF 包。

2.2 手工分步安装

如果不方便运行脚本,也可按下列步骤手工安装(均以 research/delf 目录为工作起点):

# 1) TensorFlow(Python 3.6+)
pip3 install 'tensorflow>=2.2.0'        # GPU: tensorflow-gpu>=2.2.0

# 2) TF-Slim 需从源码安装(避免旧版本依赖已废弃的 tf.contrib)
git clone git@github.com:google-research/tf-slim.git
cd tf-slim && pip3 install .

# 3) 下载 protoc(>= 3.3),然后编译 DELF 的 proto 文件
# 从 research/delf/ 目录执行:
${PATH_TO_PROTOC?}/bin/protoc delf/protos/*.proto --python_out=.

# 4) Python 依赖
pip3 install matplotlib numpy scikit-image scipy
sudo apt-get install python3-tk

# 5) 安装 DELF 包(若权限不足可加 sudo,必要时去掉 -e)
pip3 install -e .                       # 在 research/delf/ 目录下执行

安装完成后,用如下命令自检:

python3 -c 'import delf'

若没有报错即表示 DELF 包加载成功。DELF 的 proto 位于 research/delf/delf/protos,其中 box.proto 负责检测框的序列化格式、delf_config.proto 负责特征提取配置,均为编译依赖项。

三、准备图像:下载 Oxford 建筑数据集并生成检测清单

为了演示检测器用法,DETECTION.md 建议下载 Oxford buildings dataset。下载与解压的具体指令在 research/delf/EXTRACTION_MATCHING.md 的 "Download Oxford buildings dataset" 小节中给出:把数据集解压到 delf/python/examples/data/oxford5k_images/ 目录下即可。

随后,在示例目录 delf/python/examples/ 中创建检测图像清单 list_images_detector.txt,每一行写一个图像路径:

# From tensorflow/models/research/delf/delf/python/examples/
echo data/oxford5k_images/all_souls_000002.jpg >> list_images_detector.txt
echo data/oxford5k_images/all_souls_000035.jpg >> list_images_detector.txt

从源码看,该清单的解析逻辑位于 extract_boxes.py_ReadImageList():它逐行读取文件并去除行尾空白,因此每行一个图像路径是最基本的格式要求;同时脚本顶部 docstring 明确说明"图像必须为 JPG 格式"。这份清单与 DELF 特征提取阶段使用的 list_images.txt(对应 EXTRACTION_MATCHING.md 中的示例)结构完全一致,方便后续将检测与特征提取串联成流水线。

四、下载预训练检测模型

接着下载 Faster-RCNN 检测器模型到 parameters/ 目录:

# From tensorflow/models/research/delf/delf/python/examples/
mkdir parameters && cd parameters
wget http://storage.googleapis.com/delf/d2r_frcnn_20190411.tar.gz
tar -xvzf d2r_frcnn_20190411.tar.gz
cd ..

下载并解压后得到的是一个导出的 SavedModel 目录(例如 d2r_frcnn_20190411/),这正是 detector.pyMakeDetector(model_dir) 通过 tf.saved_model.load(model_dir) 加载的对象。

说明:DETECTION.md 特别注明,上述为 Faster-RCNN 版本;项目还同时发布 MobileNet-SSD 版本(d2r_mnetssd_20190411.tar.gz),下载链接见 README 的 Pre-trained models 小节。两种模型在下面的指令中均可无缝使用——只需把 --detector_path 指向对应的解压目录。

五、运行检测命令:extract_boxes.py 的参数与输出

一切就绪后,在 delf/python/examples/ 目录执行以下命令,即会以 0.8 的置信度阈值对两张 all_souls 图像检测地标框,并输出可视化结果:

# From tensorflow/models/research/delf/delf/python/examples/
python3 extract_boxes.py \
  --detector_path parameters/d2r_frcnn_20190411 \
  --detector_thresh 0.8 \
  --list_images_path list_images_detector.txt \
  --output_dir data/oxford5k_boxes \
  --output_viz_dir data/oxford5k_boxes_viz

5.1 命令行参数详解

对照 extract_boxes.py 底部的 argparse 定义,各参数的含义与默认值如下:

参数 默认值 含义(依据源码注释)
--detector_path /tmp/d2r_frcnn_20190411/ 导出的检测模型(SavedModel)路径
--detector_thresh 0.0 检测阈值,置信度得分低于该值的框不会被返回
--list_images_path list_images.txt 待检测图像清单文件路径,每行一个图像
--output_dir test_boxes 检测框输出目录;每张图像一个 .boxes 文件(同名、扩展名替换)
--output_viz_dir ''(空) 可选;若设置,则生成"检测框叠加在图像上"的可视化并保存,文件名带 _viz.jpg 后缀

本示例把阈值设为 0.8,意味着只保留检测置信度 不低于 0.8 的框;实际使用时可根据精度/召回需求调低(如默认 0.0 则保留全部框)。输出时,程序会把 .boxes 框文件写入 data/oxford5k_boxes,把可视化图片写入 data/oxford5k_boxes_viz

5.2 预期输出效果

运行结束后,data/oxford5k_boxes_viz 目录下会生成两张可视化图片,其效果与仓库中随附的示例结果一致——红色矩形框清晰地覆盖了画面中的地标建筑主体区域:

牛津地标建筑检测示例(正面视角,红色框覆盖建筑主体)

牛津地标建筑群检测示例(全景视角,红色框界定地标区域)

六、源码级原理:检测主流程拆解

理解示例的运行机制,有助于把检测步骤平滑嵌入你自己的检索/识别流程。核心代码集中在两个文件中:extract_boxes.py(主流程)与 detector.py(模型封装)。

6.1 模型加载与张量剪枝

detector.py 中的 MakeDetector() 把导出的 SavedModel 剪枝为一个"输入—输出"最小接口:

model = tf.saved_model.load(model_dir)
feeds = ['input_images:0']
fetches = ['detection_boxes:0', 'detection_scores:0', 'detection_classes:0']
model = model.prune(feeds=feeds, fetches=fetches)

即模型的输入张量是 input_images:0(uint8 的 RGB 批图像,形状为 (batch, height, width, 3)),返回三个输出:detection_boxesdetection_scoresdetection_classes。由此可以推断:DELF 项目发布的预训练检测器统一遵循这一张量命名约定,extract_boxes.py 无需关心具体是 Faster-RCNN 还是 MobileNet-SSD,这正是"两种模型指令无缝通用"的底层原因。

6.2 主循环:过滤、落盘与可视化

extract_boxes.pymain() 按如下流程工作:

  1. 读取图像清单,统计待处理数量,并创建 --output_dir / --output_viz_dir(若未存在);
  2. 通过 detector.MakeDetector(cmd_args.detector_path) 构造检测函数 detector_fn
  3. 逐张图像处理:用 utils.RgbLoader() 读图并扩展为 batch 维度后送入 detector_fn,得到 (boxes, scores, class_indices)
  4. 调用 _FilterBoxesByScore(),仅保留 scores[i] >= detector_thresh 的框及其得分、类别索引;
  5. box_io.WriteToFile() 把筛选结果写入 .boxes 文件;若设置了 --output_viz_dir,再调用 _PlotBoxesAndSaveImage() 叠加绘制红色(循环色 r/y/b/m/k/g/c/w)矩形框并保存为 _viz.jpg
  6. 每处理 100 张图像打印一次进度日志,便于在超大数据集上观察运行状态。

值得注意的两个工程细节:

  • 断点续跑:程序在处理每张图前会检查对应 .boxes 文件是否已存在,存在则打印 Skipping ... 并跳过。这在批量检测时非常实用——中断后重跑不会重复计算已完成的图像;
  • 归一化坐标:检测器输出的框坐标是归一化后的 [top, left, bottom, right](即 [ymin, xmin, ymax, xmax],取值约在 [0,1])。可视化时 _PlotBoxesAndSaveImage() 需要将归一化坐标乘上图像的实际高、宽(scaled_box = [box[0]*height, box[1]*width, ...])才能正确落位。

6.3 .boxes 输出文件格式:box.proto 与 box_io

检测框文件的格式由 box.proto 定义:一个 Boxes 消息包含多个 Box,每个 Box 有 6 个字段:

字段 说明
ymin / xmin / ymax / xmax 归一化框坐标,对应 [top, left, bottom, right]
score 检测得分,通常越高越可信
class_index 框对应的类别索引

读写接口位于 box_io.pyWriteToFile() 把 numpy 数组(boxes: [N,4]scores: [N]class_indices: [N])序列化为 Boxes proto 二进制写入文件,ReadFromFile() 则执行反向解析;两者均基于 tf.io.gfile,因此天然支持远端存储路径。这份 .boxes 输出正是后续 Detect-to-Retrieve 阶段"对检测区域提取局部特征"的输入,相关聚合、索引与检索脚本的说明可见 README 的代码总览中对 delf/python/detect_to_retrieve 子目录的介绍。

七、常见问题排查

matplotlib 无显示环境报错

在无图形界面的服务器(如纯 SSH 环境)上运行时,matplotlib 可能报出类似 no display name and no $DISPLAY environment variable 的错误。DETECTION.md 给出的解决方案是:在 ~/.config/matplotlib/matplotlibrc 文件中加入一行,强制使用非交互后端:

backend : Agg

这样 plt.savefig() 即可在无显示器的情况下正常把可视化图片落盘。

其他依赖提示

DELF 特征提取/匹配流程还可能遇到 scikit-image 相关异常,EXTRACTION_MATCHING.md 提到可用 pip3 install -U scikit-image 升级到 0.14.1 以上版本解决;若 pip3 install -e . 出现安装问题,可尝试去掉 -e 选项或为命令添加 sudo(详见 INSTALL_INSTRUCTIONS.md 的 Troubleshooting 小节)。

八、下一步:把检测接入检索流水线

完成上述检测后,你已得到每张图像的地标框(.boxes)。在 DELF 的整体思路中,这通常只是第一步:后续可以按照 EXTRACTION_MATCHING.md 对框内区域提取 DELF 局部特征并进行图像匹配,或者参考 README 中关于 DELG、Detect-to-Retrieve、GLDv2 baseline 的指引,使用同一批检测框参与区域特征聚合、建库检索与重排,从而把"定位地标"升级为完整的实例级识别与检索系统。文中展示的 extract_boxes.py 支持任意数量的 JPG 图像清单、支持阈值调节与断点续跑,可作为你自定义检测数据集的起点工具。

登录后查看全文
热门项目推荐
相关项目推荐

项目优选

收起
kernelkernel
deepin linux kernel
C
33
18
ops-transformerops-transformer
本项目是CANN提供的transformer类大模型算子库,实现网络在NPU上加速计算。
C++
1.14 K
2.74 K
pytorchpytorch
作为 Ascend for PyTorch 社区的核心组件,TorchNPU 是昇腾专为 PyTorch 打造的深度学习适配插件,使 PyTorch 框架能够直接调用昇腾 NPU,为开发者提供昇腾 AI 处理器的超强算力。
Python
857
1.35 K
docsdocs
暂无描述
Markdown
897
5.81 K
kernelkernel
openEuler内核是openEuler操作系统的核心,既是系统性能与稳定性的基石,也是连接处理器、设备与服务的桥梁。
C
531
595
ops-nnops-nn
本项目是CANN提供的神经网络类计算算子库,实现网络在NPU上加速计算。
C++
920
1.84 K
jiuwenswarmjiuwenswarm
JiuwenSwarm 是一款基于openJiuwen开发的智能AI Agent,它能够将大语言模型的强大能力,通过你日常使用的各类通讯应用,直接延伸至你的指尖。
Python
3.63 K
1.02 K
ops-mathops-math
本项目是CANN提供的数学类基础计算算子库,实现网络在NPU上加速计算。
C++
1.36 K
1.46 K
cann-learning-hubcann-learning-hub
CANN 学习中心仓,支持在线互动运行、边学边练,提供教程、示例与优化方案,一站式助力昇腾开发者快速上手。
Jupyter Notebook
1.02 K
518
AscendNPU-IRAscendNPU-IR
AscendNPU-IR是基于MLIR(Multi-Level Intermediate Representation)构建的,面向昇腾亲和算子编译时使用的中间表示,提供昇腾完备表达能力,通过编译优化提升昇腾AI处理器计算效率,支持通过生态框架使能昇腾AI处理器与深度调优
C++
547
389