视频创作者通常需要从大量的素材中找到自己需要的片段来剪辑,可真是心累。我们的社区用户:作为 Up 主的王德福抓住这一需求和他的小伙伴 Arthur,使用 Jina 搭建起一个跨模态视频搜索引擎,轻松搜索视频片段。
作为一个前端程序员兼 Up 主,平时拍摄与搜集的素材库实在太多,在视频制作时,想快速找出想要的视频片段太费劲了,那么有什么办法能节省翻找素材的时间呢?1. 通过给每段视频素材打上标签?太繁琐,并且太耗时。2. 通过检索字幕去查找出对应的画面?但只能是人物说了那句话才行,没有说话的画面就无法检索,得到的结果太局限了。而我想要这个工具能够实现:输入对画面的描述,就能得到视频素材的片段。
既要理解自然语言,又要理解视频内容,听起来不像是简单的任务......我了解到 OpenAI 开源的 CLIP 模型,它能够完成图像与文本的匹配任务。也就是说,我们可以通过利用 CLIP 模型实现用描述性的文本,而非关键词搜索到图像,而视频又可以看作是一帧帧的图像。因此,借助强大的 CLIP 模型,我可以实现一个基于语义的,而非基于关键词的搜索引擎。不同于传统的 ES 全文搜索,我不需要给每个视频素材人为地打上标签,也不需要利用 OCR、正则去做匹配。只需通过 AI 模型,优雅地提取图像和文本的特征向量,通过计算两者的向量相似度,就能返回到我想要的结果,听起来相当完美。一开始,我尝试用纯 Python + CLIP 模型实现了初版方案。
但当时遇到了一些棘手的问题,即向量无法存储。由于没有合适的数据存储方式,做数据库也需要一定开发量,因此我每次都需要重新计算一遍向量,繁琐、耗时又费力。并且由于项目无法独立部署,导致无法通过前端页面来承载视频片段搜索的能力。而这些都有太多开发成本,对于一个我这样的前端开发者来说,将大部分精力都花费在不熟悉的工作上,太得不偿失了。
因此我尝试在开源社区寻找合适的解决方案,发现了 Jina,作为一个专注于神经网络搜索的 AI 框架,正好提供了我原方案里所需的能力。于是,我转变了思路,使用 Jina + CLIP 实现从文本到视频片段的搜索系统。
如果用纯 Python 的方式表示一个视频,需要自己建立一个哈希表,包括 embedding 、图片的存储,结构会很难看。
但 Jina 里的 DocArray 能把这个存储变得非常结构化,不管有多少帧视频,都可以在一个 Document 里做封装。而且可以有不同的层级结构,比方说第一层用于存储整体的视频,第二层用于存储视频下不同的帧......切换不同的模态时,也可以设置成顶层是一整段话,第二层是一个句子,第三层是一个单词。不仅可以通过每个单词进行搜索,也可以通过每句话进行搜索,这样搜索颗粒度选择就更多,搜索结果也会更加丰富。
本项目的业务流程分为两大部分:视频的上传、搜索。包括数据向量化、向量相似度比较、结果的召回三个主要流程。具体如下图所示。首先上传视频,调用 Jina 的 Video Loader,对视频抽帧,并将数据存储到 DocArray 的块里。在 Encode image 里生成向量,最后存储到 DocArray 的 Index 。在搜索时,在 Index 里会对向量的相似度进行打分,最后依据分数排序,得到返回的结果。在定义服务上,由于 Jina 的工程师已经把逻辑都抽象出来,所以开发时只需要通过一套配置文件就能起整个服务,只需要定义需要哪些模块。就像搭积木一样,把每一个模块搭起来,不用去考虑服务之间的连接和通信。只需要专注如何实现自己的业务,不用操心架构实现的事情。有别于传统的搜索引擎的关键词匹配,本文实现的搜索引擎是基于语义的搜索。比如远处的天空,天上有云,云是金黄色的,你或许不知道这个画面的关键词是晚霞。当你想要得到这个画面时,就可以用基于语义的搜索引擎去找到。如图,输入“几个戴着麻将面具的人”,就能得到如下的视频片段。
repo:https://github.com/ArthurKing01/jina-clip
活动预告今晚 8 点,Jina AI 社区将邀请本项目开发者参与面向中文社区的首次Office Hours 活动,分享他的开发心得。请大家点击链接加入会议!
https://meeting.tencent.com/dm/5Rg6PoHLxhqW
后续 Jina AI 社区将联合 DataWhale 社区,结合本项目,打造多模态、跨模态应用的系列课程。请大家持续关注!Datawhale 是一个专注于 AI 领域的开源组织,致力于帮助学习者更好地成长。关注公众号,了解更多 AI 课程。
神经搜索、深度学习、推荐系统
教程、Demo、干货分享
扫码备注加入讨论组