遍历一棵树

发布于 2024-09-28 09:00:45 字数 769 浏览 1 评论 0原文

我试图找出如何反向迭代并向前迭代,或者至少反向调用一个方法。

这是它的工作原理。

小部件有一个 Widget* 的 std::vector,它们是该控件的子控件。子向量按 z 顺序排列,这意味着 child[0] 位于 child[1] 之后(按渲染顺序)。每个控件都有一个指向其父控件的指针,但根(虚拟)控件除外,其父控件为 NULL。

对于我的渲染,我需要进行阶梯式迭代(从后到前)例如:

root->child[0];
root->child[0]->child[0];
root->child[0]->child[1];
root->child[1];
root->child[1]->child[0];
root->child[1]->child[1];

但是要找到鼠标下方的小部件,我必须从前到后进行矩形测试中的点:

   root->child[9]->child[1];
    root->child[9]->child[0];
    root->child[9];
    root->child[8]->child[2];
    root->child[8]->child[1];
    root->child[8]->child[0];
    root->child[8];

什么样的迭代会我需要有效地进行上述两种类型的迭代吗? (从后到前,从前到后)。

谢谢

I'm trying to figure out how I can iterate in reverse, and forward through this, or atleast call a method in reverse.

Here is how it works.

Widgets have a std::vector of Widget* which are that control's children. The child vector is z ordered which means that child[0] is behind child[1] (in render order). Each control has a pointer to its parent except for the root (dummy) widget whos parent is NULL.

For my rendering, I need to sort of do a staircase sort of iteration (back to front) ex:

root->child[0];
root->child[0]->child[0];
root->child[0]->child[1];
root->child[1];
root->child[1]->child[0];
root->child[1]->child[1];

However to find which widget is under the mouse, I must do my point in rectangle test from front to back:

   root->child[9]->child[1];
    root->child[9]->child[0];
    root->child[9];
    root->child[8]->child[2];
    root->child[8]->child[1];
    root->child[8]->child[0];
    root->child[8];

What sort of iteration would I need to efficiently do the above 2 types of iterations? (back to front, front to back).

Thanks

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

不甘平庸 2024-10-05 09:00:45

正向迭代:

void blah_forward(const Widget *p)
{
    p->do_something();
    std::for_each(p->children.begin(), p->children.end(), blah_forward);
}

反向迭代:(

void blah_reverse(const Widget *p)
{
    std::for_each(p->children.rbegin(), p->children.rend(), blah_reverse);
    p->do_something();
}

未经测试,但希望您明白)。

Forward iteration:

void blah_forward(const Widget *p)
{
    p->do_something();
    std::for_each(p->children.begin(), p->children.end(), blah_forward);
}

Reverse iteration:

void blah_reverse(const Widget *p)
{
    std::for_each(p->children.rbegin(), p->children.rend(), blah_reverse);
    p->do_something();
}

(untested, but hopefully you get the idea).

尤怨 2024-10-05 09:00:45

这里真正拥有的是一棵树,里面有有序的孩子。如果我理解正确的话,你想使用深度优先搜索访问孩子们来遍历它们以相反的顺序。因此,您只需要一些递归函数 widgetUnderMouse(Widget*) ,它按照您想要的顺序遍历树并检查当前小部件是否位于鼠标下方。我想是这样的。

Widget* widgetUnderMouse(Widget* root)
{
    if (root->hasChildren) 
    {
        vector<Widget*>::reverse_iterator rit;
        for (rit = root->child.rbegin(); rit < root->child.rend(); ++rit)
        {
            if (isWidgetUnderMouse(*rit)
            {
                return widgetUnderMouse(*rit);
            }
        }
    }
    else
    {
        return root;
    }
}

如果传入的小部件位于鼠标下方,则 isWidgetUnderMouse 返回 true 或 false

What you really have here is a tree with ordered children. And if I understand correctly, what you want to traverse them using Depth First Search visiting the children in reverse order. So you just need some recursive function widgetUnderMouse(Widget*) that traverses the tree in the order you want and checks if the current widget is under the mouse. Something like this I think.

Widget* widgetUnderMouse(Widget* root)
{
    if (root->hasChildren) 
    {
        vector<Widget*>::reverse_iterator rit;
        for (rit = root->child.rbegin(); rit < root->child.rend(); ++rit)
        {
            if (isWidgetUnderMouse(*rit)
            {
                return widgetUnderMouse(*rit);
            }
        }
    }
    else
    {
        return root;
    }
}

Where isWidgetUnderMouse returns true or false if the passed in widget is under the mouse

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文