The Artima Developer Community

Objects and Patterns Workshop
Designing with Exceptions and Threads

Agenda


Broken Semantic Contract


Discussion


Abnormal Conditions


Example: FileInputStream

 1 // In file ex9/Example9a.java
 2 import java.io.*;
 3 class Example9a {
 4
 5     public static void main(String[] args)
 6         throws IOException {
 7
 8         if (args.length == 0) {
 9             System.out.println("Must give filename as first arg.");
10             return;
11         }
12
13         FileInputStream in;
14         try {
15             in = new FileInputStream(args[0]);
16         }
17         catch (FileNotFoundException e) {
18             System.out.println("Can't find file: " + args[0]);
19             return;
20         }
21
22         int ch;
23         while ((ch = in.read()) != -1) {
24             System.out.print((char) ch);
25         }
26         System.out.println();
27
28         in.close();
29     }
30

Example: StringTokenizer and Stack

 1 // In file ex9/Example9c.java
 2 // This program prints the white-space separated tokens of an
 3 // ASCII file in reverse order of their appearance in the file.
 4 import java.io.*;
 5 import java.util.*;
 6 class Example9c {
 7
 8     public static void main(String[] args)
 9         throws IOException {
10
11         if (args.length == 0) {
12             System.out.println("Must give filename as first arg.");
13             return;
14         }
15
16         FileInputStream in = null;
17         try {
18             in = new FileInputStream(args[0]);
19         }
20         catch (FileNotFoundException e) {
21             System.out.println("Can't find file: " + args[0]);
22             return;
23         }
24
25         // Read file into a StringBuffer
26         StringBuffer buf = new StringBuffer();
27         try {
28             int ch;
29             while ((ch = in.read()) != -1) {
30                 buf.append((char) ch);
31             }
32         }
33         finally {
34             in.close();
35         }
36
37         // Separate StringBuffer into tokens and
38         // push each token into a Stack
39         StringTokenizer tok = new StringTokenizer(buf.toString());
40         Stack stack = new Stack();
41         while (tok.hasMoreTokens()) {
42             stack.push(tok.nextToken());
43         }
44
45         // Print out tokens in reverse order.
46         while (!stack.empty()) {
47             System.out.println((String) stack.pop());
48         }
49     }
50

Why Just Abnormal Conditions?


Discussion


Exceptions and throws


Checked versus Unchecked


Exceptions In Your Face


Why Checked Exceptions?


Discussion


Exception Classes


Why Exception Classes?


Discussion


The Thread-Safe Object

 1 // In file objectidioms/ex6/RGBColor.java
 2 // Instances of this class are NOT thread-safe.
 3
 4 public class RGBColor {
 5
 6     private int r;
 7     private int g;
 8     private int b;
 9
10     public RGBColor(int r, int g, int b) {
11
12         checkRGBVals(r, g, b);
13
14         this.r = r;
15         this.g = g;
16         this.b = b;
17     }
18
19     public void setColor(int r, int g, int b) {
20
21         checkRGBVals(r, g, b);
22
23         this.r = r;
24         this.g = g;
25         this.b = b;
26     }
27
28     /**
29     * returns color in an array of three ints: R, G, and B
30     */
31     public int[] getColor() {
32
33         int[] retVal = new int[3];
34         retVal[0] = r;
35         retVal[1] = g;
36         retVal[2] = b;
37
38         return retVal;
39     }
40
41     public void invert() {
42
43         r = 255 - r;
44         g = 255 - g;
45         b = 255 - b;
46     }
47
48     private static void checkRGBVals(int r, int g, int b) {
49
50         if (r < 0 || r > 255 || g < 0 || g > 255 ||
51             b < 0 || b > 255) {
52
53             throw new IllegalArgumentException();
54         }
55     }
56 }

Write/Write Conflicts

Thread Statement r g b Color
none object represents green 0 255 0  GREEN 
blue blue thread invokes setColor(0, 0, 255) 0 255 0  GREEN 
blue checkRGBVals(0, 0, 255); 0 255 0  GREEN 
blue this.r = 0; 0 255 0  GREEN 
blue this.g = 0; 0 255 0  GREEN 
blue blue gets preempted 0 0 0  BLACK 
red red thread invokes setColor(255, 0, 0) 0 0 0  BLACK 
red checkRGBVals(255, 0, 0); 0 0 0  BLACK 
red this.r = 255; 0 0 0  BLACK 
red this.g = 0; 255 0 0  RED 
red this.b = 0; 255 0 0  RED 
red red thread returns 255 0 0  RED 
blue later, blue thread continues 255 0 0  RED 
blue this.b = 255 255 0 0  RED 
blue blue thread returns 255 0 255  MAGENTA 
none object represents magenta 255 0 255  MAGENTA 

Read/Write Conflicts

Thread Statement r g b Color
none object represents green 0 255 0  GREEN 
blue blue thread invokes setColor(0, 0, 255) 0 255 0  GREEN 
blue checkRGBVals(0, 0, 255); 0 255 0  GREEN 
blue this.r = 0; 0 255 0  GREEN 
blue this.g = 0; 0 255 0  GREEN 
blue blue gets preempted 0 0 0  BLACK 
red red thread invokes getColor() 0 0 0  BLACK 
red int[] retVal = new int[3]; 0 0 0  BLACK 
red retVal[0] = 0; 0 0 0  BLACK 
red retVal[1] = 0; 0 0 0  BLACK 
red retVal[2] = 0; 0 0 0  BLACK 
red return retVal; 0 0 0  BLACK 
red red thread returns black 0 0 0  BLACK 
blue later, blue thread continues 0 0 0  BLACK 
blue this.b = 255 0 0 0  BLACK 
blue blue thread returns 0 0 255  BLUE 
none object represents blue 0 0 255  BLUE 

Thread-Safe RGBColor Object

 1 // In file objectidioms/ex7/RGBColor.java
 2 // Instances of this class are thread-safe.
 3
 4 public class RGBColor {
 5
 6     private int r;
 7     private int g;
 8     private int b;
 9
10     public RGBColor(int r, int g, int b) {
11
12         checkRGBVals(r, g, b);
13
14         this.r = r;
15         this.g = g;
16         this.b = b;
17     }
18
19     public void setColor(int r, int g, int b) {
20
21         checkRGBVals(r, g, b);
22
23         synchronized (this) {
24
25             this.r = r;
26             this.g = g;
27             this.b = b;
28         }
29     }
30
31     /**
32     * returns color in an array of three ints: R, G, and B
33     */
34     public int[] getColor() {
35
36         int[] retVal = new int[3];
37
38         synchronized (this) {
39
40             retVal[0] = r;
41             retVal[1] = g;
42             retVal[2] = b;
43         }
44
45         return retVal;
46     }
47
48     public synchronized void invert() {
49
50         r = 255 - r;
51         g = 255 - g;
52         b = 255 - b;
53     }
54
55     private static void checkRGBVals(int r, int g, int b) {
56
57         if (r < 0 || r > 255 || g < 0 || g > 255 ||
58             b < 0 || b > 255) {
59
60             throw new IllegalArgumentException();
61         }
62     }
63 }

Ready for Threads

Thread Statement r g b Color
none object represents green 0 255 0  GREEN 
blue blue thread invokes setColor(0, 0, 255) 0 255 0  GREEN 
blue checkRGBVals(0, 0, 255); 0 255 0  GREEN 
blue blue thread acquires lock 0 255 0  GREEN 
blue this.r = 0; 0 255 0  GREEN 
blue this.g = 0; 0 255 0  GREEN 
blue blue gets preempted 0 0 0  BLACK 
red red thread invokes setColor(255, 0, 0) 0 0 0  BLACK 
red checkRGBVals(255, 0, 0); 0 0 0  BLACK 
red red thread blocks because object locked 0 0 0  BLACK 
blue later, blue thread continues 0 0 0  BLACK 
blue this.b = 255 0 0 0  BLACK 
blue blue thread returns and releases lock 0 0 255  BLUE 
red later, red thread acquires lock and continues 0 0 255  BLUE 
red this.r = 255; 0 0 255  BLUE 
red this.g = 0; 255 0 255  MAGENTA 
red this.b = 0; 255 0 255  MAGENTA 
red red thread returns and releases lock 255 0 0  RED 
none object represents red 255 0 0  RED 

The Thread-Safe Object


Discussion


Copyright © 1996-2019 Artima, Inc. All Rights Reserved. - Privacy Policy - Terms of Use