这是indexloc提供的服务,不要输入任何密码
Skip to content

Conversation

@xinyanghuang7
Copy link
Contributor

再次感谢您优秀的项目。

此次更新中涵盖了自己的对该项目的思考以及一些优化:

1、image_special_token 的定义以及 image_ids 的定义。

这两部分的定义长度似乎不需要根据图像编码器编码出的patch长度进行重新计算。一个理想情况是可以指定一个特殊的token,当遇见该特殊token时,即插入图像patch。

但由于minimind词表中并未为特殊token预留位置,因此直接插入特殊的token不太可行。但可以统一将其指定为一个较短的复杂token,这次实现的是'image_special_token='<'*2+'>'*2, image_ids=[30]*2+[32]*2'(指定一个正常对话不会出现的token)。这样,也不需要因为不同的图像编码器而不断改变这两个参数。

较短的token也能够为之后的遍历搜索节省大量时间。

2、对之前图像插入token的位置检测进行了进一步的优化,同时解决了之前的一些bug,这个bug曾导致无法进行单图训练。

# 使用view来创建一个视图,便于处理滑动窗口
            tokens_view = tokens.unfold(1, len_image_ids, 1)  # 在第二维度创建滑动窗口
            # 检查每个滑动窗口是否与image_ids_tensor相等
            matches = (tokens_view == image_ids_tensor).all(dim=2)  # 对窗口中的每一行进行比较

用滑动窗口和字典进行储存加速之后检索以及插入的速度。

if i in image_indices:  # 直接从字典中获取
                        for start_idx, end_idx in image_indices[i]:
                            # 插入vision_proj特征
                            before = h[i][:start_idx, :]
                            after = h[i][end_idx + 1:, :]

bug区域具体是在这一行:

vision_proj = vision_proj.unsqueeze(0) if len(vision_proj.shape) == 3 else vision_proj

.unsqueeze(0) 应该是1而不是0,因为第一维是batchsize的维度,第二维表示图像数量。

3、添加了siglip-vit-b-16的参数选择。

在源代码的基础上,添加了新的图像编码器。由于siglip通常会将图像分割成196个token,因此可能会增加模型的计算量,但几乎不影响显存。

后续训练好的权重同样也会进行更新,此次提交包括了自己的一些思考。仅供您参考。如果您能提出建议或者是意见,我也是十分感激。

期待之后与您的交流!谢谢!

@xinyanghuang7
Copy link
Contributor Author

目前实现的版本在书写方面还有点潦草,请您见谅,这几天也会陆续修改过来~

谢谢!

@jingyaogong
Copy link
Owner

我pull了这个hxy分支,测试现在的 3-eval-chat.py 的结果是这样的
image

如果改成原来的special_token

lm_config = LMConfig(image_special_token='<'*25+'>'*25, image_ids=[30]*25+[32]*25)

image
一切正常。

为什么会这样?

  • 如果只是把占位符简单替换 那么输入会变成这样:
    image

  • 具体而言
    image

  • GPT模型预测下一个字符,产生这样的输出
    image

  • 也就是用户侧看到的输入和模型的输出完全不一致
    image

  • 也就是推理时,我们取输出结果的 [9, 10, 11, 12...] 的位置作为next token的输出不断接龙
    image


说白了

1、把一段token从图像占位符个数 M 转换到图像encoder tokens个数 N
2、从真实的图像tokens个数 N,在forward时需要重新转换到图像占位符个数 M

确保输入和输出本身是对称统一的,在内部完成这样的转换即可。

但是这里只进行了1,缺少2;

占位符最初也打算使用再做这样的计算,需要在forward阶段统计保存原始输入的占位符索引,计算输出时还需要考虑next token特性偏移1位...


秉承【奥卡姆剃刀】原则,最初觉得这样更加复杂的代码实现不划算,也不便于直白的理解,所以用和真实图像tokens相同长度的占位符,虽然这看起来不简洁,但实际上最简洁。

若考虑继续完善以上问题

1、可以保持现有的 '<'*25+'>'*25 简洁做法
2、也可以实现 "对称转换"

无论哪一种,都欢迎提交新的PR

这次PR其它有很多可取之处,例如索引加速和fix这个bug(由于发现优先级更高的bug所以我稍后会先在master分支fix它)

我会在新的提交后进行新的检查,给出新的回复!
有任何想法都可以继续交流!谢谢您的新的贡献,很棒!

Copy link
Owner

@jingyaogong jingyaogong left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

very good!谢谢!

@jingyaogong jingyaogong merged commit c115169 into jingyaogong:master Nov 3, 2024
@jingyaogong
Copy link
Owner

@xinyanghuang7

对了还有 3-eval_chat.py 此处
image

如果是
image
相当于输入两个空图推理,"找到image索引替换成image encoder的步骤" 就没有了

方便时可以测试效果~😊

@xinyanghuang7
Copy link
Contributor Author

感谢您的修正,后续还会对代码进行进一步的优化和调试,以及公开更多的训练权重。

十分感谢!

@jingyaogong
Copy link
Owner

感谢您的修正,后续还会对代码进行进一步的优化和调试,以及公开更多的训练权重。

十分感谢!

no thanks!

Misaki-Akeno pushed a commit to Misaki-Akeno/minimind-v-vla that referenced this pull request Sep 19, 2025
讨论、对之前代码优化以及添加Siglip编码器
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants