如何高效合并两个按通道归一化选择的张量
技术百科
花韻仙語
发布时间:2026-01-18
浏览: 次 本文介绍一种基于布尔掩码的向量化方法,替代原始双层循环,实现对两个同形状3d/4d张量按通道l2范数比较后逐通道选取较大者,大幅提升计算效率。
在深度学习中,常需根据通道级统计量(如L2范数)对多个特征图进行融合决策。原始实现使用嵌套 for 循环遍历 batch 和 channel 维度,虽逻辑清晰但严重阻碍 GPU 并行能力,导致训练/推理速度显著下降。
更优解是利用 PyTorch 的广播机制与高级索引(advanced indexing),将条件判断和赋值完全向量化。核心思路如下:
- 计算通道范数:对输入张量 x 和 y 沿空间维度(H, W)计算 L2 范数,得到形状为 (B, C) 的二维张量;
- 生成布尔掩码:通过比较 x_norm >= y_norm 直接获得 (B, C) 布尔张量 condition;
-
向量化赋值:利用布尔掩码对四维张量 z、x、y 进行高级索引——z[condition] = x[condition] 会自动将 condition 广播至所有空间位置,等价于“对
每个满足条件的 (b,c),复制 x[b,c,:,:] 到 z[b,c,:,:]”。
✅ 完整优化代码如下:
import torch # 示例输入(实际中为你的特征张量) x = torch.randn(16, 64, 32, 32) # B, C, H, W y = torch.randn(16, 64, 32, 32) # 步骤1:计算通道L2范数(保留B,C维度) x_norm = torch.norm(x, dim=(2, 3)) # shape: (B, C) y_norm = torch.norm(y, dim=(2, 3)) # 步骤2:构建广播兼容的布尔掩码 condition = x_norm >= y_norm # shape: (B, C),dtype=torch.bool # 步骤3:向量化赋值(无需循环!) z = torch.where(condition.unsqueeze(-1).unsqueeze(-1), x, y) # 或等价写法(显式索引): # z = torch.zeros_like(x) # z[condition] = x[condition] # z[~condition] = y[~condition]
⚠️ 注意事项:torch.where() 是更推荐的方式(第3行),它天然支持广播,且一行完*部赋值,语义更清晰、内存更友好;若使用 z[condition] = x[condition],需确保 condition 为二维布尔张量,PyTorch 会自动将其广播到 (B, C, H, W) 空间,但要求 x 和 y 形状严格一致;该方法假设 x 和 y 具有完全相同的形状(B, C, H, W),否则需先对齐尺寸(如 padding 或 interpolate);对于超大 batch 或 channel 数,可进一步用 torch.cuda.amp.autocast() 配合半精度加速范数计算。
此方案将时间复杂度从 O(B×C×H×W) 的显式循环降为 O(B×C + B×C×H×W) 的向量化操作,在 GPU 上通常获得 10–100 倍加速,是 PyTorch 中“用算子代替循环”的典型实践。
# 深度学习
# 将其
# 多个
# 更清晰
# 循环
# channel
# 则需
# 遍历
# for
# 布尔
# 掩码
# padding
# pytorch
# 中为
# 完全相同
# batch
# 降为
相关栏目:
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
AI推广<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
SEO优化<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
技术百科<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
谷歌推广<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
百度推广<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
网络营销<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
案例网站<?muma echo $count; ?>
】
<?muma
$count = M('archives')->where(['typeid'=>$field['id']])->count();
?>
【
精选文章<?muma echo $count; ?>
】
相关推荐
- Windows11怎么自定义任务栏_Windows
- c++ try_emplace用法_c++ map
- MAC的“接续互通”功能无法使用怎么办_MAC检查
- mac怎么安装adb_MAC配置Android A
- Win10如何备份驱动程序_Win10驱动备份步骤
- Python性能剖析高级教程_cProfileLi
- 如何在 Laravel 中通过嵌套关联关系进行 o
- Win11怎么查看电脑配置_Win11硬件配置详细
- 如何在Golang中使用闭包_封装变量与函数作用域
- php打包exe后无法写入文件_权限问题解决方法【
- Windows 11登录时提示“用户配置文件服务登
- Win11怎么硬盘分区 Win11新建磁盘分区详细
- Win11怎么设置系统还原_Windows11系统
- php做exe支持多线程吗_并发处理实现方式【详解
- Windows电脑如何截屏?(四种快捷方法)
- 如何在 IIS 上为 ASP.NET 6 应用排除
- Win11怎样安装微信开发者工具_Win11安装开
- VSC怎样在Linux运行PHP_Ubuntu系统
- C#如何在一个XML文件中查找并替换文本内容
- 如何用正则表达式精确匹配最多含一个换行符的起止片段
- 如何在Golang中修改数组元素_通过指针实现原地
- 如何在JavaScript中动态拼接PHP的bas
- Go 中 defer 语句在 goroutine
- Windows10如何更改盘符名称_Win10重命
- Win10怎样安装Excel数据分析工具_Win1
- 如何在 VS Code 中正确配置并使用 NumP
- ACF 教程:正确更新嵌套在多层 Group 字段
- Win10怎样安装PPT模板_Win10安装PPT
- Python异步编程高级项目教程_asyncio协
- Win10如何卸载微软拼音输入法 Win10只保留
- Win11怎么设置闹钟_Windows 11时钟应
- Mac如何与安卓手机传文件_Mac和Android
- Win11怎么关闭应用权限_Windows11相机
- 如何使用Golang进行HTTP服务性能测试_测量
- Win10如何卸载Skype_Win10卸载Sky
- Win10系统字体模糊怎么办_Windows10高
- Python迭代器生成器进阶教程_节省内存与懒加载
- Win11怎么设置虚拟内存最佳大小_Windows
- Windows10电脑怎么设置文件权限_Win10
- Windows蓝屏错误0x00000023怎么修复
- Win11怎么设置开机自动连接宽带_Windows
- Win11怎么关闭定位服务 Win11禁止应用获取
- Win11怎么设置DNS服务器_Windows11
- MySQL 中使用 IF 和 CASE 实现查询字
- Win10如何更改开机密码_Windows10登录
- c++如何连接Redis c++ hiredis库
- php485在php5.6下能用吗_php485旧
- Win10怎样卸载TeamViewer_Win10
- 如何使用Golang实现Web表单数据绑定_自动映
- 如何在Golang中处理URL参数_Golang


QQ客服