140 lines · 3.8 KB · Text
RawDownload
(* Vector.sml -- new basis *) type 'a vector = 'a vector; #if defined(msdos)#include "../config.dos/m.h"#elif defined(win32)#include "../config.w32/m.h"#else#include "../config/m.h"#endif #ifdef SIXTYFOURval maxLen = 18014398509481983; (* = 2^54-1, for 64-bit architectures *)#elseval maxLen = 4194303;   	(* = 2^22-1, for 32-bit architectures *)#endif local    prim_val vector_ : int -> 'x -> 'a vector         = 2 "make_vect";    prim_val sub_    : 'a vector -> int -> 'a         = 2 "get_vect_item";    prim_val update_ : 'a vector -> int -> 'a -> unit = 3 "set_vect_item";in prim_val length : 'a vector -> int                   = 1 "vect_length"; fun fromList (vs : 'a list) =  let val n = List.length vs      val a = if n > maxLen then raise Size else vector_ n () : 'a vector      fun init [] i = ()        | init (v::vs) i = (update_ a i v; init vs (i+1))  in (init vs 0; a) end; fun tabulate(n, f : int -> 'a) =  if n < 0 orelse n > maxLen then raise Size else  let val a = vector_ n () : 'a vector      fun init i = if i >= n then () else (update_ a i (f i); init (i+1))  in (init 0; a) end; fun sub(v, i) =    if i < 0 orelse i >= length v then raise Subscript    else sub_ v i; fun extract (vec : 'a vector, i, sliceend) =    let val n = case sliceend of NONE => length vec - i | SOME n => n	val newvec = if i<0 orelse n<0 orelse i+n > length vec then	                 raise Subscript		     else			 vector_ n () : 'a vector	fun copy j = if j<n then (update_ newvec j (sub_ vec (i+j)); 				  copy (j+1))		     else ()    in copy 0; newvec end; fun concat vecs =    let fun acc [] len       = len	  | acc (v1::vr) len = acc vr (length v1 + len)	val len = acc vecs 0	val newvec = if len > maxLen then raise Size else vector_ len ()	fun copyall to []       = ()	  | copyall to (v1::vr) =	    let val len1 = length v1		fun copy j =		    if j<len1 then			(update_ newvec (to+j) (sub_ v1 j); copy (j+1))		    else			()	    in copy 0; copyall (to+len1) vr end    in copyall 0 vecs; newvec end;  fun foldl f e a =     let	val stop = length a	fun lr j res = if j < stop then lr (j+1) (f(sub_ a j, res))		       else res    in lr 0 e end fun foldr f e a =    let	fun rl j res = if j >= 0 then rl (j-1) (f(sub_ a j, res))		       else res    in rl (length a - 1) e end fun app f a =     let val stop = length a	fun lr j = if j < stop then (f(sub_ a j); lr (j+1))		   else ()    in lr 0 end fun map (f : 'a -> 'b) (a : 'a vector) : 'b vector =     let val stop = length a	val newvec = vector_ stop () 	fun lr j = if j < stop then (update_ newvec j (f(sub_ a j)); 				     lr (j+1))		   else ()    in lr 0; newvec end fun sliceend (a, i, NONE) =         if i<0 orelse i>length a then raise Subscript	else length a  | sliceend (a, i, SOME n) = 	if i<0 orelse n<0 orelse i+n>length a then raise Subscript	else i+n; fun foldli f e (slice as (a, i, _)) =     let fun loop stop =	    let fun lr j res = 		if j < stop then lr (j+1) (f(j, sub_ a j, res))		else res	    in lr i e end    in loop (sliceend slice) end; fun foldri f e (slice as (a, i, _)) =     let fun loop start =	    let fun rl j res = 		    if j >= i then rl (j-1) (f(j, sub_ a j, res))		    else res	    in rl start e end;    in loop (sliceend slice - 1) end fun appi f (slice as (a, i, _)) =     let fun loop stop = 	    let	fun lr j = 		    if j < stop then (f(j, sub_ a j); lr (j+1)) 		    else ()	    in lr i end    in loop (sliceend slice) end; fun mapi (f : int * 'a -> 'b) (slice as (a : 'a vector, i, _)) : 'b vector =     let val stop = sliceend slice	val newvec = vector_ (stop - i) () 	fun loop stop = 	    let	fun lr j = 		    if j < stop then 			(update_ newvec (j-i) (f(j, sub_ a j)); 			 lr (j+1)) 		    else ()	    in lr i end    in loop stop; newvec end; end