:-module(_,[prefix_sum/2],[]).
'$applied_packages'([prelude,nonpure,condcomp,assertions,regtypes,nativeprops,predefres(res_steps),resdefs,resdefs/resources_decl,basicmodes,argnames,rtchecks_shallow,expander]).

:-add_clause_trans(expander_tr:expand_clause/4,9910).
:-prop listnum/1+regtype.

:-entry prefix_sum/2:list(num)*var.
:-pred prefix_sum(A,B):(listnum(A),var(B))=>listnum(B).
:-pred prefix_sum_(A,B,C):(num(A),listnum(B),var(C))=>listnum(C).

listnum([]).
listnum([X|Y]) :-
        num(X),
        listnum(Y).
prefix_sum(_1,_2) :-
        'prefix_sum$pre'(_1,_2,_3,_4),
        'prefix_sum$cls'(_1,_2),
        'prefix_sum$post'(_1,_2,_3,_4).
'prefix_sum$pre'(_1,_2,_6,_8) :-
        reify_check(listnum(_1),[_1],_5),
        reify_check(var(_2),[_2],_4),
        reify_check(list(_1,num),[_1,num],_3),
        _9 is _3/\_4,
        _7 is _5/\_4,
        _6 is _7,
        _8 is _9,
        _10 is _6\/_8,
        warn_if_false(_10,'CP').
'prefix_sum$post'(_,_1,_3,_) :-
        reify_check(listnum(_1),[_1],_2),
        _4 is _2,
        _5 is _3#1\/_4,
        _=1,
        _6 is _5,
        warn_if_false(_6,'AP').
'prefix_sum$cls'([],[]).
'prefix_sum$cls'(X,Y) :-
        D=0,
        prefix_sum_(D,X,Y).
prefix_sum_(_1,_2,_3) :-
        'prefix_sum_$pre'(_1,_2,_3,_4),
        'prefix_sum_$cls'(_1,_2,_3),
        'prefix_sum_$post'(_1,_2,_3,_4).
'prefix_sum_$pre'(_2,_1,_3,_7) :-
        reify_check(listnum(_1),[_1],_6),
        reify_check(rtc_num(_2),[_2],_5),
        reify_check(var(_3),[_3],_4),
        _8 is _4/\(_5/\_6),
        _7 is _8,
        _9 is _7,
        warn_if_false(_9,'CP').
'prefix_sum_$post'(_,_,_1,_3) :-
        reify_check(listnum(_1),[_1],_2),
        _4 is _2,
        _5 is _3#1\/_4,
        _6 is _5,
        warn_if_false(_6,'AP').
'prefix_sum_$cls'(_,[],[]).
'prefix_sum_$cls'(N,[X|Y],[X1|LL]) :-
        X1 is N+X,
        prefix_sum_(X1,Y,LL).