我正在使用Ray-trace进行仿真来开发激光雷达传感器。模拟可配置为以每秒所需的帧速率运行(在我的情况下为30 fps,即1帧以33.34ms的速度运行)。
当前每秒进行300000次光线跟踪(包括水平和垂直)。在30 fps下,每帧进行10000次光线跟踪。代码如下所示
//call back at the start of frame (just for understanding - not the actual code, data type conversions and some other basics are ignored)
uint32 channels = 16;
float vert_angle[] = {15, 13, 11, 9, 7, 5, 3, 1, -1, -3, -5, -7, -9, -11, -13, -15};
float hor_angle_ref = 0;
uint32 points_per_second = 300000;
float rotation_frequency = 10;
/* 300000 points per second is divided into points per frame.
These points are distributed horizontally and vertically*/
void callback_scan(){
uint32 poits_to_scan_with_one_laser = points_per_second/ (fps * channels);
auto hor_angle_covered_this_frame = points_per_second* rotation_frequency * (1/fps);
auto hor_angle_resolution = hor_angle_covered_this_frame / poits_to_scan_with_one_laser ;
auto hor_angle = hor_angle_ref ;
for(auto i= 0u; i< poits_to_scan_with_one_laser ; ++i){
for(auto ch= 0u; ch< channels; ++ch){
auto hitPoint = raytrace(hor_angle, vert_angle[ch]);
// process_data(); -> distance, time and energy are calculated
/* distance -> Euclidean distance calculation and addition of noise
time -> c=d/t
energy -> Pr = Pt*pow(D,2)*nsys*natm*row/ pow(dist,2);*/
}
hor_angle += hor_angle_resolution ;
}
hor_angle_ref = hor_angle;
}
上面的代码运行得很好。一切在33.33ms的预期时间内完成。现在需要引入效果差异https://en.wikipedia.org/wiki/Beam_divergence。
使用的溶液:每个点取8个样品。即在嵌套的for循环内还有8个光线跟踪。总计(8+1)*300000
射线迹。该解决方案耗时很多,无法在33ms内完成。任何人都可以在构造代码/算法的体系结构方面提出任何其他选择,或者我可以使用另一种方法来以较少的计算复杂性来实现这一目标。
其他信息:
在GPU上运行的Unreal Engine 4.22
答案 0 :(得分:1)
我对您使用的引擎没有任何了解,也对尝试实现的效果没有任何了解,但是我知道有两种主要的方法可以加快射线追踪器的速度(除了明显的并行化和GPU之外):
使用旧框架/光线而不是投射更多光线
通常用于过度发光,反射,运动模糊和类似效果...因此,与其使用稍微不同的方向投射更多光线,不如使用最后一帧或多帧的光线...但这需要额外的缓冲区来存储最后一帧所需的数据。如果您不仅需要生成的颜色,那么它可能会占用大量RAM,尤其是对于光线跟踪器而言。
使用随机性而不是分裂光线
这是非常常见的方法。您知道,当光线撞击表面时,它应分为反射光线和折射光线。随机光线跟踪不会分裂。而是根据伪随机值以50/50的机会反射或折射。如您所见,无需拆分,可以将较少的光线投射到场景中。另一方面,这会产生明显的噪声(类似于低照度条件下的旧CCD摄像机图像)。可以通过将最后几个帧平均在一起来部分抑制(或每帧射线对同一场景进行多次跟踪)...
此方法的另一个优点是它不需要GLSL中未实现的递归,因此您可以更轻松地在GLSL中进行光线跟踪。没有它,您将需要将递归转换为迭代,这并不简单,请参见: