aboutsummaryrefslogtreecommitdiff
path: root/src/nbc/kahan.sml
blob: 70c6b476d858db29ce48cde28e7467e42b7347c8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
(* Kahan summation *)

signature KAHAN = sig
	type t
	val zero: t
	val add: t * real -> t
	val sum: t -> real
	val sequence: real Sequence.t -> real
	val list: real list -> real
	val array: real array -> real
end

structure Kahan :> KAHAN = struct
	type t = real * real
	val zero = (0.0, 0.0)
	fun add ((s, c), x) =
		let
			val y = x - c
			val t = s + y
		in
			(t, t - s - y)
		end
	fun sum (s, c) = s
	local
		fun swappedAdd (a, b) = add (b, a)
	in
		fun sequence e = sum (Sequence.fold swappedAdd zero e)
		fun list l = sum (foldl swappedAdd zero l)
		fun array a = sum (Array.foldl swappedAdd zero a)
	end
end