floor_plan_meshproject增加角度正则损失

news/2025/1/15 22:46:36/文章来源:https://www.cnblogs.com/sherioc/p/18673858

数据结构

data.x  #(128, 16)  16 = triangles(9) + confidence(7)
"""
每个元素
[x1, y1, z1, x2, y2, z2, x3, y3, z3, 
c_v1, c_v2, c_v3, c_e1, c_e2, c_e3, c_f]
"""
data.y  #(128)encoded_x #(128, 576)
encoded_x_conv # (2, 96, 576)
decoded_x_conv # (2, 96, 4)
decoded_x # (128, 4)

Angle_loss 计算

\[L_{\text{angle}} = p_{\text{merge}}^{\alpha} \times \min_{t \in \{90, 180, 270, 360\}} | \text{Angle}_{\text{merge}} - t | \]

\[Loss= w_1 L_{\text{classification}} + w_2 L_{\text{angle}} \]

1、朴素实现

data.x  #(num_triangles, 16) , 16 = triangles(9) + confidence(7)
# 每个元素
[x1, y1, z1, x2, y2, z2, x3, y3, z3, 
c_v1, c_v2, c_v3, c_e1, c_e2, c_e3, c_f]data.y  #(128)

image-20250115223828926

# 每个 triangle 的信息(添加了角)
data.x_with_angle
{face_idx: i,vertices: [(x1, y1, z1), (x2, y2, z2), (x3, y3, z3)],angles: [α1, α2, α3]
}# 获取所有 room triangles#取它们的顶点(去重)(x1, y1, z1): {vertices: (x1, y1, z1),faces_idx: [1, 2, 3, ...], # 包含该顶点的room面idxangle: [α1, α2, α3, ...], # 该顶点在该面的angledecoded_x: [[p_11, p_12, p_13, p_14], [p_21, p_22, p_23, p_24], [p_31, p_32, p_33, p_34], ...]
}# 计算angle_merge, p_merge# loss 计算
朴素实现
def angle_loss_torch(self, data, decoded_x):"""doc: 计算角度正则化损失return: total_angle_loss: 角度正则化损失"""# 1. 选出所有最大分类概率为room的三角形(及其索引)softmax_decoded_x = torch.nn.functional.softmax(decoded_x, dim=1)  # 使用softmax得到不同分类的概率max_probs, max_indices = torch.max(softmax_decoded_x, dim=1)room_indices = torch.where(max_indices == 2)[0]# 获取每个面的三个角 data.x_with_anglevertices = data.x[:, :9].reshape(-1, 3, 3)  # 提取顶点坐标(num_triangle, 3, 3)angles = angle_func(vertices)  # 计算内角 (num_triangle, 3)data.x_with_angle = [{'triangle_idx': i,'vertices': [tuple(v) for v in vertices[i]],'angles': angles[i].tolist()}for i in range(vertices.shape[0])]# 2. 取它们的顶点(去重)vertex_info = {}for i in room_indices:triangle = data.x_with_angle[i]face_idx = triangle['triangle_idx']vertices = triangle['vertices']angles = triangle['angles']for vertex, angle in zip(vertices, angles):vertex_key = tuple(vertex)if vertex_key not in vertex_info:vertex_info[vertex_key] = {'vertices': vertex,'faces_idx': [],'angles': [],'decoded_x': []}vertex_info[vertex_key]['faces_idx'].append(face_idx)vertex_info[vertex_key]['angles'].append(angle)vertex_info[vertex_key]['decoded_x'].append(softmax_decoded_x[face_idx])# 3. 计算每个顶点的角度总和和融合概率特征for vertex_key in vertex_info:vertex_info[vertex_key]['angle_merge'] = sum(vertex_info[vertex_key]['angles'])vertex_info[vertex_key]['p_merge'] = torch.mean(torch.stack(vertex_info[vertex_key]['decoded_x']), dim=0)# 4. angle_loss = p^alpha * min|θ - t|t_values = torch.tensor([np.pi/2, np.pi, 3*np.pi/2, 2*np.pi], dtype=torch.float32)alpha = self.config.angle_loss_alphatotal_angle_loss = 0for vertex_key, info in vertex_info.items():angle_sum = info['angle_merge']p = info['p_merge'][2]abs_diffs = torch.abs(angle_sum - t_values)min_abs_diff = torch.min(abs_diffs)angle_loss = p**alpha * min_abs_difftotal_angle_loss += angle_lossreturn total_angle_loss

for循环太多,考虑能不能优化

2、优化循环

算法优化

# room 顶点
room_vertices = vertices[room_indices].reshape(-1, 3)  # room angle
room_angles = angles[room_indices].reshape(-1)  # (num_room_triangles * 3)# 从 softmax_decoded_x 中提取出属于“room”类别的三角形的概率分布,并将每个三角形的概率分布重复 3 次,以对应每个三角形的 3 个顶点
room_decoded_x = softmax_decoded_x[room_indices].repeat_interleave(3, dim=0)  # (num_room_triangles * 3, num_cls)# 获取去重顶点
unique_vertices
# room_vertices 中相应元素在 unique_vertices 中的索引
inverse_indeces# angle_merge、p_merge
angle_merge.scatter_add_(0, inverse_indices, room_angles)
优化循环
def angle_loss(self, data, decoded_x):"""doc: 计算角度正则化损失return: total_angle_loss: 角度正则化损失"""# 1. 选出所有最大分类概率为room的三角形(及其索引)softmax_decoded_x = torch.nn.functional.softmax(decoded_x, dim=1)  # 使用softmax得到不同分类的概率max_probs, max_indices = torch.max(softmax_decoded_x, dim=1)room_indices = torch.where(max_indices == 2)[0]# 获取每个面的三个角 data.x_with_anglevertices = data.x[:, :9].reshape(-1, 3, 3)  # 提取顶点坐标(num_triangle, 3, 3)angles = angle_func(vertices)  # 计算内角 (num_triangle, 3)# 2. 取它们的顶点(去重)room_vertices = vertices[room_indices].reshape(-1, 3)  # (num_room_triangles * 3, 3)room_angles = angles[room_indices].reshape(-1)  # (num_room_triangles * 3)room_decoded_x = softmax_decoded_x[room_indices].repeat_interleave(3, dim=0)  # (num_room_triangles * 3, num_cls)# 3. 计算每个顶点的角度总和和融合概率特征unique_vertices, inverse_indices = torch.unique(room_vertices, dim=0, return_inverse=True)angle_merge = torch.zeros(unique_vertices.shape[0], dtype=torch.float32, device=room_vertices.device)p_merge = torch.zeros(unique_vertices.shape[0], softmax_decoded_x.shape[1], dtype=torch.float32, device=room_vertices.device)angle_merge.scatter_add_(0, inverse_indices, room_angles)p_merge.scatter_add_(0, inverse_indices.unsqueeze(1).expand(-1, softmax_decoded_x.shape[1]), room_decoded_x)p_merge = p_merge / torch.bincount(inverse_indices).unsqueeze(1).float()# 4. angle_loss = p^alpha * min|θ - t|t_values = torch.tensor([np.pi/2, np.pi, 3*np.pi/2, 2*np.pi], dtype=torch.float32, device=angle_merge.device)alpha = self.config.angle_loss_alphatotal_angle_loss = 0for angle_sum, p in zip(angle_merge, p_merge):abs_diffs = torch.abs(angle_sum - t_values)min_abs_diff = torch.min(abs_diffs)angle_loss = p[2]**alpha * min_abs_difftotal_angle_loss += angle_lossreturn total_angle_loss

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/869820.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2025.1.15 html基础

学习了html的基础知识,包括:n越大,字体越小换行标签表示一个完整的段落水平线标签链接: 内容 例如: <! --a页面-->这是A页面。<! --b页面-->这是B页面。在浏览器中点击“这是A页面”,会跳转到b页面。

位图有关的格式信息

GetObject(hBitmap, sizeof(BITMAP), (LPSTR)&bmp); 获取 HBITMAP 句柄包含的位图信息结构,不包含像素数据内容。 typedef struct tagBITMAP {   LONG bmType; // 位图类型,必须为 0   LONG bmWidth; // 位图宽度(以像素为单位) …

Centos7.9安装kerberos

Centos7.9安装kerberos@目录一、背景二、Kerberos安装部署2.1kerberos服务端必要软件安装2.2配置krb5.conf2.3配置kdc.conf2.4配置kadm5.acl2.5创建Kerberos数据库2.6启动Kerberos服务2.7创建Kerberos管理员principal2.8客户端安装kerberos2.9Kerberos功能验证本人其他相关文章…

并发编程 - 初识线程

线程是操作系统单独执行任务的最小单元,分前台和后台,有优先级,经历多个状态。C#可设置线程优先级和类型,控制线程状态的方法有Start、Sleep等,但Suspend和Abort已被弃用。多线程编程需通过同步机制控制线程执行。01、什么是线程? 要深刻理解什么是线程,就需要了解计算机…

Wgpu图文详解(05)纹理与绑定组

前言 什么是纹理? 纹理是图形渲染中用于增强几何图形视觉效果的一种资源。它是一个二维或三维的数据数组,通常包含颜色信息,但也可以包含其他类型的数据,如法线、高度、环境光遮蔽等。纹理的主要目的是为几何图形的表面提供详细的视觉效果,使其看起来更加真实和复杂。而我…

DeepSeek V3:AI 模型的游戏规则改变者

DeepSeek V3:AI 模型的游戏规则改变者 什么是DeepSeek V3? DeepSeekDeepSeek V3:AI 模型的游戏规则改变者什么是DeepSeek V3? DeepSeek V3是一款具有革命性的混合专家(MoE)模型,总参数达6710亿,每个标记激活370亿参数 。MoE方法允许多个专门模型(即“专家”)在门控网…

Opencv 的下载安装和VisualStudio配置

本文详细介绍了Windows系统下Opencv 的下载安装和VisualStudio配置过程。Opencv 的下载安装和VisualStudio配置 1 opencv-windows的下载 1.1 github直接下载链接(需要外网链接) 最新4.10.0版本的下载链接为: https://github.com/opencv/opencv/releases/download/4.10.0/openc…

G1原理—8.如何优化G1中的YGC

大纲 1.5千QPS的数据报表系统发生性能抖动的优化(停顿时间太小导致新生代上不去) 2.由于产生大量大对象导致系统吞吐量降低的优化(大对象太多频繁Mixed GC) 3.YGC其他相关参数优化之TLAB参数优化 4.YGC其他相关参数优化之RSet、PLAB和大对象的处理优化1.5千QPS的数据报表系统发…

【JavaSecLab靶场】Java综合漏洞平台

免责声明: 请勿利用文章内的相关技术从事非法测试,如因此产生的一切不良后果与作者无关。在我们平时的网络安全工作中,经常会面对各种各样的挑战。比如,进行定期的漏洞扫描、代码审计,甚至是参与红蓝对抗演练时,发现漏洞后往往需要及时将其修复。 最近,我接触到了一款开…

黑群晖最新安装方式|RR新手

引导盘制作 1、下载最新的黑群晖引导镜像原版链接:wjz304/rr 百度云盘:链接:https://pan.baidu.com/s/12z3v_kVYUDdWNzWBWN_NTQ?pwd=e67k2、将下载好的压缩包解压,得到一个后缀为img的文件。3、使用写盘工具Rufus将镜像文件写到u盘中,点击选择,找到解压好后缀为img的文件…

【Node.js渗透】安装与检测基于Electron的应用程序

免责声明: ⽂中所涉及的技术、思路和⼯具仅供以安全为⽬的的学习交流使⽤,任何⼈不得将其⽤于⾮法⽤途以及盈利等⽬的,否则后果⾃⾏承担。所有渗透都需获取授权!三、说明 传送门:【Node.js开发】Electron 框架介绍,我们已经了解了创建简单Electron应用程序的过程。 本文将…

器件选型---晶振

如何选型晶振,有那些选型注意事项器件选型---晶振 晶振的种类和区别 晶振大体可分为无源晶振和有源晶振两类,其区别如下:无源晶振(crystal,谐振器):内部是两侧贴着金属极板的石英晶体,必须要依赖外部电路才能进行稳定的震动;无源晶振一般会采取下面的接法来与MCU内部的…