嗯...找到一种更快地读取/写作数据以在此问题中接受的方法有点挑战( https://www.spoj.pl/problems/intest/ ) 使用 F#.

我的代码( http://paste.ubuntu.com/548748/ )tle ...

有什么想法如何加快数据阅读?

有帮助吗?

解决方案

我的这个版本通过了时间限制(但仍然非常慢,〜14秒):

open System
open System.IO

// need to change standard buffer, not to add an additional one
let stream = new StreamReader(Console.OpenStandardInput(4096))

let stdin = Seq.unfold (fun s -> if s = null then None else Some (s,stream.ReadLine())) <| stream.ReadLine()

let inline s2i (s : string) = Array.fold (fun a d -> a*10u + (uint32 d - uint32 '0') ) 0u <| s.ToCharArray()

let calc = 
    let fl = Seq.head stdin
    let [|_;ks|] = fl.Split(' ')
    let k = uint32 ks
    Seq.fold (fun a s -> if (s2i s) % k = 0u then a+1 else a) 0 <| Seq.skip 1 stdin

printf "%A" calc

虽然这个版本的瓶颈实际上是 string -> uint32 转换(从字符串中铸造的标准UINT32铸件甚至较慢)读取本身在我的样本输入(〜100m文件)上大约需要2秒(vs 6秒) - 仍然不是一个很好的结果。一次 s2i 以命令性的方式重写,可以将总运行时间缩短到SPOJ上的10秒:

let inline s2i (s : string) =
    let mutable a = 0u
    for i in 0..s.Length-1 do a <- a*10u + uint32 (s.Chars(i)) - uint32 '0'
    a

其他提示

我实际上并不知道,但是我猜想,因为一次字符一次不好,您应该一次将例如4K阅读到缓冲区中,然后处理缓冲区。

let buf =
    let raw = System.Console.OpenStandardInput()
    let bytebuf = new System.IO.BufferedStream(raw)
    new System.IO.StreamReader(bytebuf)

buf.Read()     // retrieves a single character as an int from the buffer
buf.ReadLine() // retrieves a whole line from the buffer
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top