CSP-201403-2-窗口
解题思路
-
窗口存储结构:首先,使用一个结构体
MyWindow
来存储每个窗口的信息,包括窗口的序号(index)和矩形区域的四个顶点坐标(x1, y1, x2, y2)。所有窗口的信息存储在一个向量windowList
中。 -
输入处理:程序首先接收两个输入值N和M,N表示窗口的数量,M表示点击的数量。接着,程序通过循环读取每个窗口的坐标,并将它们添加到
windowList
向量中。之后,程序通过另一个循环读取每次点击的坐标。 -
点击事件处理:对于每个点击事件,程序从最后一个添加到
windowList
中的窗口开始逆序遍历,这样可以首先检查最上层的窗口。如果点击的点位于某个窗口的范围内,程序输出该窗口的序号,并将这个窗口移动到向量的末尾,表示这个窗口被移动到了所有窗口的最上层。如果点击的点不在任何窗口的范围内,程序输出“IGNORED”。 -
更新窗口顺序(重要):当一个窗口因为点击而被选中时,它会被从列表中移除(删除原有窗口),然后添加到列表的末尾(置于顶层)。这样确保了如果再有点击事件,最新被点击的窗口将会是第一个被检查的。
完整代码
#include <iostream>
#include <vector>
using namespace std;
struct MyWindow
{
int index;
int x1, y1, x2, y2;
};
int N, M;
vector<MyWindow>windowList;
int main() {
ios_base::sync_with_stdio(false);
cin.tie(0);
cout.tie(0);
cin >> N >> M;
// 输入窗口
for (int i = 0; i < N; i++)
{
MyWindow t;
t.index = i + 1;
cin >> t.x1 >> t.y1 >> t.x2 >> t.y2;
windowList.push_back(t);
}
// 输入鼠标点击记录
for (int i = 0; i < M; i++)
{
int x, y;
cin >> x >> y;
bool isFind = 0; // 标记是否找到点击窗口 1-找到
// 倒序遍历windowList(先找到序号最大的窗口即最顶部的窗口)
for (int j = windowList.size() - 1; j >= 0; j--)
{
// 鼠标点击在该窗口内
if (windowList[j].x1 <= x && x <= windowList[j].x2
&& windowList[j].y1 <= y && y <= windowList[j].y2)
{
cout << windowList[j].index << endl;
isFind = 1;
MyWindow t = windowList[j];
windowList.erase(windowList.begin() + j); // 删除原有窗口
windowList.push_back(t); // 置于顶层
break;
}
}
if (isFind == 0)
{
cout << "IGNORED\n";
}
}
return 0;
}