整数数组是单峰的,如果:

一开始严格增加;
之后,它是恒定的;
在那之后,它严格减少。
可能没有第一个块(增加)和最后一个块(减少)。允许这两个块都不存在。

例如,以下三个数组是单峰的:[5,7,11,11,2,1],[4,4,2],[7],但以下三个数组不是单峰的:[5,5,6 ,6,1],[1,2,1,2],[4,5,5,6]。

编写一个C程序,检查数组是否为单峰。
限制:函数应按n的顺序运行。
数组元素之间最多只能执行n-1个比较操作。

我可以使用3个while循环(非嵌套)并检查数组的3个部分(如果部分编号1增加而部分编号2不变而部分3减少)吗?

最佳答案

虽然可以为单峰曲线中的每个可能阶段在三个循环中对此进行编码,但是这种“有状态”算法并不是特别数学。注意,通过在变量中而不是代码控制流中保留状态,可以在单个循环中使用等效的有状态算法。

测试单个公分母可能在数学上更健壮(或至少证明了对这种曲线的数学的理解),并且更简单-即对于单峰曲线上的每个点都成立的共同关系,但是不适用于任何非单峰曲线。这样,您可以在单个循环中算术执行测试,而不是通过控制流或状态转换。

在这种情况下,该唯一的公分母-一种在数学上定义曲线的分母是:曲线梯度的正负是单调递减的。

Signum是一个使signum(a)为的函数:


如果a == 0,则为0,
如果a> 0,则为1,
如果a

减少单调意味着值要么下降或保持不变,但从不上升-下降或平稳。

任何一点的梯度都只是d [n + 1]-d [n]。因此,循环将从另一个元素中减去一个元素,确定符号,然后将其与前一个符号进行比较。如果信号增加,则曲线不是单峰的。也就是说,它可以上升,只能是平坦的或仅下降,或者它可以上升和下降,但再也不会上升,并且具有任何水平的高原。

注意,该解决方案适用于单峰曲线的数学定义。您的问题中的定义有些含糊,似乎不允许多个平台期。也就是说,它允许:

   _________
  /         \
 /           \
/             \


但不包括例如:

      ___
     /   \
 ___/     \____
/              \


但是,我认为第二个显然是单峰的。

发件人:https://en.wikipedia.org/wiki/Unimodality
c - 检查数组是否为单峰-LMLPHP

最后一部分是关键-零不算作符号变化。但是,无论多么微妙,它都适用于所有测试用例。

10-07 17:52