我正在尝试用Haskell解决SPOJ Beads,但我超过了时间限制。我非常肯定我的算法复杂度是我能得到的最好的。因此我怀疑Haskell本身就是问题(库,严格等),但我不知道它可能是什么。
import Data.Array
import Data.List
main :: IO ()
main = do
x <- readLn
interact $ unlines . fmap proccess . take x . lines
proccess :: String -> String
proccess line = show $ minimumDisjoint line
minimumDisjoint :: String -> Int
minimumDisjoint s = minimumBy sortFn [1..len] -- gets minimum elem from list O(n)
where
len = length s
str = listArray (1, len) s
sortFn i1 i2 = foo i1 i2 -- basically 'string1 > string2' O(n)
where
foo i3 i4
| i3 > len = foo 1 i4
| i4 > len = foo i3 1
| i3 == i1 -1 = ord
| ord == EQ = foo (i3+1) (i4+1)
| otherwise = ord
where
ord = compare (str ! i3) (str ! i4)
感谢您的任何建议!
答案 0 :(得分:0)
最糟糕的情况是所有元素相等的字符串,看起来像minimumDisjoin
O(n ^ 2)。
也许这会奏效,可能是 O(n):
一次遍历字符串以查找最小元素的索引列表。
但不是列表,而是希望开始位置和连续运行索引的长度:运行长度编码
接下来处理环绕。
然后在最长的跑步后取位置。
下一次传递需要比较一组最长运行后的点数。最糟糕的情况是这是原始列表的一半大小,并且正在比较非重叠字符串,比原始重叠问题更有效。