Title: Use PLINQ to select prime numbers from an array in C#
The example Use PLINQ to select even numbers from an array in C# uses PLINQ (Parallel LINQ) to find the even numbers in an array of random values. This example uses a similar technique to do something slightly more interesting: find prime numbers. To make things even more interesting, it uses a statement lambda to determine whether a number is prime.
The following code shows the most interesting pieces of the example's Form_Load event handler. I've removed timing and display code to save space.
// Create the numbers.
Random rand = new Random();
int num_numbers = int.Parse(txtNumNumbers.Text);
int[] numbers = new int[num_numbers];
for (int i = 0; i < numbers.Length; i++)
numbers[i] = rand.Next(0, 100);
// Make an IsPrime delegate.
Func<int, bool> IsPrime = number =>
{
if (number == 0) return false;
else if (number < 0) number = -number;
if (number == 1) return false;
if (number == 2) return true;
if (number % 2 == 0) return false;
for (int i = 3; i * i <= number; i += 2)
if (number % i == 0) return false;
return true;
};
// Use LINQ to find the prime numbers.
var linq_query =
from int number in numbers
where IsPrime(number)
select number;
int[] linq_primes = linq_query.ToArray();
lstLinq.DataSource = linq_primes.Take(1000).ToArray();
// Use PLINQ to find the prime numbers.
var plinq_query =
from int number in numbers.AsParallel()
where IsPrime(number)
select number;
int[] plinq_primes = plinq_query.ToArray();
lstPlinq.DataSource = plinq_primes.Take(1000).ToArray();
The code starts by making an array of random numbers.
It then defines a delegate variable named IsPrime of type Func<int, bool>. It makes the variable refer to a statement lambda that takes a number as an input and returns true if the number is prime.
Next, the code uses LINQ to select the prime numbers from the array. It sets the DataSource property of the lstLinq ListView control equal to the first 1000 items in the array of primes. (It displays only 1000 because the program has trouble if it tries to display too many values in a ListBox.)
The program then executes a similar query that uses PLINQ. The AsParallel method highlighted in blue allows the program to use as many CPUs or cores as are available on the computer.
If you look at the picture at the top of the post, you'll see that searching 10 million random numbers took 0.72 seconds using LINQ but only 0.38 seconds using PLINQ. My computer is a dual-core system so PLINQ is considerably faster. As in the previous example, the overhead required to use both cores slows things down a bit, so the PLINQ query doesn't take exactly half as long as the LINQ query, but the speed up is considerable.
Download the example to experiment with it and to see additional details.
|