Re: [m-users.] Returning a predicate from a function

Mark Clements <[email protected]>
Newsgroups gmane.comp.lang.mercury.general
Message-ID <GV3P280MB0001A3A14DBCD81F265FB1A6F0EC9@GV3P280MB0001.SWEP280.PROD.OUTLOOK.COM>
As a follow-up, I was interested in the speed and memory requirements for lists compared with nondet predicates. I set up an experiment to sum the integers between 1 and 10 million (yes, I know that there is closed form solution:). The code is here: https://gist.github.com/mclements/b09eee918c24710f59a2eb3a6a0a7a90. I found:
1. foldl using range(1,10000000) was the least time and used the least maximum resident memory
2. unsorted_aggregate with promise_equivalent_solutions was 3 x least time and similar memory
3. foldl using 1..10000000 was 6 x least time and 5 x least memory
4. foldl using unsorted_solutions and promise_equivalent_solutions was 8 x least time and 5 x least memory
5. aggregate was 150 x least time and 13 x least memory.

Note that aggregate creates a sorted list and then uses foldl. Sorting a large (already sorted) list is apparently very slow. For operations on nondet predicates that give equivalent solutions irrespective of the order, then using promise_equivalent_solutions looks helpful.

I realise that this experiment may not generalise to most Mercury programs.

Sincerely, Mark.

PS: the following two functions may be of interest.

%% map a function to a predicate, returning a new predicate
:- func map_pred((func(T1)=T2)::in(func(in)=out is det),
                 pred(T1)::(pred(out) is nondet)) =
   (pred(T2)::(out(pred(out) is nondet))).
map_pred(F,Pred) = (pred(Y::out) is nondet :- Pred(X), Y = F(X)).

%% compose two functions, returning a new function
:- func ((func(T1)=T2)::in(func(in)=out is det)) `o` ((func(T2)=T3)::in(func(in)=out is det)) =
   (func(T1)=T3::(out(func(in)=out is det))).
F `o` G = (func(X::in) = (R::out) is det :- R = G(F(X))).

%% Examples:

:- pred test3(io::di, io::uo) is det.
test3(!IO) :-
    Data = (pred(Y::out) is nondet :- nondet_member(I,range(1,5)), Y = float(I)), % some data
    LnData = map_pred(math.ln,Data),
    aggregate(LnData, print_line, !IO).
:- pred test4(io::di, io::uo) is det.
test4(!IO) :-
    List = map(float `o` math.ln, 1..5),
    foldl(print_line, List, !IO).


När du skickar e-post till Karolinska Institutet (KI) innebär detta att KI kommer att behandla dina personuppgifter. Här finns information om hur KI behandlar personuppgifter<https://ki.se/medarbetare/integritetsskyddspolicy>.


Sending email to Karolinska Institutet (KI) will result in KI processing your personal data. You can read more about KI’s processing of personal data here<https://ki.se/en/staff/data-protection-policy>.
_______________________________________________
users mailing list
[email protected]
https://lists.mercurylang.org/listinfo/users
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.