Haskell Flags
import Data.Array (Array, listArray, (!))
flags :: [Int] -> Int
flags a = result
where
n = length a
arr = listArray (0, n - 1) a :: Array Int Int
at i
| i >= 0 && i < n = arr ! i
| otherwise = 0
isPeak i = i > 0 && i < n && arr ! (i - 1) < arr ! i && arr ! i > at (i + 1)
nextArr :: Array Int Int
nextArr = listArray (0, n - 1) [compute i | i <- [0 .. n - 1]]
where
compute i
| i == n - 1 = if isPeak i then i else -1
| isPeak i = i
| otherwise = nextArr ! (i + 1)
result = go 1 0
go i best
| i * (i - 1) > n = best
| otherwise = go (i + 1) (max best (countFlags i))
countFlags i = walk 0 0
where
walk pos num
| not (pos < n && num < i) = num
| nextArr ! pos == -1 = num
| otherwise = walk (nextArr ! pos + i) (num + 1)
This finds all peaks first, then checks how many flags can be placed while keeping the required distance.