在 C++ 中对结构数组进行排序

Posted

技术标签:

【中文标题】在 C++ 中对结构数组进行排序【英文标题】:Sorting an array of structs in C++ 【发布时间】:2014-03-12 19:23:45 【问题描述】:

我正在使用一个用 c++ 编写的粒子物理库来开发游戏。

为了绘制粒子,我必须得到一个包含所有位置的数组,像这样..

b2Vec2* particlePositionBuffer = world->GetParticlePositionBuffer();

这将返回一个 b2Vec2 对象数组(在物理引擎中表示二维向量)。 我也可以使用

获取和设置它们的颜色
  b2ParticleColor* particleColourBuffer = world->GetParticleColorBuffer();

我想得到 Y 值最高的 10% 的粒子(然后改变它们的颜色)

我的想法是.. 1. 制作一个与particlePositionBuffer数组大小相同的struct数组,struct只包含一个int(particlePositionBuffer数组中的粒子索引)和一个float(粒子y位置) 2.然后我按y位置对数组进行排序。 3.然后我使用结构数组中前 10% 的结构中的 int 来处理它们在particleColourBuffer 数组中的颜色。

有人可以告诉我如何在 c++ 中对结构进行排序和数组吗? 您还认为这是解决此问题的一种不错的方式吗?我只需要做一次(不是每一帧)

【问题讨论】:

std::sort 有什么问题?在您的结构中编写比较器函数或重载operator<。也只是一个小问题,我认为2d vector objects 指的是2dvector 而不是std::vector。你能编辑你的问题吗,因为我一开始很困惑。 是的,我看到这个问题的答案非常好。 ***.com/questions/873715/c-sort-with-structs 唯一的是他说这是针对 STL 容器而不是数组(我不知道 STL 容器是什么) @remyabel:顺便说一句,std::nth_element(或std::partial_sort)就足够了。 一个 STL 容器,是标准模板库中的一个容器。当您说“制作一个数组...”时,您会“制作(并填充)一个向量...”。事实上,由于您想要一个直到运行时才知道大小的“数组”,所以您真的想改用std::vector<> @GuyeIncognito:您可以使用std::vector<std::pair<float, int>>std::greater<std::pair<float, int>> 作为比较函子。 【参考方案1】:

以下可能会有所帮助:

// Functor to compare indices according to Y value.
struct comp

    explicit comp(b2Vec2* particlePositionBuffer) :
        particlePositionBuffer(particlePositionBuffer)
    
    operator (int lhs, int rhs) const
    
        // How do you get Y coord ?
        // note that I do rhs < lhs to have higher value first.
        return particlePositionBuffer[rhs].getY() < particlePositionBuffer[lhs].getY();
    
    b2Vec2* particlePositionBuffer;
;

void foo()

    const std::size_t size = world->GetParticleCount(); // How do you get Count ?
    const std::size_t subsize = size / 10; // check for not zero ?

    std::vector<std::size_t> indices(size);

    for (std::size_t i = 0; i != size; ++i) 
        indices[i] = i;
    
    std::nth_element(indices.begin(), indices.begin() + subsize, indices.end(),
        comp(world->GetParticlePositionBuffer()));

    b2ParticleColor* particleColourBuffer = world->GetParticleColorBuffer();
    for (std::size_t i = 0; i != subsize; ++i) 
        changeColor(particleColourBuffer[i])
    

【讨论】:

【参考方案2】:

如果您的粒子计数很低,那么无论哪种方式都无关紧要,并且首先使用简单的 stl 排序例程将它们全部排序就可以了。

如果数量很大,我会创建一个二叉搜索树,其最大大小是粒子数量的 10%。然后我会维护实际存储在树中的 minY 以便快速拒绝。那么这个算法应该可以做到:

遍历您的原始数组并将项目添加到树中,直到它已满 (10%) 更新您的 minY 对于原始数组中的剩余项目 如果 item.y 小于 minY,则转到下一项(快速拒绝) 否则 从树中移除当前最小的 Y 值 将较大的 Y 项添加到树中 更新 MinY

二叉搜索树具有快速插入、快速搜索和保持排序的优点。如果你想FAST,这比对整个数组进行完整排序要好。

【讨论】:

以上是关于在 C++ 中对结构数组进行排序的主要内容,如果未能解决你的问题,请参考以下文章

在 C++ 中对对进行排序时出现内存错误

c++ sort 函数能对类或者结构体进行排序吗

在 C++ 中对字符串数组进行排序

在Python中对关联数组进行排序[重复]

c++ - 在寻路中对 std::vector 进行排序

在 C# 中对整数三元组数组进行排序