Parallel calculations: Difference between revisions

add Ada
(add Ada)
Line 19:
 
{{omit from|J}}
 
=={{header|Ada}}==
 
I took the version from [[Prime decomposition]] and adjusted it to use tasks.
 
prime_numbers.ads:
<lang Ada>generic
type Number is private;
Zero : Number;
One : Number;
Two : Number;
with function Image (X : Number) return String is <>;
with function "+" (X, Y : Number) return Number is <>;
with function "/" (X, Y : Number) return Number is <>;
with function "mod" (X, Y : Number) return Number is <>;
with function ">=" (X, Y : Number) return Boolean is <>;
package Prime_Numbers is
type Number_List is array (Positive range <>) of Number;
 
procedure Put (List : Number_List);
 
task type Calculate_Factors is
entry Start (The_Number : in Number);
entry Get_Size (Size : out Natural);
entry Get_Result (List : out Number_List);
end Calculate_Factors;
 
end Prime_Numbers;</lang>
 
prime_numbers.adb:
<lang Ada>with Ada.Text_IO;
package body Prime_Numbers is
 
procedure Put (List : Number_List) is
begin
for Index in List'Range loop
Ada.Text_IO.Put (Image (List (Index)));
end loop;
end Put;
 
task body Calculate_Factors is
Size : Natural := 0;
N : Number;
M : Number;
K : Number := Two;
begin
accept Start (The_Number : in Number) do
N := The_Number;
M := N;
end Start;
-- Estimation of the result length from above
while M >= Two loop
M := (M + One) / Two;
Size := Size + 1;
end loop;
M := N;
-- Filling the result with prime numbers
declare
Result : Number_List (1 .. Size);
Index : Positive := 1;
begin
while N >= K loop -- Divisors loop
while Zero = (M mod K) loop -- While divides
Result (Index) := K;
Index := Index + 1;
M := M / K;
end loop;
K := K + One;
end loop;
Index := Index - 1;
accept Get_Size (Size : out Natural) do
Size := Index;
end Get_Size;
accept Get_Result (List : out Number_List) do
List (1 .. Index) := Result (1 .. Index);
end Get_Result;
end;
end Calculate_Factors;
 
end Prime_Numbers;</lang>
 
Example usage:
 
parallel.adb:
<lang Ada>with Ada.Text_IO;
with Prime_Numbers;
procedure Parallel is
package Integer_Primes is new Prime_Numbers (
Number => Integer, -- use Large_Integer for longer numbers
Zero => 0,
One => 1,
Two => 2,
Image => Integer'Image);
 
My_List : Integer_Primes.Number_List :=
( 12757923,
12878611,
12757923,
15808973,
15780709,
197622519);
 
Decomposers : array (My_List'Range) of Integer_Primes.Calculate_Factors;
Lengths : array (My_List'Range) of Natural;
Max_Length : Natural := 0;
begin
for I in My_List'Range loop
-- starts the tasks
Decomposers (I).Start (My_List (I));
end loop;
for I in My_List'Range loop
-- wait until task has reached Get_Size entry
Decomposers (I).Get_Size (Lengths (I));
if Lengths (I) > Max_Length then
Max_Length := Lengths (I);
end if;
end loop;
declare
Results :
array (My_List'Range) of Integer_Primes.Number_List (1 .. Max_Length);
Largest_Minimal_Factor : Integer := 0;
Winning_Index : Positive;
begin
for I in My_List'Range loop
-- after Get_Result, the tasks terminate
Decomposers (I).Get_Result (Results (I));
if Results (I) (1) > Largest_Minimal_Factor then
Largest_Minimal_Factor := Results (I) (1);
Winning_Index := I;
end if;
end loop;
Ada.Text_IO.Put_Line
("Number" & Integer'Image (My_List (Winning_Index)) &
" has largest minimal factor:");
Integer_Primes.Put (Results (Winning_Index));
Ada.Text_IO.New_Line;
end;
end Parallel;</lang>
 
Output:
<pre>Number 12878611 has largest minimal factor:
47 101 2713 32767</pre>
 
=={{header|PicoLisp}}==
256

edits