Checked exeptions look very usefull for API designers and useless for API users, doe's not it ?
> You missed the correct solution in your logging > example. Obviously, various implementations will > throw different sets of exceptions so the right way to > handle it is to create a checked LoggingException and > throw that from the log methods. The implementations > will wrap their exceptions in LoggingExceptions. This > keeps all of the advantages of checked exception > handling without resorting to throwing/catching > Exception. > > RuntimeExceptions indicate programmer error. In rare > cases they are thrown when you must bypass several > application layers (see SecurityException for an > example). > > David > > --- Rodney Waldhoff <[EMAIL PROTECTED]> wrote: > > I'm not sure that "ownership" necessarily enters > > into it, but here's some > > concrete examples: > > > > Consider a simple logging API: > > > > interface Log { > > void debug(String message); > > void info(String message); > > void fatal(String message); > > } > > > > One implementation of that interface might write the > > output to standard > > out. Since System.out (java.io.PrintStream I guess) > > never throws a > > checked exception, there's no need to ever throw a > > checked exception from > > that implementation or that interface. > > > > Another implementation of that interface might write > > to some external > > file. Any of those write calls might throw an > > IOException, in which case > > I should add "throws IOException" to all of my > > logging methods unless I'm > > gonna swallow all of those exceptions (while > > swallowing exceptions *might* > > be OK in the logging case, it certainly isn't OK in > > the general case). > > > > interface Log { > > void debug(String message) throws IOException; > > void info(String message) throws IOException; > > void fatal(String message) throws IOException; > > } > > > > Now even if I'm using a System.out logger, I've got > > to catch or throw > > IOException, just in case. > > > > Yet another implementation of that interface might > > write log messages to a > > database. Any of those insert statements might > > throw a SQLException, in > > which case I should add "throws SQLException" to all > > my logging methods: > > > > interface Log { > > void debug(String message) throws IOException, > > SQLException; > > void info(String message) throws IOException, > > SQLException; > > void fatal(String message) throws IOException, > > SQLException; > > } > > > > Of course, I'll never be able to anticipate all of > > the specific types of > > Exception that might be thrown. I may as well drop > > back to the general > > case: > > > > interface Log { > > void debug(String message) throws Exception; > > void info(String message) throws Exception; > > void fatal(String message) throws Exception; > > } > > > > but now I have all of the disadvantages of checked > > exceptions--I need to > > explictly catch or throw Exception every time I > > invoke one of these > > methods--but none of the advantages of checked > > exceptions--I don't have > > any guarentee that the specific type of exception > > that might be throw by > > the implementation code is going to be specifically > > handled by the calling > > code. How's this any better than RuntimeException? > > > > As another example, consider java.util.Iterator. I > > can do lots of useful > > things with Iterators (chain them, filter them, > > transform them, apply some > > function to each element within the iteration, > > etc.). One source of > > Iterators is the Collections API. But it's not > > difficult to create an > > Iterator from other sources--say an Iterator over > > the lines in a file: > > > > class LineIterator implements Iterator { > > LineIterator(BufferedReader reader) { > > this.reader = reader; > > } > > > > Object next() { > > if(hasNext()) { > > nextSet = false; > > return nextLine; > > } else { > > throw new NoSuchElementException(); > > } > > } > > > > boolean hasNext() { > > if(!nextSet) { > > setNext(); > > } > > return nextLine != null; > > } > > > > private setNext() throws IOException { > > nextLine = reader.readLine(); > > nextSet = true; > > } > > > > private Reader reader; > > private String nextLine; > > private boolean nextSet = false; > > } > > > > or the values in some column in a database table: > > > > class ColumnIterator implements Iterator { > > ColumnIterator(ResultSet rset, int column) { > > this.rset = rset; > > this.column = column; > > } > > > > Object next() { > > if(hasNext()) { > > nextSet = false; > > return next; > > } else { > > throw new NoSuchElementException(); > > } > > } > > > > boolean hasNext() { > > if(!nextSet) { > > setNext(); > > } > > return nextSet; > > } > > > > private setNext() throws SQLException { > > if(rset.next()) { > > next = rset.getString(column); > > nextSet = true; > > } else { > > nextSet = false; > > } > > } > > > > private ResultSet rset; > > private int column; > > private Object next; > > private boolean nextSet = false; > > } > > > > Of course, those don't quite work because the > > checked IOExceptions and > > SQLExceptions aren't being handled. In theory, one > > could add "throws > > Exception" to all of the Iterator methods (subject > > to the limitations > > above), but in practice that's not going to happen. > > > > Why not just throw RuntimeException in this case > > (and ignore the tunneling > > concept)? Because there are times when I might be > > able to handle or > > announce the underlying cause: > > > > // process the commands in the given stream, > > ignoring lines that start > > with # > > void processCommandStream(Reader in) throws > > IOException { > > UnaryPredicate startsWithHash = new > > UnaryPredicate() { > > public boolean evaluate(Object obj) { > > return ((String)obj).startsWith("#"); > > } > > } > > > > Iterator iterator = new FilteringIterator( > > new NotPredicate(startsWithHash), > > new LineIterator(in)); > > > > try { > > while(iterator.hasNext()) { > > processCommand((String)iterator.next()); > > } > > } catch(TunneledException e) { > > if(e.getException() instanceof IOException) { > > throw (IOException)(e.getException()); > > } > > } > > > === message truncated === > > > __________________________________ > Do you Yahoo!? > SBC Yahoo! DSL - Now only $29.95 per month! > http://sbc.yahoo.com > > --------------------------------------------------------------------- > To unsubscribe, e-mail: [EMAIL PROTECTED] > For additional commands, e-mail: [EMAIL PROTECTED] > > --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]