首页 > 解决方案 > alloca的性能

问题描述

这些天我使用alloca了很多来分配临时缓冲区。在我的应用程序(信号处理)中,这是一个常见的需求。

问题是:

分配多个数组时,只使用一次 alloca 会更好(性能方面)吗?

像这样:

float *array1 = (float*)alloca(4096 * 4);
float *array2 = array1 + 1024;
float *array3 = array2 + 1024;
float *array4 = array3 + 1024;

或者像这样多次使用它:

void *array1 = (float*)alloca(4096);
void *array2 = (float*)alloca(4096);
void *array3 = (float*)alloca(4096);
void *array4 = (float*)alloca(4096);

我的意思是它可能所做的只是减少堆栈指针并可能执行“堆栈探测”,这取决于大小,所以可能没关系?

标签: c++performancestackalloca

解决方案


allocamalloc正如我确定您知道的那样,由于与执行分配/解除分配的方式以及使用的内存部分相关的原因,它的速度更快。正如评论中所述,它也很容易出错。

就这一点而言,我的猜测是alloca,在未优化的设置中,第一个版本 repeating 会比玩间接更快,事实上,在一些基准测试之后,这一点得到了证实:

在此处输入图像描述

测试是使用google benchmark、clang 10.0、C++20 std 进行的,没有优化。使用类似于 OP 代码的函数运行重复测试并获得恒定结果:

#include <alloca.h>

void alloc1(){
    float *array1 = (float*)alloca(4096 * 4);
    float *array2 = array1 + 1024;
    float *array3 = array2 + 1024;
    float *array4 = array3 + 1024;
}

void alloc2(){
    void *array1 = (float*)alloca(4096);
    void *array2 = (float*)alloca(4096);
    void *array3 = (float*)alloca(4096);
    void *array4 = (float*)alloca(4096);
}

static void alloca1_test(benchmark::State& state) {
    for (auto _ : state) {
        alloc1();
        //benchmark::DoNotOptimize();
    }
}
BENCHMARK(alloca1_test);

static void alloca2_test(benchmark::State& state) {
    for (auto _ : state) {
        alloc2();
        //benchmark::DoNotOptimize();
    }
}
BENCHMARK(alloca2_test);

正如O3人们所期望的那样,添加了优化后,测试结果将趋于平衡,倍数alloca仍然始终稍快一些,但性能差异可以忽略不计。正如你所说,它基本上是一样的。使用其中一个似乎没有什么区别。

在此处输入图像描述

免责声明:

为了更好地了解您的程序的性能,集成测试会给您比这里所做的孤立测试更准确的读数。构建工具和环境也会影响最终结果,要全面准确地衡量您的选项的性能,您必须自己测试它们。


推荐阅读