Mail.ruПочтаМой МирОдноклассникиВКонтактеИгрыЗнакомстваНовостиКалендарьОблакоЗаметкиВсе проекты

Как можно оптимизировать эту функцию?

Protonix Знаток (357), на голосовании 15 часов назад
У меня есть функция с декоратором numba.cuda.jit, Она нужна для рендера. У неё есть 2 проблемы. Во-первых, возникают артефакты в виде белых точек или полосок. Во-вторых она медленная, когда проекция грани занимает много места на экране. То есть нужно оптимизировать часть с 2 циклами

функция довольно большая и не помещается в вопросе, поэтому я оставлю 2 частями


 @cuda.jit 
def _render_FbF_kernel(surfarray, vertices, normals, tex_coords, faces, camera_fov, z_buffer):

face_index = cuda.grid(1)
if face_index < faces.shape[0]:

inv_camera_fov = 1 / camera_fov
max_surfarray_side = max(surfarray.shape[:2])
surf_offsetx, surf_offsety = (max_surfarray_side - surfarray.shape[0]) / 2, (max_surfarray_side - surfarray.shape[1]) / 2
face = faces[face_index]
normal_az, normal_bz, normal_cz = normals[face[2], 2], normals[face[5], 2], normals[face[8], 2]

if normal_az != 0 and normal_bz != 0 and normal_cz != 0:

vertex_ax, vertex_ay, vertex_az = vertices[face[0]]
vertex_bx, vertex_by, vertex_bz = vertices[face[3]]
vertex_cx, vertex_cy, vertex_cz = vertices[face[6]]

if vertex_az > 0 and vertex_bz > 0 and vertex_cz > 0:

inv_az, inv_bz, inv_cz = 1 / vertex_az, 1 / vertex_bz, 1 / vertex_cz

proj_ax = (vertex_ax * inv_az * inv_camera_fov + 0.5) * max_surfarray_side - surf_offsetx
proj_ay = (vertex_ay * inv_az * inv_camera_fov + 0.5) * max_surfarray_side - surf_offsety
proj_bx = (vertex_bx * inv_bz * inv_camera_fov + 0.5) * max_surfarray_side - surf_offsetx
proj_by = (vertex_by * inv_bz * inv_camera_fov + 0.5) * max_surfarray_side - surf_offsety
proj_cx = (vertex_cx * inv_cz * inv_camera_fov + 0.5) * max_surfarray_side - surf_offsetx
proj_cy = (vertex_cy * inv_cz * inv_camera_fov + 0.5) * max_surfarray_side - surf_offsety

proj_x1 = max(int(min(proj_ax, proj_bx, proj_cx) - 1), 0)
proj_x2 = min(ceil(max(proj_ax, proj_bx, proj_cx) + 1), surfarray.shape[0])
proj_y1 = max(int(min(proj_ay, proj_by, proj_cy) - 1), 0)
proj_y2 = min(ceil(max(proj_ay, proj_by, proj_cy) + 1), surfarray.shape[1])

for pixel_x in range(proj_x1, proj_x2):
for pixel_y in range(proj_y1, proj_y2):

v0x, v0y = proj_cx - proj_ax, proj_cy - proj_ay
v1x, v1y = proj_bx - proj_ax, proj_by - proj_ay
v2x, v2y = pixel_x - proj_ax, pixel_y - proj_ay

dot00 = v0x * v0x + v0y * v0y
dot01 = v0x * v1x + v0y * v1y
dot02 = v0x * v2x + v0y * v2y
dot11 = v1x * v1x + v1y * v1y
dot12 = v1x * v2x + v1y * v2y

denom = dot00 * dot11 - dot01 * dot01
proj_v = (dot11 * dot02 - dot01 * dot12) / denom
proj_w = (dot00 * dot12 - dot01 * dot02) / denom
proj_u = 1 - proj_v - proj_w
Дополнен 1 месяц назад
if proj_u >= 0 and proj_v >= 0 and proj_w >= 0:

res_a, res_b, res_c = proj_u * inv_az, proj_w * inv_bz, proj_v * inv_cz
res_sum = res_a + res_b + res_c
point_u, point_v, point_w = res_a / res_sum, res_b / res_sum, res_c / res_sum
point_z = point_u * vertex_az + point_v * vertex_bz + point_w * vertex_cz
prev_z = z_buffer[pixel_x, pixel_y]

if prev_z > point_z or prev_z == 0:

z_buffer[pixel_x, pixel_y] = point_z

colour = 255 * abs(normal_az + normal_bz + normal_cz) / 3
surfarray[pixel_x, pixel_y] = colour, colour, colour
Голосование за лучший ответ
Youtube @MAJORIK_YT Гуру (3911) 1 месяц назад
Мозг себе оптимизируй
Валым Заработавич Мудрец (12509) 1 месяц назад
нет тут таких уникумов, спроси у гпт
ProtonixЗнаток (357) 1 месяц назад
Я уже спрашивал, он ничего рабочего не предлагал
Похожие вопросы