CCF 202206-4 光线追踪 python

CCF 202206-4 光线追踪 python

CCF官网题目
此题因为运行超时得到了30分,仅为没思路的同学提供一些想法,如果有改进建议欢迎评论!

题目分析

  1. 首先将反射镜转换为单独的反射点,去除反射镜的两端点。例如,反射镜(0,0)–(5,5)就可以转换为反射点(1,1),(2,2),(3,3),(4,4)。
    题目中说“平面中有一些激光光源,每个光源位于一个坐标为整数的点上,会向某个水平或竖直的方向发射一定强度的激光。”。由此可知,光线与反射镜相交时一定是位于一个整数点上,所以反射镜就可以进行离散化,这样可以将坐标系内的点提前进行标记是否为反射点,光源移动到达某个整数点只需要判断其是否为反射点,从而进行相应的操作。
  2. 每个光源单独追踪,以时间和光强进行控制,移动后判断是否到达反射点,更改其光向及光强。
    当到达设定时间阈值t或者光强I<1时,输出结果。本文提前将反射点加入字典point_dict,每次光源移动都要判断是否到达反射点。
    反射点根据其所在反射镜的方向可以分为两类,斜率为-1及1。光线与这两种反射镜相交后的方向改变需要分别进行讨论。
    而光源的移动,有上下左右四种情况,所以每个光源需要有一个参数—光向,这样就可以编程自动化了。
  3. 设置reflection、light两个类,并灵活使用python的字典数据结构。

代码

class reflection:
    def __init__(self, x1, y1, x2, y2, a):
        self.x1 = x1
        self.x2 = x2
        self.y1 = y1
        self.y2 = y2
        self.a = a

    def gradient(self):
        return (self.x1 - self.x2) / (self.y1 - self.y2)

    def insert_reflection(self):
        if self.x1 < self.x2:
            j = self.y1
            for i in range(self.x1 + 1, self.x2):
                if self.gradient() == 1:
                    j = j + 1
                else:
                    j = j - 1
                point_dict[(i, j)] = [self.gradient(), self.a]
        else:
            j = self.y2
            for i in range(self.x2 + 1, self.x1):
                if self.gradient() == 1:
                    j = j + 1
                else:
                    j = j - 1
                point_dict[(i, j)] = [self.gradient(), self.a]

    def remove_reflection(self):
        if self.x1 < self.x2:
            j = self.y1
            for i in range(self.x1 + 1, self.x2):
                if self.gradient() == 1:
                    j = j + 1
                else:
                    j = j - 1
                del point_dict[(i, j)]
        else:
            j = self.y2
            for i in range(self.x2 + 1, self.x1):
                if self.gradient() == 1:
                    j = j + 1
                else:
                    j = j - 1
                del point_dict[(i, j)]


class light:
    def __init__(self, x, y, d, I, t):
        self.x = x
        self.y = y
        self.d = d
        self.I = I
        self.t = t

    def move(self):
        # d 的含义为:d = 0 表示沿 x 坐标增加的方向,d = 1 表示沿 y 坐标增加的方向,d = 2 表示沿 x 坐标减小的方向,d = 3 表示沿 y 坐标减小的方向
        if self.d == 0:
            self.x = self.x + 1
        elif self.d == 1:
            self.y = self.y + 1
        elif self.d == 2:
            self.x = self.x - 1
        else:
            self.y = self.y - 1

    def change_d(self, g):
        if g == 1:
            if self.d == 0:
                self.d = 1
            elif self.d == 1:
                self.d = 0
            elif self.d == 2:
                self.d = 3
            else:
                self.d = 2
        elif g == -1:
            if self.d == 0:
                self.d = 3
            elif self.d == 1:
                self.d = 2
            elif self.d == 2:
                self.d = 1
            else:
                self.d = 0

    def time_pass(self):
        while self.t > 0 and self.I >= 1:
            self.t = self.t - 1

            self.move()

            # 判断此时的(x,y)是否处于反射点 | 反射点的方向 1 或者 -1 | 修改d
            if (self.x, self.y) in point_dict.keys():
                reflection = point_dict[(self.x, self.y)]
                self.change_d(reflection[0])
                self.I = reflection[1] * self.I


if __name__ == "__main__":
    # 是否为反射镜
    point_dict = {}
    reflection_dict = {}
    m = int(input())

    # 1 x1 y1 x2 y2 a :反射系数为 a 的反射面
    # 2 k :删除第 k 个操作插入的反射面
    # 3 x y d I t :发射光线的方向为 d ,强度为 I ,求其所经 t 时刻后光线到达的坐标以及采样得到的光线强度

    for i in range(m):
        input_list = list(input().split())

        if int(input_list[0]) == 1:
            reflection_dict[i + 1] = reflection(x1=int(input_list[1]), y1=int(input_list[2]), x2=int(input_list[3]),
                                                y2=int(input_list[4]),
                                                a=float(input_list[5]))
            reflection_dict[i + 1].insert_reflection()

        elif int(input_list[0]) == 2:
            reflection_dict[int(input_list[1])].remove_reflection()

        else:
            light_temp = light(x=int(input_list[1]), y=int(input_list[2]), d=int(input_list[3]), I=float(input_list[4]),
                               t=int(input_list[5]))
            light_temp.time_pass()
            if int(light_temp.I) == 0:
                print(0, 0, 0)
            else:
                print(light_temp.x, light_temp.y, int(light_temp.I))

结果

提交编号 用户名 姓名 试题名称 提交时间 代码长度 编程语言 评测结果 得分 时间使用 空间使用
3132778 佚名 佚名 光线追踪 08-01 19:52 4.078KB PYTHON 运行超时 30 运行超时 82.93MB

觉得不错,记得帮忙点个赞哟!

你可能感兴趣的:(CCF及算法,python,数据结构,算法)