concurrency
play

Concurrency http://csunplugged.org/routing-and-deadlock - PowerPoint PPT Presentation

Concurrency http://csunplugged.org/routing-and-deadlock Fundamentals of Computer Science Outline Multi-threaded programs Multiple simultaneous paths of execution Seemingly at once (single core) Actually at the same time (multiple


  1. Concurrency http://csunplugged.org/routing-and-deadlock Fundamentals of Computer Science

  2. Outline  Multi-threaded programs  Multiple simultaneous paths of execution  Seemingly at once (single core)  Actually at the same time (multiple cores)  Concurrency issues  The dark side of threading  Unpredictability of thread scheduler  Protecting shared data:  synchronized methods  Deadlock  The really dark side of threading

  3. Review: Creating & Starting a Thread public class BlastOff implements Runnable { public void run() { for ( int i = 10; i > 0; i--) System. out.print (i + " "); System. out.println ("BLAST OFF!"); } public class Launch } { public static void main(String [] args) { System. out.println ("prepare for launch"); Thread thread = new Thread( new BlastOff()); thread.start(); System. out.println ("done with launch"); } } % java Launch % java Launch prepare for launch prepare for launch done with launch 10 9 done with launch 10 9 8 7 6 5 4 3 2 1 BLAST OFF! 8 7 6 5 4 3 2 1 BLAST OFF! % java Launch prepare for launch … 10 done with launch 9 8 7 6 5 4 3 2 1 BLAST OFF!

  4. Review: Multithreading for Speed  Goal: Count how often different integers occur  In a large array of integers  Randomly generated in [0, 100)  Have one thread handle each target integer % java ParallelSearch 1000000 2 7 16 42 99 Starting workers... Count of 2 = 9888 Count of 7 = 10222 Count of 16 = 9989 Count of 42 = 10099 Count of 99 = 9894

  5. public class SearchWorker implements Runnable { private int target = 0; private int [] data = null ; private int result = 0; public SearchWorker( int target, int [] data) { this .target = target; this .data = data; } Worker object: One of these is created for each target public int getResult() { integer we want to search for. return result; } Needs to keep track of its input: what number to search for, the array to search public int getTarget() { in. return target; } Must remember its output: count of the target in the array. public void run() { for ( int i = 0; i < data.length; i++) { if (data[i] == target) result++; } } }

  6. ... final int DATA_SIZE = Integer. parseInt (args[0]); final int WORKERS = args.length - 1; int [] data = new int [DATA_SIZE]; for ( int i = 0; i < DATA_SIZE; i++) data[i] = ( int ) (Math. random() * 100); SearchWorker [] workers = new SearchWorker[WORKERS]; Thread [] threads = new Thread[WORKERS]; for ( int i = 0; i < WORKERS; i++) { workers[i] = new SearchWorker(Integer. parseInt (args[i + 1]), data); threads[i] = new Thread(workers[i]); threads[i].start(); } Client program: 1. Parses command line arguments. for ( int i = 0; i < WORKERS; i++) { 2. Creates random array of data to search try in. { 3. Creates each worker, launches each threads[i].join(); } worker in its own thread. catch (InterruptedException e) 4. Waits for each thread to finish, printing { out the worker’s result. e.printStackTrace(); } System. out .printf("Count of %d = %d\n", workers[i].getTarget(), workers[i].getResult()); } ...

  7. Trouble in Concurrency City: Act 1  Lost update problem  Multiple threads  All sharing a single counter object  Each thread increments fixed number of times public class Count public class IncrementWorker implements Runnable { { private int count = 0; private Count count = null ; public int getCount() public IncrementWorker(Count count) { { return count; this .count = count; } } public void increment() public void run() { { count++; for ( int i = 0; i < 1000; i++) } count.increment(); } } }

  8. Lost Update Problem ... Count count = new Count(); Thread [] threads = new Thread[N]; for ( int i = 0; i < N; i++) { threads[i] = new Thread( new IncrementWorker(count)); threads[i].start(); % java Increment 1 } Final count = 1000 for ( int i = 0; i < N; i++) % java Increment 2 { Final count = 2000 try { % java Increment 20 threads[i].join(); Final count = 20000 } catch (InterruptedException e) % java Increment 20 { Final count = 19761 e.printStackTrace(); } % java Increment 20 } Final count = 19014 System. out .println("Final count = " + count.getCount()); ...

  9. Synchronizing Methods  Only allow 1 worker in increment at a time!  Tell Java this using synchronized keyword public class Count { private int count = 0; public int getCount() { return count; } public synchronized void increment() % java Increment 20 { Final count = 20000 count++; } % java Increment 20 } Final count = 20000 % java Increment 20 Final count = 20000

  10. Locking an Object  Each object instance has a lock  Multiple methods can be marked synchronized  Only one can be executing at any time  Locking is on the object level  On the instance of the class, not the class data type itself  Locking and unlocking takes time  Only synchronize methods if necessary public void run() { Another approach to fixing the for ( int i = 0; i < 1000; i++) { lost update problem. synchronized (count) { Synchronization can be count.increment(); enforced on a block of code } instead of an entire method. } }

  11. Trouble in Concurrency City: Act 2  Concurrent access to same data structure  Many built-in containers are not thread-safe!  e.g. ArrayList , HashMap  Program will crash (probably)  Protect all reading/writing to shared structure  Via synchronized method or synchronized code block

  12. public class ArrayListBad implements Runnable { private static ArrayList<Integer> list = new ArrayList<Integer>(); public void run() { for ( int i = 0; i < 10; i++) { list .add((int) (Math.random() * 100)); } System. out .println("Thread all done..."); } public static void main(String[] args) { Thread t1 = new Thread( new ArrayListBad()); t1.start(); Thread t2 = new Thread( new ArrayListBad()); t2.start(); May sometimes work, especially if loop in run() is short. try { But most likely you’ll get some sort of t1.join(); t2.join(); exception: } catch (InterruptedException e) Exception in thread "Thread-1" { Thread all done... java.lang.ArrayIndexOutOfBoundsException: 15 e.printStackTrace(); at java.util.ArrayList.add(Unknown Source) } at ArrayListBad.run(ArrayListBad.java:12) System. out .println("Phew, we made it!"); at java.lang.Thread.run(Unknown Source) } Phew, we made it! } 12

  13. public class ArrayListGood implements Runnable { private static ArrayList<Integer> list = new ArrayList<Integer>(); public void run() { for ( int i = 0; i < 100000; i++) { synchronized ( list) { list .add((int) (Math.random() * 100)); } } System. out .println("Thread all done..."); } ... Adding synchronized block protects the shared static list instance variable, now only one thread is allowed to add to the list at any point in time. 13

  14. Trouble in Concurrency City: Act 3  Deadlock  Program stops doing anything useful  All you need is 2 objects and 2 threads

  15. Summary  Multi-threaded programs  Multiple simultaneous paths of execution  Seemingly at once (single core)  Actually at the same time (multiple cores)  Concurrency issues  The dark side of threading  Unpredictability of thread scheduler  Protecting shared data:  synchronized methods  Deadlock  The really dark side of threading

  16. Hands On Exercise  Goal: Increment/decrement all ints in an array Create class NumHolder , holds array of 100 ints   Create increment() and decrement() methods  Methods that go through all 100 integers and ++ or -- them  Create run() method  Loop 1000 times, each loop flip coin and call either increment() or decrement() Create main program in NumHolderLaunch   Create a single NumHolder object  Create two threads, passing them the NumHolder object you created  Print out NumHolder object  Start threads, wait for them to finish  Print out NumHolder again Hint: All numbers should be the same in the second print of NumHolder   Open Moodle, go to CSCI 136, Section 11  Open the dropbox In-Class Exercise 8  Drag and drop your program file to the Moodle dropbox  You get: 1 point if you turn in something, 2 points if you turn in something that is correct.

Recommend


More recommend