trim 数组到 i 和 j 之间的元素

trim array to elements between i and j

经典之作,我在这里寻求优化:我有一些东西,经过一些处理我知道我只对元素 i 到 j 感兴趣。如何 trim 我的数组以最轻的方式在 fatset 中完成 deletions/freeing i 之前和 j 之后的元素内存?

我正在做嵌入式 C++,所以我可能无法编译各种类库。但 std 或 vector 事物在第一阶段受到欢迎!

我试过,数组 A trim介于 i 和 j 之间,变量 numElms 告诉我 A 中的元素数:

A = &A[i];
numElms = i-j+1;

因为这会产生不兼容错误。可以修复吗?即使修复了,是否可以为现在未使用的元素释放内存?

一点上下文:这个数组是我模块的中央数据集,它可能很重。只要模块存在,它就会存在。并且一直不需要负重。这是要做的第一件事 - 确定必须分析数据集的哪一部分,然后 trim 永久删除其余部分,永远不再使用它(直到我们得到的下一个周期一个可能完全不同大小的新数组)。

无法在标准 C++ 中更改分配的内存块大小(除非您有 POD 数据——在这种情况下,可以使用像 realloc 这样的 C 工具)。 trim 数组的唯一方法是分配新数组。 copy/move 需要元素并销毁旧数组。

您可以手动完成,也可以使用向量:

int* array = new int[10]{0,1,2,3,4,5,6,7,8,9};
std::vector<int> vec {0,1,2,3,4,5,6,7,8,9};
//We want only elements 3-5
{
    int* new_array = new int[3];
    std::copy(array + 3, array + 6, new_array);
    delete[] array;
    array = new_array;
}
vec = std::vector<int>(vec.begin()+3, vec.begin()+6);

如果您使用的是 C++11,这两种方法应该具有相同的性能。

如果你只是想删除多余的元素而不是真的想释放内存(例如你可能想稍后添加更多元素)你可以按照

但是,您应该考虑:您真的需要立即释放内存吗?您现在需要移动元素吗?你的阵列会活这么久,以至于你的程序会完全失去这段记忆吗?也许你需要一个 range 或者 perharps 一个 view 到数组内容?在许多情况下,您可以存储两个指针(或指针和大小)来表示您的 "new" 数组,同时保持旧指针一次全部释放。

当询问有关速度的问题时,您的速度可能取决于您正在使用的阵列的大小,但是:

你的最快方法是不是trim数组,只需使用A[index + i]找到你想要的元素。

最轻的方法是:

  1. 分配动态数组 malloc
  2. 找到 ij 后,将该范围复制到动态数组的头部
  3. 使用realloc将动态数组的大小调整为j - i + 1

但是您将此标记为 C++ 而不是 C,因此我相信您也对可读性和所需的编程投资感兴趣,而不是原始速度或重量。如果这是真的,那么我建议使用 vectordeque.

给定 vector<thing> Adeque<thing> A 你可以这样做:

A.erase(cbegin(A), next(cbegin(A), i));
A.resize(j - i + 1);