当前位置: 首页 > 知识库问答 >
问题:

在一个基准内使用大范围输入

易昌翰
2023-03-14

我想为一些地图实现编写一个基准测试,包括一个自定义实现。我想测试它在广泛的输入范围内的平均行为。

因为这是我第一次使用JMH,所以使用@Param看起来是显而易见的选择。但事实证明,JMH不会在一个基准测试中使用所有这些不同的输入,而是会为每一组参数运行单独的基准测试。

是否有一些我缺少的功能,或者只是在我的基准测试中循环输入的范围,这是正确的做法?

更新:

我实现了2个不同的基准,给出了完全相反的比较结果(注意:这是使用3d坐标作为键的特殊Map(不实现Map界面))。

>

  • 在基准测试的输入范围内循环

    @Benchmark
    public void benchmarkGet(Blackhole bh){
        //8*20 different starting positions
        for(int i = 0;i < 8 * 20;i++){
    
            for(int x = 0;x < 20;x++){
                for(int y = 0;y < 20;y++){
                    for(int z = 0;z < 20;z++){
                        Object value = map.get(x + offsets[i][0], y + offsets[i][1], z + offsets[i][2]));
                        bh.consume(value);
                    }
                }
            }
        }
    }
    

    每次仅获取1个值,并使用状态每次获取不同的值:

    @Benchmark
    @OutputTimeUnit(value = TimeUnit.MICROSECONDS)
    public void benchmarkGet(Blackhole bh) {
        Object value = map.get(x + offsets[i][0], y + offsets[i][1], z + offsets[i][2]));
        bh.consume(value);
        x++;
        if (x > 20) {
            y++;
            x = 0;
            if (y > 20) {
                z++;
                y = 0;
                if (z > 20) {
                    i++;
                    z = 0;
                    if (i >= 8*20) {
                        i = 0;
                    }
                }
            }
        }
    }
    

    哪一个是正确的?

  • 共有1个答案

    汪正卿
    2023-03-14

    JMH基准测试试图非常精确地测量特定代码段的性能。

    只有当问题包括哪些输入时,才能回答哪个实现更快的问题,因为答案可能不同。要知道哪种实现平均速度更快,您需要知道必须平均的输入。

    正因为如此,说这两种实现总体上都更快是不可能的,JMH没有试图回答这个问题。

    你在问JMH你想问的问题时遇到了问题,哪一个“总的来说”更快,因为JMH认为这是一个错误的问题,并且很难问它错误的问题。

    事实上,正确的实现是使用具有不同值的Param,获得不同的基准,基准测试的结果就是从中得到的答案范围。

    在研究了基准测试的结果后,您的结果可能看起来像是第一个算法对于某些范围内的小输入要快x得多,但是对于某些范围内的大输入要慢x得多。你从中得出什么结论,哪一个对你的用例来说更快,这必须由用例来得出。

     类似资料:
    • 我正在尝试编写一个素数筛生成器,我将其转换为打印列表,然后在给定范围内打印素数。我很确定我的配对数是正确的,但出于某种原因,我在素数列表中得到了一些非素数的额外值。(我马上发现了这一点,因为我在输出中的最后一个值是3599,这不是素数)。我不确定我是否有某种逻辑错误,所以任何帮助都很棒。

    • 问题内容: 在下面的代码中,您将看到它询问“ shift”值。我的问题是我想将输入限制为1到26。 我如何轻松做到这一点? 问题答案: 使用循环不断询问他们的输入,直到收到您认为有效的信息: 如果您收到一个呼叫(例如,如果他们键入),您还希望在呼叫周围有一个障碍。 请注意,如果您使用Python 2.x,则需要使用而不是。后者将尝试将输入解释为Python代码-可能非常糟糕。

    • 问题内容: 我有以下三个简单的T-SQL查询。第一个是获取一定范围内的记录(DATETIME类型): 第二个是获取最接近@startDT的记录(DATETIME类型) 最后一个是获取@endDT之后最接近的记录: 我想将以上三个查询的所有记录作为一组记录。我尝试使用UNION,但似乎UNION中的子查询不允许使用ORDER BY子句。有没有有效的方法来得到我的结果? 上图仅将* s的记录显示为我的

    • 对于我的Java类,我正在编写一个小程序,首先选择一个介于1和100之间的数字。然后,它会提示用户开始猜测正确的。如果用户对的猜测过高或过低,程序会打印出一个新范围,供他们在该范围内进行猜测。如果用户输入或,程序只需重新要求用户输入,但不会以任何方式更改范围。 示例输出(当机密号为20时)如下所示: 该项目似乎已经基本完成,但只有一个例外。其中一个要求是,当用户键入的超出我们给定的1和100范围时

    • 我是一个角度开发人员和新的反应,这是简单的反应组件,但不工作 错误:在JSX作用域中使用JSX React/React时,“React”必须在作用域中

    • 我需要根据下面的说明制定一个方法。提示是“您想要多宽?”。用户输入输入,如果不是3到20之间的整数,则会弹出错误消息“预期为3到20之间的数字”。用户应该继续输入,直到给出有效答案,然后该值应该返回到main。 此方法提示用户输入一个数字,在返回该数字之前,验证该数字介于最小和最大之间。 如果输入的数字不在最小值和最大值之间,则会向用户显示一条错误消息,并给用户另一个输入数字的机会。如果最小值为1