RabbitFarm
2025-05-11
The Weekly Challenge 320 (Prolog Solutions)
The examples used here are from the weekly challenge problem statement and demonstrate the working solution.
Part 1: Maximum Count
You are given an array of integers. Write a script to return the maximum between the number of positive and negative integers. Zero is neither positive nor negative.
Our solution will be pretty short, contained in just a single file that has the following structure.
We’ll define two predicates for counting the number of negative and positive numbers. These will use small helper predicates to be called via maplist.
-
identify_negatives(Number, 1):-
Number < 0.
identify_negatives(_, 0).
◇
-
Fragment referenced in 1.
-
identify_positives(Number, 1):-
Number > 0.
identify_positives(_, 0).
◇
-
Fragment referenced in 1.
-
count_negatives(Numbers, Count):-
maplist(identify_negatives, Numbers, Negatives),
sum_list(Negatives, Count).
◇
-
Fragment referenced in 1.
-
count_positives(Numbers, Count):-
maplist(identify_positives, Numbers, Positives),
sum_list(Positives, Count).
◇
-
Fragment referenced in 1.
We’ll need a predicate to tie everything together, that’s what this next one does.
-
maximum_count(Numbers, MaximumCount):-
count_negatives(Numbers, NegativesCount),
count_positives(Numbers, PositivesCount),
max_list([NegativesCount, PositivesCount], MaximumCount).
◇
-
Fragment referenced in 1.
Sample Run
$ gprolog --consult-file prolog/ch-1.p | ?- maximum_count([-3, -2, -1, 1, 2, 3], MaximumCount). MaximumCount = 3 ? yes | ?- maximum_count([-2, -1, 0, 0, 1], MaximumCount). MaximumCount = 2 ? yes | ?- maximum_count([1, 2, 3, 4], MaximumCount). MaximumCount = 4 ? yes | ?-
Part 2: Sum Differences
You are given an array of positive integers. Write a script to return the absolute difference between digit sum and element sum of the given array.
As in the first part, our solution will be pretty short, contained in just a single file.
The element sum is a straightforward application of the builtin predicate sum_list/2.
-
element_sum(Numbers, ElementSum):-
sum_list(Numbers, ElementSum).
◇
-
Fragment referenced in 7.
To compute the digit sum we’ll first convert them to characters, via maplist, flatten the list, convert them back to numbers, and take the sum_list.
-
digit_sum(Numbers, DigitSum):-
maplist(number_chars, Numbers, Characters),
flatten(Characters, CharactersFlattened),
maplist(char_number, CharactersFlattened, Digits),
sum_list(Digits, DigitSum).
◇
-
Fragment referenced in 7.
The above predicate, for convenience of the maplist, requires a small helper predicate to reverse the arguments of numbers_chars.
sum_difference/2 is the main predicate, which calls the others we’ve defined so far.
-
sum_differences(Numbers, Differences):-
element_sum(Numbers, ElementSum),
digit_sum(Numbers, DigitSum),
Differences is abs(DigitSum - ElementSum).
◇
-
Fragment referenced in 7.
Sample Run
$ gprolog --consult-file prolog/ch-2.p | ?- sum_differences([1, 23, 4, 5], SumDifferences). SumDifferences = 18 yes | ?- sum_differences([1, 2, 3, 4, 5], SumDifferences). SumDifferences = 0 yes | ?- sum_differences([1, 2, 34], SumDifferences). SumDifferences = 27 yes | ?-
References
posted at: 13:04 by: Adam Russell | path: /prolog | permanent link to this entry