CS 523 Project presentation slides (PPT)

advertisement
Ant Colony Optimization
A threaded application in Java
What is it?
• An ant colony optimization algorithm seeks to
solve hard problem by mimicking the behavior
of ants.
• This presentation shows an application of a
basic ant colony algorithm to generate
reasonably good solutions to the Travelling
Salesperson Problem.
The Ant Colony Simulation GUI
Input params
Map graphic
Text output
Program flow
• Send some number of ants to explore the problem
space (visit each city, then return) in a probabilistic
fashion.
• Ants deposit pheromones on the trails they visit. The
intensity of these pheromones increases as the path
distance decreases. Thus, the probability increases
that more favorable paths get used more often.
• Pheromones evaporate by some percentage each time
an iteration occurs. (run only by threads[0])
• Return the result when the processing budget has been
exhausted.
Parallelism
• The activities of the ants can be run using
threads.
• Running the course/collecting the distance data.
• Depositing the pheromones
• The GUI and ActionListener also run in threads.
Synchronized methods
This is how a mutex lock is implemented in Java:
private synchronized void applyPheromone( int distance,
int bestPathDistance,
String[] run)
{
long newpheromoneLevel;
newpheromoneLevel = (long) (distance/Math.sqrt(distance));
// each ant deposits pheromone
for (int i=1; i < run.length; i++)
{
pheromoneLevels[getCityIndex(run[i-1])][getCityIndex(run[i])]
+= newpheromoneLevel;
}
pheromoneLevels[getCityIndex(run[(run.length)-1][getCityIndex(run[0])]
+= newpheromoneLevel;
}
Synchronized code within a method
private void applyPheromone(int distance,
int bestPathDistance,
String[] run) {
long newpheromoneLevel;
newpheromoneLevel = (long) (distance/Math.sqrt(distance));
// each ant deposits pheromone
synchronized(pheromoneLevels) {
for (int i=1; i < run.length; i++)
{
pheromoneLevels[getCityIndex(run[i-1])][getCityIndex(run[i])]
+= newpheromoneLevel;
}
pheromoneLevels[getCityIndex(run[(run.length)-1])][getCityIndex(run[0])]
+= newpheromoneLevel;
}
}
Interleaved synchronization
• If you have class variables that are never used
together, create a mutex for each of them,
public class MsLunch {
thus:
private
private
private
Object();
private
Object();
long c1 = 0;
long c2 = 0;
Object lock1 = new
Object lock2 = new
public void inc1() {
synchronized(lock1) {
c1++;
}
}
public void inc2() {
synchronized(lock2) {
c2++;
}
}
}
Implementing threads
// In the actionPerformed method (Run button has been clicked)
for (int i = 0; i < numThreads; i++)
{
//ThreadRunner contains the run() method
threads[i] = new Thread(new ThreadRunner(),
Integer.toString(i));
threads[i].start();
}
for (int i = 0; i < numThreads; i++)
{
threads[i].join();
}
// In the run() method
// Evaporate once each run, before any pheromone is applied.
// Only thread 0 gets to evaporate.
if (k > 0 && Thread.currentThread().getName().equals("0"))
{
evaporate();
}
Volatility
• The volatile keyword, applied to variables,
guarantees that a thread sees the latest
version of it.
// read from memory, not from thread cache
private volatile int[][] pheromoneLevels;
Resource usage
• Workload is more or less shared equally
between processors if run in server mode.
(ex. java –jar [path]/SwingAnts.jar
-server)
• Otherwise, using one or all the CPUs depends
on the platform you’re using.
Performance
• On (DogNet machine) grey:
– 1 thread/100000 runs: 12500 ms
– 2 threads/50000 runs: 6600 ms
– 4 threads/25000 runs: 6700 ms
– 8 threads/12500 runs: 6800 ms
Java support for parallelism
• Plain Old Threads (the Runnable class)
• java.util.concurrent Packages (Java 7)
– executors
– Callables
– Fork/join
ExecutorTest output
run:
Pool size: 10: 679 ms. (this run was a “warm up”)
Pool size: 5: 651 ms
Pool size: 100: 675 ms.
Pool size: 500: 746 ms.
Pool size: 1000: 851 ms.
BUILD SUCCESSFUL (total time: 36 seconds)
SerialTest output
(tail end of the output)
result 46
start - Task 47
run time 1.105 secs
result 47
start - Task 48
run time 1.103 secs
result 48
start - Task 49
run time 1.123 secs
result 49
run time 55.618 secs
BUILD SUCCESSFUL (total time: 55 seconds)
ExecutorServiceTest output
(the tail end of the output)
result 45
start - Task 49
run time 1.19 secs
result 46
run time 1.19 secs
result 47
run time 1.124 secs
result 48
run time 1.12 secs
result 49
run time 16.036 secs
BUILD SUCCESSFUL (total time: 16 seconds)
Useful references/tutorials
• http://embarcaderos.net/2011/01/23/parallel
-processing-and-multi-core-utilization-withjava/
• http://openjdk.java.net/groups/hotspot/docs/
RuntimeOverview.html
• http://www.vogella.com/tutorials/JavaConcur
rency/article.html
Download