<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-7033735639680913694</id><updated>2012-02-28T11:28:37.828-08:00</updated><category term='Neil Gershenfeld'/><category term='virtualization'/><category term='SuperComputing'/><category term='Fortress'/><category term='SpringMVC'/><category term='clojure'/><category term='gchartjava'/><category term='Spring Framework'/><category term='manycore'/><category term='tomcat'/><category term='Stackoverflow'/><category term='google chart api'/><category term='conference'/><category term='Qwest'/><category term='Apple'/><category term='osx'/><category term='OSS'/><category term='statics'/><category term='exceptions'/><category term='iPod'/><category term='Objective-C'/><category term='Bits and Atoms'/><category term='Mac'/><category term='nfs'/><category term='Apache'/><category term='charts4j'/><category term='Spring'/><category term='Rockies'/><category term='Flytunes'/><category term='Mac Mini'/><category term='X10'/><category term='reno'/><category term='collaborative media'/><category term='visualization'/><category term='BJUG'/><category term='charts'/><category term='wrapper'/><category term='threads'/><category term='Internet'/><category term='workshop'/><category term='World Series'/><category term='forethought.net'/><category term='java'/><category term='wifi'/><category term='JSON Java Spring AJAX YUI Annotations'/><category term='tickets'/><category term='keynote'/><category term='sorting'/><category term='music'/><category term='multicore'/><category term='HPC'/><category term='Whirlpool'/><category term='Roku'/><category term='Home Network'/><category term='YUI'/><category term='fiasco'/><category term='concurrency'/><category term='chart'/><category term='book'/><category term='tip'/><category term='cilk'/><category term='iPhone'/><category term='iTunes'/><category term='Firebug'/><category term='sc07'/><category term='generics'/><category term='Internet Radio'/><category term='Cocoa'/><category term='YSlow'/><category term='collections'/><category term='Zoom Modem'/><category term='Rubik&apos;s Cube'/><category term='ASP.net'/><category term='molecular biology'/><category term='google'/><category term='java generics'/><title type='text'>Radio Eiffel</title><subtitle type='html'></subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>25</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-729563942878849393</id><published>2009-03-31T21:31:00.001-07:00</published><updated>2009-03-31T21:53:21.459-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JSON Java Spring AJAX YUI Annotations'/><title type='text'>An Annotated AJAX (via JSON) Spring Controller</title><content type='html'>&lt;div&gt;Because I could not find an example of an annotated Spring AJAX (via JSON) controller in Google, I forged ahead and figured this one out on my own. I thought I would share this code snippet with the blogosphere. Without further ceremony here is the code example:&lt;br /&gt;&lt;br /&gt;&lt;PRE&gt;&lt;br /&gt;@Controller&lt;br /&gt;public class AjaxController {&lt;br /&gt; @RequestMapping("/index")&lt;br /&gt;     public void handler(@RequestParam("myParam") Object myParam, &lt;br /&gt;HttpServletResponse response) {&lt;br /&gt;             JSONObject json = new JSONObject();&lt;br /&gt;             json.putAll(getMyData(myParam));&lt;br /&gt;             response.setContentType("application/json");&lt;br /&gt;             response.setHeader("Cache-Control", "no-cache");&lt;br /&gt;             response.getWriter().write(json.toJSONString());&lt;br /&gt;       }&lt;br /&gt;}&lt;br /&gt;&lt;/PRE&gt;&lt;br /&gt;&lt;br /&gt;The URL request mapping is specified with the &lt;span style="font-family:Courier New;"&gt;RequestMapping&lt;/span&gt; annotation. Make sure the path is accessible by properly configuring with web.xml with the correct &lt;span style="font-family:Courier New;"&gt;servlet-mapping&lt;/span&gt;. Note that the annotated Spring controller offers tremendous flexibility with respect to the method signature. We can leverage this feature for building the AJAX request handler method. Moreover, you can specify the required URL parameters via the &lt;span style="font-family:Courier New;"&gt;RequestParam&lt;/span&gt; annotation and bind them to the method arguments. Lastly, you will need the &lt;span style="font-family:Courier New;"&gt;HttpServletResponse&lt;/span&gt; object for the JSON response. Notice that the method returns &lt;span style="font-family:Courier New;"&gt;void&lt;/span&gt; because the JSON response is returned via the response object.&lt;/div&gt;&lt;br /&gt;&lt;div&gt;The JSON library I used can be found &lt;a title="here" href="http://code.google.com/p/json-simple/" id="bixj"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Handle the JSON in the browser with your favorite JavaScript library (e.g. &lt;a title="YUI" href="http://developer.yahoo.com/yui/" id="vp_v"&gt;YUI&lt;/a&gt;).&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-729563942878849393?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/729563942878849393/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=729563942878849393' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/729563942878849393'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/729563942878849393'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2009/03/annotated-ajax-via-json-spring.html' title='An Annotated AJAX (via JSON) Spring Controller'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-4873094004814341689</id><published>2009-02-15T21:03:00.001-08:00</published><updated>2011-08-13T15:11:01.270-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Rubik&apos;s Cube'/><category scheme='http://www.blogger.com/atom/ns#' term='google chart api'/><category scheme='http://www.blogger.com/atom/ns#' term='google'/><title type='text'>Google Threw Me a Bone</title><content type='html'>&lt;p&gt;&lt;/p&gt;&lt;div id="le92" style="padding: 1em 0pt; text-align: left;"&gt;&lt;img style="width: 550px; height: 412px;" src="http://docs.google.com/File?id=df88fvbt_29hdgk3fg6_b" /&gt;&lt;/div&gt;This past week I received a package from Google - 1600 Amphitheatre Parkway Mountain View, CA 94043. That's right, Google. I&lt;br /&gt;was unaware that Google knew of the existence of the USPS, considering it a communication mechanism from the time of Neanderthals.&lt;br /&gt;&lt;p&gt;I opened it to reveal:&lt;/p&gt;&lt;ul&gt;&lt;li&gt;A Rubik's Cube&lt;/li&gt;&lt;li&gt;A mouse pad&lt;/li&gt;&lt;li&gt;A pen&lt;/li&gt;&lt;li&gt;A "My Other Computer is a Data Center" bumper sticker&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;All were emblazoned with the Google logo.&lt;/p&gt;&lt;p&gt;And a thank you note hand written with excellent penmanship. They sent me some Google schwag as a token of their appreciation for the contributions I have made to the Google Chart API -- both on the &lt;a title="group list" href="http://groups.google.com/groups/profile?enc_user=WRzF3RsAAABglNAmOd2Xy8fiudJWmGqBJMKBSZEm-SPGtmJX6z_DdA" id="onya"&gt;group list&lt;/a&gt;  and the wrapper API I developed, &lt;a title="charts4j" href="http://charts4j.googlecode.com/" id="itk_"&gt;charts4j&lt;/a&gt; .&lt;br /&gt;&lt;/p&gt;&lt;p&gt;There is no name to reveal who sent it.&lt;br /&gt;&lt;/p&gt;&lt;p&gt;At any rate, in the extremely unlikely possibility the person that sent this to me is reading this blog post (I think I am the only one who reads my blog, except for &lt;a title="Newwest" href="http://newwest.net/books" id="bxfz"&gt;my wife&lt;/a&gt;), thanks for the schwag, especially the Rubik's cube.&lt;/p&gt;&lt;p&gt;&lt;/p&gt;&lt;div id="i_oh" style="padding: 1em 0pt; text-align: left;"&gt;&lt;img style="width: 550px; height: 412px;" src="http://docs.google.com/File?id=df88fvbt_30dfk373cj_b" /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-4873094004814341689?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/4873094004814341689/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=4873094004814341689' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4873094004814341689'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4873094004814341689'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2009/02/google-threw-me-bone.html' title='Google Threw Me a Bone'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-1532520335907304744</id><published>2009-02-11T22:13:00.001-08:00</published><updated>2009-02-11T22:15:20.368-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='generics'/><category scheme='http://www.blogger.com/atom/ns#' term='sorting'/><title type='text'>What? Java Can't Sort Numbers?</title><content type='html'>&lt;div&gt;I was recently working on some &lt;a id="xvkr" title="charts4j" href="http://code.google.com/p/charts4j/"&gt;charts4j&lt;/a&gt; code to sort a list of Numbers (java.lang.Numbers -- to be exact) and discovered that it could not be done simply by calling &lt;a id="amos" title="Collections.sort" href="http://java.sun.com/javase/6/docs/api/java/util/Collections.html#sort%28java.util.List%29"&gt;Collections.sort&lt;/a&gt;. I would think, if anything ought to be sortable in Java, it should be a list of Numbers. &lt;/div&gt;&lt;br /&gt;&lt;div&gt;As most Java programmers know, sorting lists in Java is easy -- sort of. "Simply" use the static Collections.sort method, which under the hood is implemented with the classic merge sort algorithm.  The major caveat, of course, is that the class of objects you are sorting must implement the &lt;a id="tzto" title="Comparable" href="http://java.sun.com/javase/6/docs/api/java/lang/Comparable.html"&gt;Comparable&lt;/a&gt; interface by having a properly written &lt;a id="z4t9" title="compareTo" href="http://java.sun.com/javase/6/docs/api/java/lang/Comparable.html#compareTo%28T%29"&gt;compareTo&lt;/a&gt; method. Fortunately, many classes in the core Java language already implement Comparable: String, Date, Integer. They can immediately be sorted with Collections.sort without any special effort from the programmer, but not for Numbers. I did a little research by posting a question on &lt;a id="o_lg" title="this topic on Stackoverflow" href="http://stackoverflow.com/questions/480632/why-doesnt-java-lang-number-implement-comparable"&gt;this topic on Stackoverflow&lt;/a&gt;. I received a lot of good albeit -- Sun party line -- answers. The issue is a bit more complex than one would immediately think.&lt;/div&gt;&lt;br /&gt;&lt;div&gt;The simplest explanation for why java.lang.Number does not implement Comparable is rooted in mutability concerns. For a bit of review, java.lang.Number is the abstract super-type of AtomicInteger, AtomicLong, BigDecimal, BigInteger, Byte, Double, Float, Integer, Long, Short. On that list, AtomicInteger and AtomicLong to do not implement Comparable. Digging around, I discovered that it is not a good practice to implement Comparable on mutable types because the objects can change during or after comparison rendering the result of the comparison useless. Both AtomicLong and AtomicInteger are mutable. The API designers had the forethought to not have Number implement Comparable because it would have constrained implementation of future subtypes. Indeed, AtomicLong and AtomicInteger were added in Java 1.5 long after java.lang.Number was initially implemented.&lt;/div&gt;&lt;br /&gt;&lt;div&gt;Apart from mutability, there are probably other considerations here too. A compareTo implementation in Number would have to promote all numeric values to BigDecimal because it is capable of accommodating all the Number sub-types. The implication of that promotion in terms of mathematics and performance is a bit unclear to me, but my intuition finds that solution kludgy.&lt;/div&gt;&lt;br /&gt;&lt;div&gt;&lt;/div&gt;&lt;div&gt;A related issue to this discussion is autoboxing. In Java 1.5, Sun introduced this language feature to seamlessly go back and forth between primitive numeric types and reference types. This is useful for adding and getting numbers in and out of Collections, for example, without having to explicitly convert the primitive type to a reference type. The Java numeric primitive types are byte, char, short, int, float, and double. They all have corresponding reference types, Byte, Character, Short, etc. Those reference types all extend Number (except for Character). The rules for converting from primitive types to boxed reference types are difficult to anticipate for purposes of building APIs. (I thought Java 1.5 was supposed to be all about type safety.) For instance, Arrays.asList(1,2,3) yields a List&amp;lt;Integer&amp;gt; and not a List&amp;lt;Long&amp;gt;. Arrays.asList(1.0,2,3) produces a List&amp;lt;? extends Number&amp;gt; instead of a List&amp;lt;Double&amp;gt;. This lack of predictability is burdensome for API designers, because they essentially have to build multiple method signatures to accommodate multiple boxed numeric reference types. Overloading the method signature may not even be an option in the case of Collections since List&amp;lt;Integer&amp;gt; and List&amp;lt;? extends Number&amp;gt; have the same erasure. One possibility is to rely only on the Number type or in the case of Collections List&amp;lt;? extends Number&amp;gt; for polymorphism but the problem is that the Number type is too general, encompassing more than the Java boxed primitive types, and it does not implement Comparable.&lt;/div&gt;&lt;br /&gt;&lt;div&gt;A potential solution is to implement an intermediate RealNumber type that would extend Number and encompass all the boxed numeric primitive types (except for char). This approach would allow polymorphism on numeric primitive types via autoboxing. Moreover, it would be reasonable for this RealNumber type to implement Comparable by promoting primitive numeric types to double in the compareTo method.&lt;/div&gt;&lt;br /&gt;&lt;div&gt;Unfortunately, this is yet another example of how Java has never been great in the numerical computation arena.&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-1532520335907304744?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/1532520335907304744/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=1532520335907304744' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1532520335907304744'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1532520335907304744'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2009/02/what-java-can-sort-numbers.html' title='What? Java Can&amp;#39;t Sort Numbers?'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-2983392017571437403</id><published>2009-01-28T22:35:00.001-08:00</published><updated>2009-01-28T22:43:02.401-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='BJUG'/><category scheme='http://www.blogger.com/atom/ns#' term='iPhone'/><category scheme='http://www.blogger.com/atom/ns#' term='Objective-C'/><category scheme='http://www.blogger.com/atom/ns#' term='Cocoa'/><title type='text'>The iPhone Changes the Game for Small Independent Software Vendors</title><content type='html'>Over the years at the &lt;a title="Boulder Java User Group" href="http://www.boulderjug.org/" id="y5ms"&gt;Boulder Java User Group&lt;/a&gt;, I have discovered many technologies that have eventually played an important role in my daily software development, YUI or YSlow, for example. Matthew McCullough's fascinating talk earlier this month on iPhone development may&lt;br /&gt;eventually turn out to have been another influential moment.&lt;br /&gt;&lt;br /&gt;For a bit of background, last year Apple finally opened up the iPhone platform to non-Apple developers. This sea change reveals a vast and relatively unexplored landscape for software developers where there are probably many good ideas ripe for the picking. In addition, iPhone's smart phone market share is large and growing rapidly potentially providing many customers for iPhone developers. The revenue model is also tantalizing; developers may sell their applications at the iTunes store -- an extremely high visibility marketplace. I know of no other high profile online store where small independent developers have relatively easy access to huge audiences. Of course, this scenario makes the rosy assumption that Apple will approve the application for sale at the iTunes store. Nevertheless, this possibility is better than the alternatives. Hopefully, we will be seeing more of these high visibility online software bazaars.&lt;br /&gt;&lt;br /&gt;Contrast this situation to the web application arena, where it seems every good idea has been already explored, not to mention the fact that the competition is cut throat, and the revenue model usually depends on mega traffic, which is difficult if not almost impossible to attain. Overall, it remains extremely difficult to break through and get attention in the web application world.&lt;br /&gt;&lt;br /&gt;As a consequence, Matt's BJUG talk certainly whet my appetite for iPhone development.  The major caveat, of course, is developers such as myself must learn Cocoa and Objective-C, which is not a small feat. Back in 2003, I became interested in Objective-C and Cocoa development when OS X and the iPod were really becoming popular. I spent about a year tooling around during evenings and weekends learning Objective-C and Cocoa. While I was interested in this environment, nothing concrete ever materialized from my efforts and I moved on to other projects. At any rate, I am glad I did not toss those Cocoa and Objective-C books I purchased a few years ago. Indeed, I have been brushing up on my Cocoa as fast as I can.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-2983392017571437403?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/2983392017571437403/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=2983392017571437403' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/2983392017571437403'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/2983392017571437403'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2009/01/iphone-changes-game-for-small.html' title='The iPhone Changes the Game for Small Independent Software Vendors'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-1075325268705504427</id><published>2009-01-12T20:47:00.001-08:00</published><updated>2009-01-13T09:02:56.384-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Stackoverflow'/><category scheme='http://www.blogger.com/atom/ns#' term='ASP.net'/><category scheme='http://www.blogger.com/atom/ns#' term='Internet'/><category scheme='http://www.blogger.com/atom/ns#' term='collaborative media'/><title type='text'>Stackoverflow and the Future of Collaborative Media</title><content type='html'>&lt;div id="r-25" style="padding: 1em 0pt; text-align: left;"&gt;&lt;img style="width: 500px; height: 200px;" src="http://docs.google.com/File?id=df88fvbt_18grjdw5cj_b" /&gt;&lt;/div&gt;&lt;br /&gt;&lt;a title="Stackoverflow" href="http://stackoverflow.com/" id="eokl"&gt;Stackoverflow&lt;/a&gt;  is the collaborative media site founded by the illustrious duo, &lt;a title="Joel Spolsky" href="http://www.joelonsoftware.com/" id="nxof"&gt;Joel Spolsky&lt;/a&gt;  and &lt;a title="Jeff Atwood" href="http://www.codinghorror.com/" id="gyhn"&gt;Jeff Atwood&lt;/a&gt;. It makes a fresh and original attempt to improve the state of the online software development community, and does so mostly successfully. The site combines the best features and concepts from wikis, blogs, forums, and sites like Digg and Reddit (and perhaps a even a touch of Twitter). The result is an impressive collaborative space where developers can post questions, obtain quick answers and spark discussions.&lt;br /&gt;&lt;br /&gt;To highlight just a few Stackoverflow features:&lt;br /&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;Use of Open ID. Account creation -- often the biggest barrier for adoption for collaborative sites -- is near frictionless by leveraging this up-and-coming authentication mechanism.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Voting. Higher quality answers and topics tend to filter upwards via a voting and point scheme.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;An outstanding user interface, with plenty of rich interactivity that adds to the user experience instead of detracting from it.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;High web traffic yields quick responses and usually decent quality answers and discussions.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Questions, answers, and comments (assuming you have the credentials) are editable which means mistakes are corrected over time.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Unobtrusive ads.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;The engineering behind Stackoverflow must be outstanding. I have noticed very few odd quirks (apart from the occasional dirty cache) and it seems to be scaling fine. This is certainly more proof that the ASP.net stack is at least as good as anything offered in the Java arena, not to mention the fact that Jeff Atwood and friends are &lt;a title="extraordinary developers" href="http://stackoverflow.com/about" id="e4ee"&gt;extraordinary developers&lt;/a&gt;. They designed, implemented, and had the site up and running in just a few months. I have been fantasizing about starting a knockoff site with the Java Spring stack which would theoretically be very doable as long as you had the right talent and time. (I know, easier said than done.)&lt;br /&gt;&lt;br /&gt;Stackoverflow is not perfect, however. Question and answers can receive up and down votes, and users accumulate reputation points based on the vote count of their questions and answers. Moreover, users obtain badges as they use the system. It can become annoyingly addictive. This merit system is both an asset and a detriment. The right answers theoretically filter to the top, but Stackoverflow also biases quick answers over the best answers because the quick answer simply receives more views and points. This fact in turn incites users to provides rapid-fire answers over more thoughtful, measured responses resulting in a positive feedback loop. They may be able to partially fix these issues through some algorithmic / social engineering tweak. The reputation point system also means that users can become competitive, which leads to pettiness, incivility, and even borderline vigilantism at times. For &lt;a title="exhibit A" href="http://stackoverflow.com/questions/432922/significant-new-inventions-in-computing-since-1980" id="tbia"&gt;exhibit A&lt;/a&gt;, note the comments on the legendary (fellow University of Colorado alum) &lt;a title="Alan Kay" href="http://en.wikipedia.org/wiki/Alan_Kay" id="kjuc"&gt;Alan Kay&lt;/a&gt;'s question. Possibly a better solution is to provide a relatively low ceiling on reputation points.&lt;br /&gt;&lt;br /&gt;Searching has problems, as well, and I have even posted questions that already had answers despite a preliminary search for my question. Again, they will fix this issue eventually.&lt;br /&gt;&lt;br /&gt;The quality of the discussion is not universally great, but generally adequate and certainly better than the alternatives. For example, &lt;a title="this discussion on JavaFX" href="http://stackoverflow.com/questions/377593/javafx-is-now-out-are-applets-and-java-desktop-officially-dead-dying" id="ord1"&gt;this discussion on JavaFX&lt;/a&gt; technology partially misses the point that JavaFX is very much related and built on top of applet technology -- a fact I try to point out.&lt;br /&gt;&lt;br /&gt;At any rate, the development community is responding favorably to Stackoverflow, and the number of users is &lt;a title="growing sharply" href="http://siteanalytics.compete.com/stackoverflow.com/?metric=uv" id="xmwm"&gt;growing sharply&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Stackoverflow is the brainchild of Joel Spolsky and Jeff Atwood (actually mostly Jeff, I suspect) of software blogging fame. This effort is another example of how successful bloggers have bootstrapped other facets of their careers by using their blogs as self-promotional springboards.&lt;br /&gt;&lt;br /&gt;Stackoverflow's meteoric rise proves&lt;b&gt; there is a real hunger for collaborative spaces that don't suck&lt;/b&gt;. I predict that they are going to start spinning off other "spaces," some perhaps having nothing to do with software. Why not have cinema.stackoverflow.com, gaming.stackoverflow.com, IT.stackoverflow.com? Better yet, make those spaces integrated. For instance, if someone asks a question on the IT forum that belongs in the gaming forum, there would be a mechanism to re-assign the question to a better space. &lt;b&gt;The evolution of Stackoverflow into other domains will provide an invaluable service to many online communities whose forums currently stink&lt;/b&gt;. How many times have you looked for something on the Internet only to arrive at a forum where your question has been asked but with no answer? Or that you do not have the credentials to provide the answer and that obtaining a login is too onerous. And, of course, you are assaulted with ads along the way. I have encountered this scenario countless times, as have my colleagues. Stackoverflow's expansion into other domains will be a quantum leap in the evolution of collaborative media. An evolution that I will wholeheartedly welcome.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-1075325268705504427?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/1075325268705504427/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=1075325268705504427' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1075325268705504427'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1075325268705504427'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2009/01/stackoverflow-and-future-of.html' title='Stackoverflow and the Future of Collaborative Media'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-5383181094612065582</id><published>2008-12-15T10:16:00.001-08:00</published><updated>2008-12-30T10:53:39.058-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='Spring Framework'/><category scheme='http://www.blogger.com/atom/ns#' term='charts'/><category scheme='http://www.blogger.com/atom/ns#' term='visualization'/><category scheme='http://www.blogger.com/atom/ns#' term='google chart api'/><category scheme='http://www.blogger.com/atom/ns#' term='SpringMVC'/><category scheme='http://www.blogger.com/atom/ns#' term='charts4j'/><category scheme='http://www.blogger.com/atom/ns#' term='Spring'/><category scheme='http://www.blogger.com/atom/ns#' term='chart'/><title type='text'>Incorporating Google Charts into a Spring MVC application</title><content type='html'>&lt;div id="j2fs" style="padding: 1em 0pt; text-align: center;"&gt;&lt;div id="iy-n" style="padding: 1em 0pt; text-align: center;"&gt;&lt;div id="x_s4" style="padding: 1em 0pt;"&gt;&lt;img style="width: 500px; height: 300px;" src="http://docs.google.com/File?id=df88fvbt_14d2vmg2f3_b"&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;&lt;div style="text-align: left;"&gt;&lt;br&gt;&lt;/div&gt;&lt;br&gt;The &lt;a title="last blog post" href="http://radioeiffel.blogspot.com/2008/12/interactive-charting-with-clojure.html" id="e89-"&gt;last blog post&lt;/a&gt; on interactively building charts with Clojure generated quite a bit of interest. As a continuation of the chart theme, I will describe how to incorporate professional quality charts into a Spring MVC web application by leveraging &lt;a title="charts4j" href="http://charts4j.googlecode.com" id="lhsf"&gt;charts4j&lt;/a&gt;.&lt;br&gt;&lt;br&gt;The &lt;a title="Google Chart API" href="http://code.google.com/apis/chart/" id="y-nr"&gt;Google Chart API&lt;/a&gt; potentially provides developers a lightweight mechanism to incorporate static and dynamic charts into a web application. Dealing with the Google Chart API directly, however, is tedious and error prone. Fortunately, &lt;a title="charts4j" href="http://charts4j.googlecode.com" id="z0.b"&gt;charts4j&lt;/a&gt;, a lightweight wrapper to the Google Chart API, makes incorporating charts into your Spring web application much easier. To see examples of all the charts that can be generated with charts4j, see &lt;a title="chart gallery" href="http://charts4j.googlecode.com" id="we56"&gt;the chart gallery here&lt;/a&gt;.&lt;br&gt;&lt;br&gt;See &lt;a title="here" href="http://code.google.com/p/charts4j/downloads/list" id="y6js"&gt;here&lt;/a&gt; to download the example code that this post describes. What follows below assumes some familiarity with how to build a Spring MVC web application.&lt;br&gt;&lt;br&gt;To incorporate Google Charts into your Spring application, you will first need the standard Spring MVC infrastructure:&lt;br&gt;&lt;br&gt;&lt;ul&gt;&lt;li&gt;8 Spring framework jars and friends: commons-logging-api-1.1.jar, jstl.jar, spring-beans.jar, spring-context.jar, spring-core.jar, spring-web.jar, spring-webmvc.jar, standard.jar. Put these jars in the WEB-INF/lib directory.&lt;br&gt;&lt;/li&gt;&lt;li&gt;3 Spring and servlet XML configuration files: applicationContext.xml, frontController-servlet.xml, web.xml. Put these XML files in the WEB-INF directory.&lt;br&gt;&lt;/li&gt;&lt;/ul&gt;&lt;br&gt;Plus, you will need to write one Spring Controller, one JSP. And most importantly, also &lt;a title="charts4j jar" href="http://code.google.com/p/charts4j/downloads/list" id="pcqm"&gt;grab the charts4j jar&lt;/a&gt; and put it in WEB-INF/lib.&lt;br&gt;&lt;br&gt;Here is the controller code:&lt;br&gt;&lt;blockquote&gt;&lt;font size="1"&gt;&lt;span style="font-family: Courier New;"&gt;&lt;/span&gt;&lt;span style="font-family: Courier New;"&gt;&lt;/span&gt;&lt;/font&gt;&lt;b&gt;&lt;span style="font-family: Courier New;"&gt;@Controller&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;public class ChartController {&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; @RequestMapping("/index.html")&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public ModelAndView indexHandler() {&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; //Your really great chart.&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; final Plot plot = Plots.newPlot(Data.newData(0, 66.6, 33.3, 100));&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; final LineChart chart = GCharts.newLineChart(plot);&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; chart.setTitle("My Really Great Chart");&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; //Passing the chart to the JSP for rendering.&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return new ModelAndView().addObject("url", chart.toURLString());&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;/span&gt;&lt;/b&gt;&lt;br&gt;&lt;b&gt;&lt;span style="font-family: Courier New;"&gt;}&lt;/span&gt;&lt;/b&gt;&lt;br&gt;&lt;/blockquote&gt;&lt;br&gt;Note that I am making use of the newer style &lt;a title="annotation based Spring MVC controllers" href="http://static.springframework.org/spring/docs/2.5.x/reference/mvc.html#mvc-annotation" id="fz:i"&gt;annotation based Spring MVC controllers&lt;/a&gt;. Also, the line&lt;br&gt;&lt;br&gt;&lt;span style="font-family: Courier New;"&gt;&lt;b&gt;final Plot plot = Plots.newPlot(Data.newData(0, 66.6, 33.3, 100));&lt;/b&gt;&lt;br&gt;&lt;br&gt;&lt;/span&gt;has static, hard coded data, but the real power of this mechanism comes into play when the application &lt;b&gt;dynamically&lt;/b&gt; generates data. For example, perhaps you would like to display up-to-date stock price or weather data from your database in your web application.&lt;br&gt;&lt;br&gt;In addition, here is the JSP code:&lt;br&gt;&lt;blockquote&gt;&lt;b&gt;&lt;font size="1"&gt;&lt;span style="font-family: Courier New; background-color: rgb(255, 255, 0);"&gt;&amp;lt;%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;%@ page language="java" contentType="text/html; charset=ISO-8859-1"&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;pageEncoding="ISO-8859-1"%&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;html&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;head&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;title&amp;gt;Your great chart&amp;lt;/title&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;/head&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;body&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New; background-color: rgb(255, 255, 0);"&gt;&amp;lt;img src="${url}" alt="Chart" /&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;/body&amp;gt;&lt;/span&gt;&lt;br style="font-family: Courier New;"&gt;&lt;span style="font-family: Courier New;"&gt;&amp;lt;/html&amp;gt;&lt;/span&gt;&lt;/font&gt;&lt;/b&gt;&lt;br&gt;&lt;/blockquote&gt;&lt;br&gt;&lt;br&gt; The only noteworthy lines of code in the JSP are highlighted. To display the chart in the JSP, use an HTML &amp;lt;img&amp;gt; tag with the URL generated in the controller: &lt;span style="font-family: Courier New;"&gt;&lt;b&gt;&amp;lt;img src="${url}" alt="Chart" /&amp;gt;&lt;/b&gt;.&amp;nbsp;&lt;/span&gt;Also note that I am using the &lt;a title="JSTL EL" href="http://java.sun.com/products/jsp/jstl/index.jsp" id="catf"&gt;JSTL EL&lt;/a&gt; to access the URL string.&lt;br&gt;&lt;br&gt;&lt;i&gt;Deploy your web application and that is it. You are done.&lt;/i&gt;&lt;br&gt;&lt;br&gt;The strength of this solution is&lt;i&gt; &lt;/i&gt;its&lt;i&gt; &lt;/i&gt;&lt;b&gt;small footprint and low impact on your code base&lt;/b&gt;. To generate nice charts in your Spring MVC application, all you need is one 160 kb &lt;a title="charts4j jar" href="http://code.google.com/p/charts4j/downloads/list" id="fjxc"&gt;charts4j jar&lt;/a&gt;, an&lt;br /&gt;Internet connection, a bit of charting code and you are done. No need for special graphics libraries, extra servlet infrastructure, etc. There are many more chart examples with code samples &lt;a title="here" href="http://charts4j.googlecode.com" id="jybs"&gt;here&lt;/a&gt;.&lt;br&gt;&lt;br&gt;Finally, the Google Chart API and charts4j will satisfy many Java application charting requirements, but there are three reasons why you may not wish to choose this technology:&lt;br&gt;&lt;br&gt;&lt;ol&gt;&lt;li&gt; No Internet connection, no Google Charts. Your application &lt;b&gt;must&lt;/b&gt; be connected to the Internet because the charts are ultimately rendered by the Google Chart API.&lt;/li&gt;&lt;li&gt;There is no security with these charts. Your data will be sent as clear text over the Internet, and it would be trivial for someone to intercept this information.&lt;/li&gt;&lt;li&gt;If you have lots of data, &lt;a title="roughly speaking, more than 2000 data points" href="http://www.boutell.com/newfaq/misc/urllength.html" id="xnz1"&gt;roughly speaking, more than 2000 data points&lt;/a&gt;, you should try to sample your data less frequently, and use the simple encoding scheme. If this is not a possibility, this technology may not be right for you.&lt;/li&gt;&lt;/ol&gt;&lt;br&gt;This blog post has shown you how to incorporate &lt;a title="charts4j" href="http://charts4j.googlecode.com" id="x3u1"&gt;charts4j&lt;/a&gt; in your Spring MVC web application, but there is no reason why you cannot also incorporate charts4j in any Java application environment, as long as the three requirements above are met. Moreover, this design pattern of generating charts in the servlet layer and rendering the chart URL in the JSP will work for any Java web application environment (e.g Struts, etc.)&lt;br&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-5383181094612065582?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/5383181094612065582/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=5383181094612065582' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5383181094612065582'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5383181094612065582'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2008/12/incorporating-google-charts-into-spring.html' title='Incorporating Google Charts into a Spring MVC application'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-5266700694900420554</id><published>2008-12-02T22:08:00.001-08:00</published><updated>2008-12-02T22:58:10.278-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='charts'/><category scheme='http://www.blogger.com/atom/ns#' term='visualization'/><category scheme='http://www.blogger.com/atom/ns#' term='google chart api'/><category scheme='http://www.blogger.com/atom/ns#' term='clojure'/><category scheme='http://www.blogger.com/atom/ns#' term='charts4j'/><title type='text'>Interactive Charting with Clojure</title><content type='html'>&lt;div id="aby-" style="padding: 1em 0pt; text-align: center;"&gt;&lt;img style="width: 500px; height: 500px;" src="http://docs.google.com/File?id=df88fvbt_9d9mnzqcg_b"&gt;&lt;/div&gt;&lt;div style="text-align: left;"&gt;&lt;br&gt;&lt;/div&gt;I stumbled upon the &lt;a title="Clojure" href="http://clojure.org" id="gu15"&gt;Clojure&lt;/a&gt; programming language a few months ago when I was trolling around the Internet for topics relating to Java threading and concurrency. This Lisp and Scheme derived dynamic language runs on the JVM and has the ability to invoke Java APIs via the &lt;a title="Clojure special form sytanx" href="http://clojure.org/java_interop" id="rpha"&gt;Clojure special form syntax&lt;/a&gt;. One of Clojure's main features is its &lt;a title="strong support" href="http://clojure.org/concurrent_programming" id="usmz"&gt;strong support&lt;/a&gt; for concurrent programming, taking advantage of its bias toward immutability, and leveraging its own notion of software transactional memory in addition to invoking the java.util.concurrent API and the forthcoming &lt;a title="fork-join framework" href="http://gee.cs.oswego.edu/dl/jsr166/dist/jsr166ydocs/" id="f7_0"&gt;fork-join framework&lt;/a&gt;.&lt;br&gt;&lt;br&gt;At any rate, Clojure is dynamic and thus has an interactive shell or REPL. Because you can invoke Java APIs from the REPL, I thought it would be a fun exercise to leverage &lt;a title="charts4j" href="http://charts4j.googlecode.com/" id="yojk"&gt;charts4j&lt;/a&gt; to build charts interactively. I created the charts above and below fairly easily, certainly much easier than in a Java main program because Clojure's dynamic environment provides instant feedback. You can find the Clojure script that generated these images &lt;a title="charts4j" href="http://code.google.com/p/charts4j/downloads/list" id="yjx3"&gt;here&lt;/a&gt;.&lt;br&gt;&lt;br&gt; Simply load it with the following command: (load-file "&lt;a title="charting.clj" href="http://code.google.com/p/charts4j/downloads/list" id="ts7b"&gt;charting.clj&lt;/a&gt;"), setting your path appropriately, of course. You will also need the &lt;a title="charts4j" href="http://code.google.com/p/charts4j/downloads/list" id="v1bq"&gt;charts4j jar&lt;/a&gt; in your Clojure classpath. Moreover, you &lt;i&gt;must&lt;/i&gt; be connected to the Internet for this script to run, as the charts are ultimately rendered by the &lt;a title="Google Chart API" href="http://code.google.com/apis/chart/" id="o_a0"&gt;Google Chart API&lt;/a&gt;. It will play a slide show, and can be a starting point for generating your own charts interactively. It should be straightforward to generate all the charts available in charts4j by using that script as an example. One last important note about the charting.clj script; it works with the latest Clojure SVN revision as of the day of this blog post, but this language is still young, and the Clojure authors are still &lt;a title="fiddling with the syntax" href="http://clojure.org/java_interop#toc14" id="jm.k"&gt;fiddling with the syntax&lt;/a&gt;. Therefore, I also provide a "&lt;a title="charting-20080916.clj" href="http://code.google.com/p/charts4j/downloads/list" id="sir0"&gt;charting-20080916.clj&lt;/a&gt;" that works with the &lt;a title="official latest release" href="http://sourceforge.net/project/showfiles.php?group_id=137961" id="p:hc"&gt;official latest release&lt;/a&gt;.&lt;br&gt;&lt;br&gt;If there is enough interest, I may write a Clojure library that would make this interactive charting environment a bit easier to use, for instance by predefining more chart functions. This library could even be combined into a Clojure tutorial as programmers often respond to visual cues and eye candy as they are hacking away at code.&lt;br&gt;&lt;br&gt;For the Clojure experts out there, I would welcome feedback on my Clojure code.&lt;br&gt;&lt;div id="td7-" style="padding: 1em 0pt; text-align: center;"&gt;&lt;img style="width: 500px; height: 500px;" src="http://docs.google.com/File?id=df88fvbt_10cksvdhtc_b"&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-5266700694900420554?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/5266700694900420554/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=5266700694900420554' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5266700694900420554'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5266700694900420554'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2008/12/interactive-charting-with-clojure.html' title='Interactive Charting with Clojure'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-1472709505312178623</id><published>2008-11-18T21:08:00.001-08:00</published><updated>2008-12-01T21:34:14.077-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='charts'/><category scheme='http://www.blogger.com/atom/ns#' term='visualization'/><category scheme='http://www.blogger.com/atom/ns#' term='gchartjava'/><category scheme='http://www.blogger.com/atom/ns#' term='google chart api'/><category scheme='http://www.blogger.com/atom/ns#' term='charts4j'/><title type='text'>gchartjava moves to charts4j</title><content type='html'>&lt;div id="ugqu" style="padding: 1em 0pt; text-align: left;"&gt;&lt;img style="width: 400px; height: 400px;" src="http://docs.google.com/File?id=df88fvbt_6gqbxzkhb_b"&gt;&lt;/div&gt;&lt;br&gt;&lt;br&gt;When the &lt;a title="Google Chart API" href="http://code.google.com/apis/chart/" id="kcda"&gt;Google Chart API&lt;/a&gt; was released almost a year ago, I saw an opportunity to start a relatively simple, useful open source project. I quickly designed and developed an early version of a Java wrapper API enabling developers to programmatically interact with the Google Chart API from Java. I knew I had to stake out my territory quickly because many developers would have the same idea. Therefore on a whim, I chose the "&lt;a title="gchartjava" href="http://gchartjava.googlecode.com" id="lodx"&gt;gchartjava&lt;/a&gt;" moniker -- an accurate, but completely clunky and meaningless name to anyone outside the narrow Google API community. Moreover, having "Java" in the name may violate &lt;a title="Sun trademark" href="http://www.sun.com/policies/trademarks/" id="o9:o"&gt;Sun trademark&lt;/a&gt;. I reluctantly lived with "gchartjava" for several months until a user pointed out the trademark problems and suggested "gchart4j", a variation on the familiar "4j"&amp;nbsp; suffix (e.g. log4j). That suggestion, however, still sounded too specific, so I simplified the name a bit to arrive at "&lt;a title="charts4j" href="http://charts4j.googlecode.com" id="cfzd"&gt;charts4j&lt;/a&gt;" which is apparently unique in the &lt;a title="universal namespace" href="http://www.google.com/search?q=charts4j" id="ikrf"&gt;universal namespace&lt;/a&gt;. The new charts4j moniker will simply and accurately describe its purpose -- a chart API for Java developers-- but will also give it a ring of familiarity with the 4j suffix.&lt;br&gt;&lt;br&gt;The cost of this move will not be cheap. I will have to spend some time rebranding, and who knows what will happen to my PageRank. But in the long run, it will cast a wider net than just trying to appeal to Google API users and developers.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-1472709505312178623?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/1472709505312178623/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=1472709505312178623' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1472709505312178623'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1472709505312178623'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2008/11/gchartjava-moves-to-charts4j.html' title='gchartjava moves to charts4j'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-248325793103936767</id><published>2008-10-24T19:37:00.001-07:00</published><updated>2008-12-01T21:33:05.478-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='charts'/><category scheme='http://www.blogger.com/atom/ns#' term='visualization'/><category scheme='http://www.blogger.com/atom/ns#' term='gchartjava'/><category scheme='http://www.blogger.com/atom/ns#' term='google chart api'/><title type='text'>The new release candidate of gchartjava</title><content type='html'>I have been on blogging hiatus since last winter because I was busy at work on &lt;a title="gchartjava" href="http://gchartjava.googlecode.com/" id="zzk2"&gt;gchartjava&lt;/a&gt;.&lt;br&gt;&lt;br&gt;This project has grown to 20,000 lines of code and 150 classes (including many junit test classes). The end product is still relatively small--a 161Kb jar for producing great charts and graphs with 100% pure core Java. I have received great feedback from many users and developers. There have been about 850 downloads of the distribution in 4.5 months.&lt;br&gt;&lt;br&gt;&lt;div id="s93c" style="padding: 1em 0pt; text-align: center;"&gt;&lt;img style="width: 500px; height: 375px;" src="http://docs.google.com/File?id=df88fvbt_3hk2jdxfb_b"&gt;&lt;/div&gt;&lt;br&gt;&lt;br&gt;This latest release candidate version of gchartjava now finally exposes nearly all the features of the &lt;a title="Google Chart API" href="http://code.google.com/apis/chart/" id="s56j"&gt;Google Chart API&lt;/a&gt;, or at least I thought so until I saw the &lt;a title="recent announcement" href="http://groups.google.com/group/google-chart-api/browse_thread/thread/b0a10b55384bf749" id="udg2"&gt;recent announcement&lt;/a&gt; about some new chart types. That is one of the problems maintaining an API; you are always playing catchup with the underlying technology. At any rate, I hope to have those chart types available in gchartjava soon, but probably not in this release.&lt;br&gt;&lt;br&gt;This project has been an invaluable lesson in many aspects of software development. To name just a few:&lt;br&gt;&lt;br&gt;&lt;ul&gt;&lt;li&gt;Object design&lt;/li&gt;&lt;li&gt;API design&lt;/li&gt;&lt;li&gt;Collaborating with users and developers around the world&lt;/li&gt;&lt;li&gt;Managing an OSS project &lt;/li&gt;&lt;li&gt;Swallowing your pride when a user points out you have done something silly&lt;/li&gt;&lt;li&gt;Not leaving javadoc documentation to the last minute&lt;br&gt;&lt;/li&gt;&lt;li&gt;Not leaving static analysis to the last minute&lt;br&gt;&lt;/li&gt;&lt;/ul&gt;&lt;br&gt;I hope to be able to blog in greater detail about some of these issues in the future. There should be more time in my schedule, now that gchartjava is mostly complete.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-248325793103936767?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/248325793103936767/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=248325793103936767' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/248325793103936767'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/248325793103936767'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2008/10/gchartjava.html' title='The new release candidate of gchartjava'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-3552927996915248512</id><published>2008-02-24T20:28:00.000-08:00</published><updated>2008-02-24T20:58:56.269-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='BJUG'/><category scheme='http://www.blogger.com/atom/ns#' term='YUI'/><category scheme='http://www.blogger.com/atom/ns#' term='YSlow'/><category scheme='http://www.blogger.com/atom/ns#' term='tomcat'/><category scheme='http://www.blogger.com/atom/ns#' term='Apache'/><category scheme='http://www.blogger.com/atom/ns#' term='Firebug'/><title type='text'>High Performance Web Sites and Tomcat</title><content type='html'>I recently attended a &lt;a href="http://www.boulderjug.org/"&gt;Boulder Java User Group&lt;/a&gt; meeting, at which Scott Davis pointed us to &lt;a href="http://developer.yahoo.com/yslow/"&gt;YSlow&lt;/a&gt;, a website performance analysis tool. It is an add-on to the &lt;a href="https://addons.mozilla.org/en-US/firefox/addon/1843"&gt;Firebug&lt;/a&gt; plug-in. When analyzing a web site, YSlow takes into account &lt;a href="http://developer.yahoo.com/performance/index.html#rules"&gt;10-15 criteria&lt;/a&gt;, and gives a grade.&lt;br /&gt;&lt;br /&gt;As an aside, this is exactly why I attend the BJUG. I often pick up information that is instantly useful in my day-to-day software development. Another gem I recently discovered at BJUG is &lt;a href="http://developer.yahoo.com/yui/"&gt;YUI&lt;/a&gt;, which I now use extensively both at work and for my own personal projects. YUI is to front-end development as &lt;a href="http://www.springframework.org/"&gt;Spring&lt;/a&gt; is to middle-tier development. In particular, YUI makes the life of the developer much easier.&lt;br /&gt;&lt;br /&gt;At any rate, I analyzed my own web site, &lt;a href="http://www.weathermole.com"&gt;weathermole.com&lt;/a&gt;, with YSlow, and was given an 'F' for performance. Here is the full analysis:&lt;br /&gt;&lt;br /&gt;Performance Grade: F (58)&lt;br /&gt;&lt;br /&gt;B       1. Make fewer HTTP requests&lt;br /&gt;F       2. Use a CDN&lt;br /&gt;F       3. Add an Expires header&lt;br /&gt;F       4. Gzip components&lt;br /&gt;A       5. Put CSS at the top&lt;br /&gt;A       6. Put JS at the bottom&lt;br /&gt;A       7. Avoid CSS expressions&lt;br /&gt;n/a     8. Make JS and CSS external&lt;br /&gt;D       9. Reduce DNS lookups&lt;br /&gt;A       10. Minify JS&lt;br /&gt;A       11. Avoid redirects&lt;br /&gt;A       12. Remove duplicate scripts&lt;br /&gt;F       13. Configure ETags&lt;br /&gt;&lt;br /&gt;To improve this grade, I have been focusing on 3,4, and 13, all of which require manipulation of the Apache HTTP Server's httpd.conf file.&lt;br /&gt;&lt;br /&gt;The problem that I am encountering is I actually use Tomcat to serve all my web content including static resources (e.g. javascript, CSS files). I only use Apache HTTP Server as a proxy server to forward web traffic to Tomcat. My attempts at manipulating the httpd.conf file yield nothing. For example, when I insert these lines into the httpd.conf file:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&amp;lt;ifmodule mod_expires.c&amp;gt;&lt;br /&gt;   &amp;lt;FilesMatch "\.(png|css|js)$"&amp;gt;&lt;br /&gt;        ExpiresActive on&lt;br /&gt;        ExpiresDefault "access plus 10 year"&lt;br /&gt;    &amp;lt;/FilesMatch&amp;gt;&lt;br /&gt; &amp;lt;/ifmodule&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;it does not add any expires header to my CSS or javascript files. You can see this for yourself if you have Firebug and YSlow installed.&lt;br /&gt;&lt;br /&gt;Perhaps there is some other explanation, but I presume this is happening because I am only using Apache HTTP Server as a proxy. All header information is actually supplied by Tomcat.&lt;br /&gt;&lt;br /&gt;A possible solution is to have the Apache HTTP Server serve all my static resources, and have Tomcat only serve content relevant to the web application. The problem with this approach is that it makes deployment a real pain in the neck. I have to split my deployment between the HTTP Server and Tomcat. Moreover, I would also have to figure out how to selectively forward requests to Tomcat depending on what is requested (i.e. static versus dynamic content). I do not know how difficult this is to implement since I have not tried, but it just feels convoluted and kludgy. It would probably require a fair amount of trial and error mucking with the httpd.conf file.&lt;br /&gt;&lt;br /&gt;Another potential solution is to programmatically add these headers within my web application, but this approach is somewhat absurd.&lt;br /&gt;&lt;br /&gt;So my question is, is there a simpler solution to improving weathermole's performance?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-3552927996915248512?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/3552927996915248512/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=3552927996915248512' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/3552927996915248512'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/3552927996915248512'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2008/02/high-performance-web-sites-and-tomcat.html' title='High Performance Web Sites and Tomcat'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-6290816760866208076</id><published>2008-01-30T19:47:00.000-08:00</published><updated>2008-01-31T09:59:50.064-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='iPhone'/><category scheme='http://www.blogger.com/atom/ns#' term='Roku'/><category scheme='http://www.blogger.com/atom/ns#' term='Internet Radio'/><category scheme='http://www.blogger.com/atom/ns#' term='iPod'/><category scheme='http://www.blogger.com/atom/ns#' term='Flytunes'/><category scheme='http://www.blogger.com/atom/ns#' term='Apple'/><title type='text'>Internet Radio finally coming to the iPod and iPhone?</title><content type='html'>Macworld took place recently, and I was hoping to see an announcement from Steve Jobs explaining how the iPod Touch or iPhone can now play Internet radio streams via WiFi. For some background, I have &lt;a href="http://radioeiffel.blogspot.com/2007/07/my-home-network-joys-and-woes.html"&gt;written in the past&lt;/a&gt; about my love hate relationship with my &lt;a href="http://www.rokulabs.com/products_soundbridgeradio.php"&gt;Roku Internet radio&lt;/a&gt;. In sum, the Roku is a wonderful device for playing  digital music libraries (served via iTunes or &lt;a href="http://www.fireflymediaserver.org/"&gt;Firefly Media Server&lt;/a&gt;) and listening to thousands of Internet radio streams. Moreover, the sound quality is excellent. But the Roku suffers from the following big problems:&lt;br /&gt;&lt;br /&gt;1/  Reliability. My Roku has died twice in one year. Thankfully it was still under warranty so I could replace it. Other Roku owners were not so lucky, and the Roku newgroups are full of people complaining about their Rokus dying after the warranty ran out.&lt;br /&gt;&lt;br /&gt;2/ User Interface. The UI is mediocre at best, and at times terrible. This does not matter too much when selecting my favorite Internet radio station or changing the volume. But the UI is awful for browsing large music collections via the remote control. It is a slow, awkward and painful interaction. The user experience is incomparable to the wonderful album browsing UI available via iTunes.&lt;br /&gt;&lt;br /&gt;3/ The wireless connection between the Roku and the MP3 music server is unreliable. It dies all the time, and I must reset it by restarting iTunes or the Firefly Media Server. This could be a networking problem too, and thus not the Roku's fault, strictly speaking.&lt;br /&gt;&lt;br /&gt;4/ The Roku cannot play Apple's proprietary music format, so I cannot listen to music purchased at the iTunes store via the Roku.&lt;br /&gt;&lt;br /&gt;Because of these problems I have been looking for Roku alternatives, and I have been hoping to see a solution from  Apple via the iPod Touch or iPhone. Of course, these devices can play music and video digital content. Until recently, however, there has been nothing to support Internet radio streams.&lt;br /&gt;&lt;br /&gt;So this week I have been surfing around the tech news site to see what Steve Jobs had to say at Macworld. Initially, it was looking like I was going to be dissapointed again. But then I stumbled upon &lt;a href="http://www.flytunes.fm/"&gt;flytunes&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;I presume the iPod/iPhone platform must have been opened up to third party developers along the way. At any rate, flytunes (or something comparable) may be part of my dream solution of having a reliable device that can play both Internet radio and music libraries with a great user interface.  I would also need an auxiliary device like &lt;a href="http://store.apple.com/1-800-MY-APPLE/WebObjects/AppleStore.woa/wa/RSLID?mco=5D239CBB&amp;amp;fnode=home/shop_ipod/ipod_accessories/speakers&amp;amp;nplm=TK199VC/A"&gt;this&lt;/a&gt;. Moreover, I would like to see more storage capacity on the iPod Touch or iPhone to hold my entire (20GB+) music  collection.&lt;br /&gt;&lt;br /&gt;This solution is a lot of money so I won't be giving up the Roku anytime soon (unless, of course it dies again), but it is nice to know that this technology has finally arrived.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-6290816760866208076?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/6290816760866208076/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=6290816760866208076' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/6290816760866208076'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/6290816760866208076'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2008/01/internet-radio-finally-coming-to-ipod.html' title='Internet Radio finally coming to the iPod and iPhone?'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-1769170564278429913</id><published>2007-12-31T12:28:00.000-08:00</published><updated>2008-01-31T10:00:42.397-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='tip'/><category scheme='http://www.blogger.com/atom/ns#' term='osx'/><category scheme='http://www.blogger.com/atom/ns#' term='Apple'/><title type='text'>OS X Tip: Use the /tmp Folder as a Scratch Directory.</title><content type='html'>Here is a tip for dealing with Mac desktop clutter.  But first, this tip comes with the following disclaimer:&lt;br /&gt;&lt;br /&gt;!!!WARNING. ANY FILES YOU PUT IN THE /tmp DIRECTORY WILL BE AUTOMATICALLY EXPUNGED (I.E. PERMANENTLY DELETED/ERASED) EACH TIME YOU REBOOT OR SHUTDOWN YOUR COMPUTER. DO NOT PUT IMPORTANT FILES IN THE /tmp FOLDER!!!&lt;br /&gt;&lt;br /&gt;With that warning out of the way, to reduce the number of files that end up on your desktop, create a soft link between your Desktop directory and the OS X /tmp directory. To do that, open the Terminal application (Applications --&gt; Utilities), and type the following 2 commands:&lt;br /&gt;&lt;br /&gt;cd ~/Desktop&lt;br /&gt;ln -s /tmp/ tmp&lt;br /&gt;&lt;br /&gt;These commands will result in a tmp folder visible on your desktop that corresponds to the /tmp directory. Then, add this directory to your finder sidebar by opening a finder window and dragging the folder to the sidebar.&lt;br /&gt;&lt;br /&gt;Each time you need a temporary scratch space, you can easily access this tmp directory via the finder or the "Save" or "Save as" menu item in any application. Uninteresting files will conveniently go away whenever you shutdown or reboot your computer.&lt;br /&gt;&lt;br /&gt;Moreover, you can use this directory to save downloads coming from your web browser. This is useful for dealing with PDFs that, over time, result desktop clutter and you don't want lying around anyway. To change where your browser saves downloaded files, go to the either the "Main" tab of the Firefox preferences dialog or the "General" tab of the Safari preferences dialog.&lt;br /&gt;&lt;br /&gt;If the file is interesting to you, be sure to move it to a permanent location outside the /tmp directory.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-1769170564278429913?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/1769170564278429913/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=1769170564278429913' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1769170564278429913'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/1769170564278429913'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/12/os-x-tip-use-tmp-folder-as-scratch.html' title='OS X Tip: Use the /tmp Folder as a Scratch Directory.'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-7994947664640299238</id><published>2007-12-11T21:15:00.000-08:00</published><updated>2007-12-12T08:51:18.274-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='wrapper'/><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='visualization'/><category scheme='http://www.blogger.com/atom/ns#' term='gchartjava'/><category scheme='http://www.blogger.com/atom/ns#' term='google chart api'/><title type='text'>Google Releases Chart API and gchartjava Wrapper API</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_UO4RaoE0QIU/R19wPwNkQiI/AAAAAAAAAAc/x1RAxk8uNLA/s1600-h/chart.png"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://1.bp.blogspot.com/_UO4RaoE0QIU/R19wPwNkQiI/AAAAAAAAAAc/x1RAxk8uNLA/s400/chart.png" alt="" id="BLOGGER_PHOTO_ID_5142952715422548514" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;In the earth science arena, programmatically displaying charts and graphs is often a user requirement. The problem is that building charting software is not easy. To have those tick marks just right and produce a graph that looks better than amateurish can consume 100% of a good programmer's time for weeks and months. Alternatively, there are charting libraries, but as the old saying goes, "it is either free or it works." &lt;a href="http://www.vni.com/index.php"&gt;Visual Numerics&lt;/a&gt; looks like a decent product, but it's not free. &lt;a href="http://www.jfree.org/jfreechart/"&gt;JFreeChart&lt;/a&gt; looks pretty good, although you have to purchase the documentation.&lt;br /&gt;&lt;br /&gt;It was therefore with great interest that I read that Google recently released a &lt;a href="http://code.google.com/apis/chart/"&gt;Chart API&lt;/a&gt;. I have been playing around with it , and I am mostly impressed. I wish I had more control over the orientation of the text along side the axes. Maybe that feature is forthcoming. I have not quite figured out why they released it as a service instead of a library that programmers can download. But I guess that is where Google and the world is heading, where even "medium-grained" capabilities will be offered as services. On a related note, if you ever have trouble explaining to a colleague what Service Oriented Architecture is, this is a great example of SOA technology.&lt;br /&gt;&lt;br /&gt;Back to scientific programming, it is easy to push the limits of any charting software when dealing with weather or climate data, but for straightforward data, the Google charting API could be a great solution.&lt;br /&gt;&lt;br /&gt;The next &lt;a href="http://gchartjava.googlecode.com"&gt;logical step&lt;/a&gt; is to define wrapper APIs in Java, C#, Python, or Ruby around the Google Chart API. The reason it is useful to wrap the GChart API with Java/ Ruby/.Net/ Python is that it allows the developer to interact with the GChart API *programmatically.* Imagine this use case: a sensor monitors traffic patterns on a busy highway and displays the data in a chart on a web page. In this case, it is nice to have your business logic query the traffic data and build those charts dynamically. Subsequently, those charts are forwarded to your (web-tier) view, for example. Also, a wrapper hides the ugly details of making and chaining the URL GET parameters.&lt;br /&gt;&lt;br /&gt;I have taken a first stab at buildng a Java wrapper for Google Charts and you can find it &lt;a href="http://gchartjava.googlecode.com"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;This &lt;a href="http://gchartjava.googlecode.com"&gt;wrapper API&lt;/a&gt; is still very much in flux, but should be solidifying soon.&lt;br /&gt;&lt;br /&gt;Oh, and kudos to Google for a job well done. They really do live up to their reputation.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-7994947664640299238?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/7994947664640299238/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=7994947664640299238' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/7994947664640299238'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/7994947664640299238'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/12/google-releases-chart-api-and.html' title='Google Releases Chart API and gchartjava Wrapper API'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_UO4RaoE0QIU/R19wPwNkQiI/AAAAAAAAAAc/x1RAxk8uNLA/s72-c/chart.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-2619923592122039360</id><published>2007-11-14T20:18:00.000-08:00</published><updated>2007-11-15T08:46:40.345-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='sc07'/><category scheme='http://www.blogger.com/atom/ns#' term='Whirlpool'/><category scheme='http://www.blogger.com/atom/ns#' term='HPC'/><category scheme='http://www.blogger.com/atom/ns#' term='virtualization'/><title type='text'>SC07- Day 3 - HPC in the Kitchen and Laundry Room</title><content type='html'>After spending some time on the exhibitor floor checking out the cool &lt;a href="http://secondlife.com/"&gt;Second Life&lt;/a&gt; demo at the Sun booth, I decided to walk over to see the "&lt;a href="http://sc07.supercomp.org/schedule/event_detail.php?evid=11141"&gt;HPC in the Kitchen and Laundry Room&lt;/a&gt;" talk.&lt;br /&gt;&lt;br /&gt;It's interesting to note how manufacturing is becoming virtualized at all levels. I saw a piece on the &lt;a href="http://www.pbs.org/newshour/"&gt;NewsHour&lt;/a&gt; a few months ago on how companies like &lt;a href="http://en.wikipedia.org/wiki/CATIA"&gt;CATIA and Dassault&lt;/a&gt; build aircrafts virtually before they assemble the real thing. This strategy allows them to find all sorts of assembly bugs that they would not be able to discover otherwise (e.g. if you attach the wing to the aircraft in that manner, it is going to smash into the fuselage on the way).&lt;br /&gt;&lt;br /&gt;The Whirlpool researcher explained how washing machine construction and assembly is virtualized. Even the packaging of the machine into the cardboard box is modeled. (Repackaging a washing machine is expensive, if the packaging is damaged.) Other parts of the assembly workflow appear to be modeled as well. The result is a significant cost savings to Whirlpool. They have one or two clusters at the company to get the job done.&lt;br /&gt;&lt;br /&gt;I imagine the time is not far off when when this trend will play-out in the manufacturing of all kinds of equipment, if it hasn't already. I wonder what can't be virtualized? Can home construction be virtualized?&lt;br /&gt;&lt;br /&gt;Maybe we will be able to build a virtual house in Second Life, and even live in it for a while and make adjustments and decide if we like it before we actually have it constructed by the builder.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-2619923592122039360?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/2619923592122039360/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=2619923592122039360' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/2619923592122039360'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/2619923592122039360'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/11/sc07-day-3-hpc-in-kitchen-and-laundry.html' title='SC07- Day 3 - HPC in the Kitchen and Laundry Room'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-8527292217614756709</id><published>2007-11-13T15:16:00.000-08:00</published><updated>2007-11-13T22:25:37.853-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='sc07'/><category scheme='http://www.blogger.com/atom/ns#' term='molecular biology'/><category scheme='http://www.blogger.com/atom/ns#' term='Neil Gershenfeld'/><category scheme='http://www.blogger.com/atom/ns#' term='Bits and Atoms'/><category scheme='http://www.blogger.com/atom/ns#' term='HPC'/><category scheme='http://www.blogger.com/atom/ns#' term='keynote'/><title type='text'>SC07- Day 3 - Neil Gershenfeld Keynote on "Programming Bits and Atoms"</title><content type='html'>I arrived this morning at SC07 excited to see &lt;a href="http://ng.cba.mit.edu/"&gt;Professor Neil Gershenfeld's&lt;/a&gt; talk on "Programming &lt;a href="http://cba.mit.edu/"&gt;Bits and Atoms&lt;/a&gt;." He has been featured on the&lt;a href="http://www.pbs.org/newshour/"&gt; Lehrer NewsHour&lt;/a&gt;, my favorite news program, so I figured he must be interesting.&lt;br /&gt;&lt;br /&gt;I got out my laptop ready to take careful notes. After a somewhat lengthy introduction composed of many illustrious dignitaries as well overwrought, loud orchestral music, and a peculiar music video featuring SC07 organizers, Professor Gershenfeld arrived on stage.&lt;br /&gt;&lt;br /&gt;What followed was either brilliant or insane; probably mostly the former, but a bit of the latter. I was unable to take any notes because mostly, I could not comprehend what he was saying. I closed my laptop and instead focused on spirit and essence of the talk.&lt;br /&gt;&lt;br /&gt;I think the take away point is that software and hardware professional need to stop thinking about computers as boxes with screens and keyboards that you can use surf the web, etc. Instead, let's focus on all the wonderful things that Professor Gershenfeld talked about which included: molecular biology, nanotechnology, physical objects as computers, and many, many other topics.&lt;br /&gt;&lt;br /&gt;His discussion on molecular biology was especially interesting to me as, long ago, I had a former career in a molecular biology lab. His thoughts on the ribosome as a sort of molecular Turing machine, and his attempts to mimic that mechanism in other mediums were certainly fascinating.&lt;br /&gt;&lt;br /&gt;Apart from that, I can't say much more. My mind is still buzzing.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-8527292217614756709?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/8527292217614756709/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=8527292217614756709' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/8527292217614756709'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/8527292217614756709'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/11/day-3-neil-gershenfeld-keynote-on.html' title='SC07- Day 3 - Neil Gershenfeld Keynote on &quot;Programming Bits and Atoms&quot;'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-2704892047388212896</id><published>2007-11-12T21:57:00.000-08:00</published><updated>2007-11-16T13:56:07.590-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='sc07'/><category scheme='http://www.blogger.com/atom/ns#' term='multicore'/><category scheme='http://www.blogger.com/atom/ns#' term='conference'/><category scheme='http://www.blogger.com/atom/ns#' term='reno'/><category scheme='http://www.blogger.com/atom/ns#' term='HPC'/><category scheme='http://www.blogger.com/atom/ns#' term='cilk'/><category scheme='http://www.blogger.com/atom/ns#' term='workshop'/><category scheme='http://www.blogger.com/atom/ns#' term='manycore'/><title type='text'>SC07- Day 1 &amp; 2 - Manycore and Multicore Computing Workshop</title><content type='html'>I am attending &lt;a href="http://sc07.supercomputing.org/"&gt;SC07&lt;/a&gt;: "The International Conference on High Performance Computing, Networking, Storage, and Analysis." The conference is taking place in Reno, Nevada -- "The Biggest Little City in the World." The town appears to be a miniature version of Las Vegas with the omnipresent casinos and slot machines -- something I find a little depressing. Many of the casinos and the general infrastructure of the town seem to suffer from accelerated decrepitude. In contrast to Las Vegas, the town is surrounded by picturesque mountains, which are pleasantly snow capped from the precipitation Saturday night. If I had time and a car, I would go for a hike.&lt;br /&gt;&lt;br /&gt;I attended the "Manycore and Multicore Computing" &lt;a href="http://gamma.cs.unc.edu/SC2007/program.htm"&gt;workshop&lt;/a&gt; Sunday and Monday of SC07. As an object-oriented applications developer, my main interest in this topic is to observe how multicore architectures are changing desktop and server-side computing and to learn how to best leverage these new types of machines for my own development.&lt;br /&gt;&lt;br /&gt;The overall message is, ready or not, HPC and parallel programming have arrived in the desktop computing environment. Many of you are probably reading this post on a dual or quad core machine. What follows are a few points I took away from the workshop. Also, I use the terms multicore and manycore somewhat interchangeably since, as far as I can tell, the distinction is not really set in stone.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Motivation&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;The chief motivation behind manufacturing multicore machines is that users always want more computing power. This is a self-evident truth, as judged by the last few decades of computing. Users not only want to run traditional applications faster (e.g. MS Powerpoint), they want to run entirely new applications not permitted by slower computers (e.g. the &lt;a href="http://en.wikipedia.org/wiki/3D_Internet"&gt;3D Internet&lt;/a&gt;, molecular dynamics). Single processors have hit physical limits that do not allow for increased performance. If users want faster applications, programmers will have to design and code them for manycore/multicore architectures.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Flavors&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;There are a couple of different varieties of manycore and multicore architectures. In particular, researchers distinguish between homogeneous (CPU only) versus heterogeneous hardware. Heterogeneous architectures derive their computational horsepower from CPUs and GPUs (Graphical Processing Units). GPUs &lt;a href="http://www.hpcwire.com/hpc/1129975.html"&gt;are no longer just for graphics&lt;/a&gt;, but can also be leveraged for intensive floating-point arithmetic. GPUs have attractive power consumption characteristics as well. Moreover, my understanding is that GPUs have not hit the sorts of physical limitations in delivering performance that CPUs have.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Caveats&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Multicore architectures can deliver improved performance, but there are major caveats that impact hardware and the entire software stack.&lt;br /&gt;&lt;br /&gt;At the hardware level, there are difficult issues as to how the multicore architectures will scale out to many cores. The number of cores is expected to double every two years. The main problems appear to be memory bandwidth and IO bottlenecks. Increased power demand by the hardware is another hurdle in the way of massively multicore architectures.&lt;br /&gt;&lt;br /&gt;At the operating system level, scheduling algorithms will have to drastically change.&lt;br /&gt;&lt;br /&gt;The impact on software developers will be major. In particular, programmers will have to build shared memory parallel algorithms and overcome the significant challenges that parallel programming entails. The shift to the multicores will be a sea change for most application developers (outside of HPC) who will now have to reason about thread-based, shared memory parallelism in addition to locks, synchronization, data races, and fine-grained parallelism, just to cite a few examples.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Abstractions &amp;amp; Frameworks&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;To deal with this new programming landscape, libraries, frameworks, and higher level programming abstractions must be developed in order to bring parallel computing to the masses. Building these abstractions, however, will take away some of the performance benefits that multicore architectures can theoretically achieve. But this disadvantage will be more than offset by the advantage of bringing parallel programming to a much wider audience.&lt;br /&gt;&lt;br /&gt;On the topic of frameworks, one of the most interesting talks of the workshop was Charles E. Leiserson's introduction of the &lt;a href="http://www.cilk.com/"&gt;Cilk&lt;/a&gt; suite of products that enable programmers to transition to parallel programming for the multicores. It is essentially a fork-join (or “spawn-sync” in Cilk parlance) framework for C++ that allow programmers to easily express fine-grained parallelism. Under the hood, it employs a work stealing scheduler to dynamically balance workloads. Leiserson also suggested that the multicore/manycore architectures could spell the end for distributed memory parallel programming, notwithstanding significant architectural issues that must be overcome (e.g. memory bandwidth). Cilk reminded me a bit of what I &lt;a href="http://www.infoq.com/news/2007/07/concurrency-java-se-7"&gt;heard&lt;/a&gt;  concerning the forthcoming &lt;a href="http://gee.cs.oswego.edu/dl/jsr166/dist/jsr166ydocs/"&gt;Java fork-join&lt;/a&gt;  framework, which will be part of the java.util.concurrent package.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Next Generation Parallel Languages&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;The speakers talked a bit about &lt;a href="http://domino.research.ibm.com/comm/research_projects.nsf/pages/x10.index.html"&gt;X10&lt;/a&gt;, &lt;a href="http://fortress.sunsource.net/"&gt;Fortress&lt;/a&gt;, and &lt;a href="http://chapel.cs.washington.edu/"&gt;Chapel&lt;/a&gt;, the so-called &lt;a href="http://www.highproductivity.org/"&gt;HPCS&lt;/a&gt; (High-Productivity Computing System) languages in the context of multicore. X10 received most of the attention. The designers of the X10 language removed the concurrency constructs out of Java and replaced them with a new set of concurrency idioms that better assist programmers develop deadlock-free, scalable parallel code. Some of the speakers expressed skepticism concerning these languages as they are geared more towards homogeneous multicore architectures. The &lt;a href="http://gamma.cs.unc.edu/SC2007/abstracts.htm#sarkar"&gt;Habanero&lt;/a&gt; language builds upon X10 to deliver programmers a high level language that can harness heterogeneous architectures.&lt;br /&gt;&lt;br /&gt;Overall, it was an interesting  &lt;a href="http://gamma.cs.unc.edu/SC2007/abstracts.htm"&gt;series of talks&lt;/a&gt; combining a good blend of visionary and technical speakers. By the end of the workshop on day 2 though, I was ready to return to the &lt;a href="http://www.sienareno.com/"&gt;Siena Hotel&lt;/a&gt; and go for a jog on the banks of the Truckee River, which is not exactly the Seine to say the least.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-2704892047388212896?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/2704892047388212896/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=2704892047388212896' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/2704892047388212896'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/2704892047388212896'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/11/sc07-day-1-2-manycore-and-multicore.html' title='SC07- Day 1 &amp; 2 - Manycore and Multicore Computing Workshop'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-4999793599304969637</id><published>2007-10-29T20:49:00.000-07:00</published><updated>2007-11-13T08:38:19.830-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='tickets'/><category scheme='http://www.blogger.com/atom/ns#' term='Rockies'/><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='fiasco'/><category scheme='http://www.blogger.com/atom/ns#' term='World Series'/><title type='text'>My Take on the Rockies Ticket Fiasco</title><content type='html'>Before I mothball all my baseball thoughts until next Spring, I want to state the following completely unsubstantiated assertions and speculative conjectures about the &lt;a href="http://www.google.com/search?hl=en&amp;amp;safe=off&amp;amp;client=firefox-a&amp;amp;rls=org.mozilla%3Aen-US%3Aofficial&amp;amp;hs=pxh&amp;amp;q=2007+Rockies+World+Series+ticket+fiasco&amp;amp;btnG=Search"&gt;World Series ticket fiasco&lt;/a&gt;:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;This was a Java application, evidenced by the fact that users were hitting &lt;span class="blsp-spelling-error" id="SPELLING_ERROR_0"&gt;JSPs&lt;/span&gt;. Well built Java applications a very scalable, but this one was not.&lt;/li&gt;&lt;li&gt;They experienced a software and not hardware failure. It was a possible to access the site, but making progress was almost impossible.&lt;/li&gt;&lt;li&gt;8 million hits in 90 minutes is a lot, but can be handled by a well-designed scalable system.&lt;/li&gt;&lt;li&gt;They were probably not the victim of a malicious attack. Hackers usually demand ransoms these days. I did not hear anything about a ransom in the news. Staging a denial of service attack "just for fun" does not ring true and would require substantial resources.&lt;/li&gt;&lt;li&gt;There was no "online queue".  When users entered the site, the window claimed that they were given a place in line, and said not to reload, or they'd lose their place in line.  I was thinking about how to implement this, and in theory it can be done with session IDs, but would be difficult to implement fairly and correctly. It may not be possible at all, and I know of no online queues like this. Users were better off hitting reload constantly which is what I did in about 20 Safari web browser tabs. I was actually able to make progress but not enough to buy tickets.&lt;/li&gt;&lt;li&gt;Users that were closer to the servers in California with fast Internet had an advantage over users in Colorado. My wife's cousin was able to buy eight tickets without any difficulties from California, and mysteriously also easily surpassed the four ticket limit.&lt;/li&gt;&lt;/ol&gt;Next time the Rockies make it to the World Series,  they ought follow the Red Sox's example and use a lottery system. It is fairer and kinder to fans.&lt;br /&gt;&lt;br /&gt;Oh and by the way, congratulations to the Rockies. They didn't win the World Series, but they had a much better year than anyone expected.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-4999793599304969637?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/4999793599304969637/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=4999793599304969637' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4999793599304969637'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4999793599304969637'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/10/my-take-on-whole-rockies-ticket-fiasco.html' title='My Take on the Rockies Ticket Fiasco'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-5932724856481052619</id><published>2007-10-04T20:54:00.000-07:00</published><updated>2007-11-13T15:34:10.796-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='collections'/><category scheme='http://www.blogger.com/atom/ns#' term='java generics'/><category scheme='http://www.blogger.com/atom/ns#' term='generics'/><category scheme='http://www.blogger.com/atom/ns#' term='book'/><title type='text'>Book Recommendation: Java Generics and Collections</title><content type='html'>I recently wrote a &lt;a title="blog entry" href="http://radioeiffel.blogspot.com/2007/06/java-generics-finally-drinking-kool-aid.html" id="ezjd"&gt;blog entry&lt;/a&gt; about reluctantly accepting Java Generics. If you are planning on genericising your Java code (which is in principle inevitable for all Java programmers as Sun recommends against using raw types, and may not support them in the future), then "&lt;a title="Java Generics and Collections" href="http://www.amazon.com/Java-Generics-Collections-Maurice-Naftalin/dp/0596527756" id="o6vr"&gt;Java Generics and Collections&lt;/a&gt;" by Maurice Naftalin, and Philip Wadler is the book for you. It is the clearest, most coherent treatise I have read on the subject. Java Generics make a lot more sense after reading this book.&lt;br /&gt;&lt;br /&gt;Declarations like&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:Courier New;"&gt;List&amp;lt;? extends XYZ&amp;gt; list = new LinkedList&amp;lt;XYZ&amp;gt;();&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;and notions like covariance finally make sense. I even find using wildcards useful since they give programmers some indication as to the purpose of the data structure in addition to providing type safety.&lt;br /&gt;&lt;br /&gt;The "Get and Put Principle" in section (2.4) is a real gem. To quote Java Generics and Collections:&lt;br /&gt;&lt;br /&gt;&lt;div style="margin-left: 40px;"&gt;&lt;i&gt;The Get and Put Principle&lt;/i&gt;: use an &lt;span style="font-family:Courier New;"&gt;extends&lt;/span&gt; wildcard when you only get values out of a structure, use &lt;span style="font-family:Courier New;"&gt;super&lt;/span&gt; wildcard when you only &lt;i&gt;put&lt;/i&gt; values into a structure, and don't use a wildcard when you both get and put.&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;They also give some best practices on dealing with non-generic legacy libraries. This is particularly useful information, as we are probably a long way from seeing Apache project libraries moving to generics.&lt;br /&gt;&lt;br /&gt;(I still wonder about the cost benefit ratio adding so much complexity to the language, but let's ignore that for now.)&lt;br /&gt;&lt;br /&gt;There are other resources out there for Java Generics, but they tend to be insufficient or a bit rote like Angelika Langer's huge &lt;a title="FAQ" href="http://angelikalanger.com/GenericsFAQ/JavaGenericsFAQ.html" id="svc0"&gt;FAQ&lt;/a&gt;. I would actually recommend reading Java Generics first, and if you have questions left over, consult the FAQ.&lt;br /&gt;&lt;br /&gt;Moreover, there is a section on the Collections Framework interface that reviews the major Java core data structures (Sets, Queues, Lists, and Maps). This type of material is really great to know. Java programmers tend to gravitate 99% to ArrayList and HashMap, but there are a lot of other fine data structures available in the core language that may be more appropriate for your requirements. Java Generics and Collections covers them all.&lt;br /&gt;&lt;br /&gt;There are a few obnoxious typos, such as the broken Function Pattern code. This is confirmed in the &lt;a title="errata" href="http://www.oreilly.com/catalog/javagenerics/errata/" id="vtv3"&gt;errata&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Regardless, this is the best programming book I have read since "Java Concurrency in Practice."&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-5932724856481052619?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/5932724856481052619/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=5932724856481052619' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5932724856481052619'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5932724856481052619'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/10/book-recommendation-java-generics-and.html' title='Book Recommendation: Java Generics and Collections'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-4998431899566347683</id><published>2007-09-11T20:55:00.000-07:00</published><updated>2007-11-13T15:36:56.561-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Mac Mini'/><category scheme='http://www.blogger.com/atom/ns#' term='iTunes'/><category scheme='http://www.blogger.com/atom/ns#' term='Roku'/><category scheme='http://www.blogger.com/atom/ns#' term='Mac'/><category scheme='http://www.blogger.com/atom/ns#' term='music'/><category scheme='http://www.blogger.com/atom/ns#' term='iPod'/><category scheme='http://www.blogger.com/atom/ns#' term='nfs'/><category scheme='http://www.blogger.com/atom/ns#' term='osx'/><category scheme='http://www.blogger.com/atom/ns#' term='Apple'/><category scheme='http://www.blogger.com/atom/ns#' term='wifi'/><title type='text'>iTunes over NFS: A Failed Experiment</title><content type='html'>I &lt;a href="http://radioeiffel.blogspot.com/2007/07/my-home-network-joys-and-woes.html"&gt;recently wrote&lt;/a&gt; about my home network and music library issues. To review, I have a headless &lt;a href="http://www.apple.com/macmini/"&gt;Mac mini&lt;/a&gt; that lives under my bed. It holds our 20GB music library. It serves music to the &lt;a href="http://www.rokulabs.com/products_soundbridgeradio.php"&gt;Roku&lt;/a&gt; and various Macs around the house (via shared iTunes libraries). It is on 24/7, so it always ready to serve music. This solution mostly works, but the problem is that interfacing with the Mac mini (via &lt;a href="http://www.apple.com/downloads/macosx/networking_security/chickenofthevnc.html"&gt;Chicken of the VNC&lt;/a&gt;) is a pain since it is just a headless server. For scanning CDs and syncing an iPod it is not  a workable solution.&lt;br /&gt;&lt;br /&gt;As a workaround,  I set up an NFS mount, as described &lt;a href="http://www.behanna.org/osx/nfs/howto1.html"&gt;here&lt;/a&gt;, between the iTunes Music folder on the laptops and the iTunes Music directory on the Mac mini. My aim was to solve the CD scanning and iPod syncing problem by fooling iTunes on my laptop into thinking that it was dealing with a local file system when in reality it was accessing the server Music directory. For a while, this harebrained solution actually seemed to work. I could play music with no apparent lag. Syncing the iPod was slow, but tolerable. Things quickly went downhill, however. To have this solution work, I had to muck with the Music folder file permissions, which iTunes and the Mac mini did not seem to like. (Maybe the NFS mount was set up wrong with respect to permissions, but ultimately this was the least of my problems.) Strange temp and "Damaged" files starting showing up in the Music directory in large numbers. It would not function reliably, with the iTunes library dropping out and the file permissions confusing iTunes.&lt;br /&gt;&lt;br /&gt;In retrospect my strategy was doomed to fail. I was expecting, without realizing it, to have the iTunes file system function as a transactional music server  able to handle several client iTunes. iTunes is not a music server in that sense, capable of handling several clients at  once. There are perhaps other workarounds, such as making sure only one iTunes client is accessing the library at once, but that is getting too kludgy. (I know iTunes can view other iTunes on the same network via iTunes shared libraries, but, again, I want to scan CDs and sync an iPod to a remote library.)&lt;br /&gt;&lt;br /&gt;In the end, I copied all 20GBs of music over to one of our laptops. We now use that computer for syncing iPods, and unfortunately I am stuck with having to maintain two music libraries at once; one for serving music, and another for syncing the iPod and scanning CDs. It was a frustrating experience, but the last thing I did was listen to some Brian Eno and Nick Drake, which reminded me how much I like my music collection, and put me in a good mood again.&lt;br /&gt;&lt;br /&gt;On a related note, Apple recently released a &lt;a href="http://www.apple.com/ipodtouch/"&gt;WiFi iPod&lt;/a&gt;. If this device could connect to Internet radio (which as far as I can tell, it can't), this would be the ultimate solution for me, coupled with something like &lt;a href="http://store.apple.com/1-800-MY-APPLE/WebObjects/AppleStore.woa/wa/RSLID?mco=D90EA1A1&amp;amp;nplm=TK198VC/A"&gt;this&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-4998431899566347683?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/4998431899566347683/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=4998431899566347683' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4998431899566347683'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4998431899566347683'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/09/itunes-over-nfs-failed-experiment.html' title='iTunes over NFS: A Failed Experiment'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-8216056645515024901</id><published>2007-09-01T18:49:00.000-07:00</published><updated>2007-11-13T15:38:46.793-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='OSS'/><category scheme='http://www.blogger.com/atom/ns#' term='tomcat'/><category scheme='http://www.blogger.com/atom/ns#' term='exceptions'/><title type='text'>OSS, You Get What You Pay For.</title><content type='html'>Like many developers, I have mixed feelings about open source software (OSS).  It is a nice idea to leverage (and even, in the spirit of OSS, contribute back) to other people's work and harness their code to achieve your goals. This strategy has led to some phenomenal success stories. Several software companies that recently experienced meteoric success (such as Google and YouTube) use open source software to run their core business processes. Evidently, some flavors of OSS work in real economic terms.&lt;br /&gt;&lt;br /&gt;This fact, however, is somewhat ironic because a lot of open source software just plain sucks. This paradox was brought to my attention recently when I was migrating from Tomcat 5.5 to 6.&lt;br /&gt;&lt;br /&gt;For one thing, the directory structure was reorganized so I did not know where the external jars (e.g. mysql and log4j) lived. In the end, figured out where to place the jars as described &lt;a href="http://tomcat.apache.org/migration.html"&gt;here&lt;/a&gt;. This portion of the upgrade was not too painful. The logic to these directory structure changes is unclear to me.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://tomcat.apache.org/tomcat-6.0-doc/logging.html"&gt;Incorporating log4j&lt;/a&gt; was the most unpleasant experience. I don't know about you, but when I read crummy documentation with spelling and grammar mistakes (e.g. "van be very", "teh Tomcat" ) and ambiguous directions, it does not give me much confidence about the internals of the application. With that thought in mind, I downloaded the Tomcat source code. It took me less than a minute to find code that looked like this:&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;try {&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;//Code, code, code&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;catch (Throwable t) {&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;return (null);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;This is a good example of how not to write Java. To see why, consult Chapter 8 from "&lt;a href="http://www.amazon.com/Effective-Java-Programming-Language-Guide/dp/0201310058"&gt;Effective Java&lt;/a&gt;" (items 39-47). In addition, the Java language Specification  (&lt;a href="http://java.sun.com/docs/books/jls/third_edition/html/exceptions.html#11.2.4"&gt;JLS 11.2.4&lt;/a&gt;) states that catching Errors (Throwable is the parent of Exception and Error) is not recommended.&lt;br /&gt;&lt;br /&gt;Moreover, it is conventional Java wisdom to not swallow exceptions. Technically, here, the exception was not totally swallowed, but it certainly lost much of its information. The details about what exactly went wrong and where are lost forever. All the caller receives is a measly null. (What's up with those superfluous parentheses around the null?)&lt;br /&gt;&lt;br /&gt;With respect to proper exception handling, I would add, catch the most specific exception possible and try to handle the problem in an intelligent fashion. Clean up resources, log errors, notify the user in a friendly way that something went wrong and do stuff that is appropriate to your application logic where something unexpected has happened.&lt;br /&gt;&lt;br /&gt;If you can't recover from the exception (which is often the case), rethrow it  or better yet, throw a new (possibly runtime) exception that is appropriate to the level of abstraction at that point in the code (&lt;a href="http://www.amazon.com/Effective-Java-Programming-Language-Guide/dp/0201310058"&gt;EJ&lt;/a&gt; Item 43). Only throw checked exceptions if the caller can actually recover from the problem (&lt;a href="http://www.amazon.com/Effective-Java-Programming-Language-Guide/dp/0201310058"&gt;EJ&lt;/a&gt; Item 41).&lt;br /&gt;&lt;br /&gt;So why is it that Tomcat is so popular in spite of poor coding standards? Because, to my great amazement, it works! I have been using it for some time, relatively problem free. I am not pushing it to its limits. If I were, maybe I would start seeing unusual problems -- probably obfuscated by the exception handling mechanism.&lt;br /&gt;&lt;br /&gt;The only explanation I can think of for this sad state of affairs is that with so large a userbase, many of the bugs have been eliminated through a brute force approach of trial and error programming.  I find trial and error coding particularly odious, but I guess if you have enough testers out there, OSS developers can create an application that is relatively stable despite terrible coding.&lt;br /&gt;&lt;br /&gt;But if the application is ported to a new environment or something unusual goes wrong, good luck trying to find the source of any problems. Sometimes you really do get what you pay for.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-8216056645515024901?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/8216056645515024901/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=8216056645515024901' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/8216056645515024901'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/8216056645515024901'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/09/oss-you-get-what-you-pay-for.html' title='OSS, You Get What You Pay For.'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-4827539248564910262</id><published>2007-08-17T20:40:00.000-07:00</published><updated>2007-11-13T15:39:40.686-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='threads'/><category scheme='http://www.blogger.com/atom/ns#' term='statics'/><category scheme='http://www.blogger.com/atom/ns#' term='concurrency'/><title type='text'>How Java Static Fields (AKA Class Variables) Break Thread Confinement and Lead to Concurrency Bugs.</title><content type='html'>Java &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; fields are shared between all instances of a class for a given class loader. One common use of &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; fields is to declare constants via the &lt;span style="font-family:courier new;"&gt;static final&lt;/span&gt; syntax.&lt;br /&gt;&lt;br /&gt;Unfortunately, &lt;span style="font-family:courier new;"&gt;static final&lt;/span&gt; fields don’t ensure that the variable will be constant or immutable. It only guarantees that the field will be shared between all instances of the class for a given class loader (i.e. &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt;) and that, apart from special cases involving reflection and deserialization (see &lt;a style="font-style: italic;" href="http://java.sun.com/docs/books/jls/third_edition/html/j3TOC.html"&gt;JLS&lt;/a&gt; v3 17.5.3), it will not be reinitialized (i.e. &lt;span style="font-family:courier new;"&gt;final&lt;/span&gt;). In particular, there are two situations to consider corresponding to the major type categories in Java; primitive types (e.g. &lt;span style="font-family:courier new;"&gt;int&lt;/span&gt;, &lt;span style="font-family:courier new;"&gt;boolean&lt;/span&gt;, etc.) and reference types (e.g. arrays, interfaces, and classes).&lt;br /&gt;&lt;br /&gt;Once a primitive is declared &lt;span style="font-family:courier new;"&gt;static final&lt;/span&gt; and it is assigned  a value, there is no need to worry about it anymore. It will never change (except in unusual circumstances, see &lt;a style="font-style: italic;" href="http://java.sun.com/docs/books/jls/third_edition/html/j3TOC.html"&gt;JLS&lt;/a&gt; v3 17.5.3).&lt;br /&gt;&lt;br /&gt;For reference types, this is a different story. If the &lt;span style="font-family:courier new;"&gt;static final&lt;/span&gt; reference type is a mutable class (e.g. HashMap), it cannot be reinitialized, but the instance of that class can change after construction via the HashMap put method, for example.&lt;br /&gt;&lt;br /&gt;Listing 1&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;public class Foobar{&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;  //Mutable class variable.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;  private static final Map mutableField = new HashMap();&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;  public Foobar() {}&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;  public void qwerty(){&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    // Code to mutate the mutableField via put method.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;  }&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;And therein that &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; mutable field lies our thread safety concerns. If there are a couple threads floating around both using instances of that same class via the &lt;span style="font-family:courier new;"&gt;qwerty&lt;/span&gt; method from listing 1 for example, they can step on each other via their mutable class variable. Worse, the &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; mutable can be sitting "far away" from the programmer’s code in an open source library and a multi-threaded application can indirectly hammer on that &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; mutable possibly leaving it inconsistent and broken. The &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; &lt;span style="font-family:courier new;"&gt;final&lt;/span&gt; class variable can even be private. If it is affected by the instances of the class from multi-threaded application, it can be subject to thread safety concerns.&lt;br /&gt;&lt;br /&gt;Even worse still, there are many ways to refactor the class referenced by &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; field to be immutable thereby achieving thread safety, but there is no way to make the contents of an array type immutable in Java. (This is yet another reason to consider arrays a deprecated type -- see O’Reilly’s&lt;a href="http://www.amazon.com/Java-Generics-Collections-Maurice-Naftalin/dp/0596527756"&gt;&lt;span style="font-style: italic;"&gt; Java Generics&lt;/span&gt;&lt;/a&gt; 6.9.)&lt;br /&gt;&lt;br /&gt;This is not an academic point. A common way of ensuring thread safety is to have objects visible only from one thread. This is known as thread confinement and is common to client-server request-based architectures (see &lt;a href="http://www.amazon.com/Concurrent-Programming-Java-TM-Principles/dp/0201310090"&gt;&lt;span style="font-style: italic;"&gt;CPJ&lt;/span&gt;&lt;/a&gt; 2.3). The problem is that &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; fields break thread confinement and encapsulation because the same class variable can be accessed from multiple instances of the class, and if it is mutable is subject to race conditions in a multi-threaded environment.&lt;br /&gt;&lt;br /&gt;This discussion may seem obvious, but I do not see this fact explicitly stated in either &lt;a href="http://www.amazon.com/Java-Concurrency-Practice-Brian-Goetz/dp/0321349601"&gt;&lt;span style="font-style: italic;"&gt;Java Concurrency in Practice&lt;/span&gt;&lt;/a&gt; or &lt;a href="http://www.amazon.com/Concurrent-Programming-Java-TM-Principles/dp/0201310090"&gt;&lt;span style="font-style: italic;"&gt;Concurrency in Java&lt;/span&gt;&lt;/a&gt;. Don’t get me wrong. These books are masterpieces of modern software engineering literature and I have immense admiration and respect for the authors, but I did not see any concrete mention of this danger with &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; mutable variables. In fact, to fix these problems I would recommend reading these books. Describing solutions and workarounds would definitely go beyond the scope of this blog entry.&lt;br /&gt;&lt;br /&gt;Once again, as detailed in &lt;a href="http://www.amazon.com/Java-Concurrency-Practice-Brian-Goetz/dp/0321349601"&gt;&lt;span style="font-style: italic;"&gt;Java Concurrency in Practice&lt;/span&gt;&lt;/a&gt;, it is the shared mutable field that endangers thread safety. But in the case of &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; fields, the shared mutable is shared via the &lt;span style="font-family:courier new;"&gt;static&lt;/span&gt; modifier rather than one instance of the class shared by multiple threads.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-4827539248564910262?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/4827539248564910262/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=4827539248564910262' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4827539248564910262'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4827539248564910262'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/08/how-java-static-fields-aka-class.html' title='How Java Static Fields (AKA Class Variables) Break Thread Confinement and Lead to Concurrency Bugs.'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-4850826777559813450</id><published>2007-07-25T20:51:00.000-07:00</published><updated>2007-07-26T08:33:02.139-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Mac Mini'/><category scheme='http://www.blogger.com/atom/ns#' term='iTunes'/><category scheme='http://www.blogger.com/atom/ns#' term='Zoom Modem'/><category scheme='http://www.blogger.com/atom/ns#' term='Roku'/><category scheme='http://www.blogger.com/atom/ns#' term='Qwest'/><category scheme='http://www.blogger.com/atom/ns#' term='Mac'/><category scheme='http://www.blogger.com/atom/ns#' term='Internet Radio'/><category scheme='http://www.blogger.com/atom/ns#' term='iPod'/><category scheme='http://www.blogger.com/atom/ns#' term='Home Network'/><category scheme='http://www.blogger.com/atom/ns#' term='forethought.net'/><category scheme='http://www.blogger.com/atom/ns#' term='Apple'/><title type='text'>My Home Network Joys and Woes</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_UO4RaoE0QIU/RqgattO5UgI/AAAAAAAAAAU/4i2EXXCQL0I/s1600-h/HomeNetwork.png"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://2.bp.blogspot.com/_UO4RaoE0QIU/RqgattO5UgI/AAAAAAAAAAU/4i2EXXCQL0I/s400/HomeNetwork.png" alt="" id="BLOGGER_PHOTO_ID_5091348751280853506" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Qwest DSL + foreThought.net ISP&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;I have a &lt;a href="http://www.qwest.com/"&gt;Qwest&lt;/a&gt; DSL line coming into the condo. My ISP is through &lt;a href="http://forethought.net/"&gt;foreThought.net&lt;/a&gt;. They gave me a dedicated IP address from which I serve a few different web sites (e.g. &lt;a href="http://www.weathermole.com/"&gt;weathermole.com&lt;/a&gt;). I have no complaints here. I have experienced few service interruptions, and the guys at foreThought are responsive whenever I have a question or an issue arises.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Zoom X6 Gateway&lt;/span&gt;&lt;br /&gt;  &lt;br /&gt;This product claims to be an "all-in-one" solution. It has a wireless-G access point, router,  and  4-port switch. I have a headless Mac Mini plugged into one of the ports. The &lt;a href="http://www.zoom.com/"&gt;Zoom X6&lt;/a&gt; has a little embedded web server inside that users can configure the modem, set up the firewall, block ports, etc. I purchased it because it was recommended by my ISP and they know how to work with Zoom modems.&lt;br /&gt;&lt;br /&gt;I was not crazy about this product after I purchased it. I found it hard to configure, and it froze up regularly so I would have to reboot often. After installing a bunch of &lt;a href="http://www.zoom.com/techsupport/adsl/adsl_x6.shtml"&gt;firmware updates&lt;/a&gt; throughout the months, it seems to be doing better. I only rarely have to reboot it. The folks at foreThought originally helped me set it up shortly after I purchased it. I have since made a million screen shots of the configuration so that I will hopefully never have problems with the setup. I do not know if I would recommend it, but it basically works at this point.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Headless Mac Mini&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;On the &lt;a href="http://www.apple.com/macmini/"&gt;Mac Mini&lt;/a&gt; I host a few websites (e.g. &lt;a href="http://www.weathermole.com/"&gt;weathermole.com&lt;/a&gt;) and serve iTunes for various devices around the house.&lt;br /&gt;&lt;br /&gt;I think this is a clever solution not to have a keyboard and monitor, and it does not take up much room in our tiny condo; it sits under our bed. But the fact that it is headless makes it hard to deal with at times. I connect to it via  ssh to control it remotely with the command line. For desktop UI applications -- basically just iTunes-- I use &lt;a href="http://sourceforge.net/projects/cotvnc/"&gt;Chicken of the VNC&lt;/a&gt;, but it is somewhat slow and kludgy. Moreover, I am always nervous during a software update that it is not going to come back up, and I do not have a spare monitor/keyboard lying around to see what is going on if that ever happens. When I originally set it up, I brought it to work and plugged it into a monitor/keyboard there to do the initial configuration. As Mac users know, a lot functionality on a Mac needs to be accessed via a user interface.&lt;br /&gt;&lt;br /&gt;Also, my wife and I both have iPods. It is really inconvenient when we have to them sync them up. Again, it sits under a bed. I have to control iTunes via Chicken of the VNC. This aspect is pretty lame. If I ever have the funds to upgrade, the next machine will not be headless.&lt;br /&gt;&lt;br /&gt;In the meantime, I thought about setting up a cross-mount (over the wireless) and having the iTunes directory visible on the laptops, as if it were local. I tried this plan half-heartedly , but I never had any success, and in the end, I am not sure it would work. It would nicely solve the iPod syncing problem if it did.&lt;br /&gt;&lt;br /&gt;The headless Mac Mini is a fun but imperfect solution.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;UPS&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;I have one of the &lt;a href="http://www.apc.com/products/family/index.cfm?id=21"&gt;cheaper varieties&lt;/a&gt; that supply uninterruptible power to the Zoom gateway and Mac Mini at least for a few minutes. We have had power interruptions so it has served its purpose.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Roku Soundbridge Radio&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;I have a love / hate relationship with this product. It seems to have limitless potential for serving music and Internet radio. My favorite local stations are &lt;a href="http://www.kunc.org/"&gt;KUNC&lt;/a&gt;, &lt;a href="http://www.kuvo.org/"&gt;KUVO&lt;/a&gt;, &lt;a href="http://www.kgnu.org/"&gt;KGNU&lt;/a&gt; -- which I could, of course, listen to with good old-fashioned technology. On the Internet we listen to &lt;a href="http://www.wefunkradio.com/"&gt;WeFunk&lt;/a&gt; and &lt;a href="http://www.radioparadise.com/"&gt;Radio Paradise&lt;/a&gt;. For foreign stations, I like to listen to &lt;a href="http://www.radiofrance.fr/chaines/france-culture/sommaire/"&gt;France Culture&lt;/a&gt;, &lt;a href="http://www.rfi.fr/"&gt;Radio France Internationale&lt;/a&gt;, &lt;a href="http://www.europe1.fr/"&gt;Europe 1&lt;/a&gt;. Plus, it is a client for our gazillions of scanned CDs that reside on the Mac Mini. My wife used to be a music writer so we have a lot of CDs.&lt;br /&gt;&lt;br /&gt;This is all great, but I find the user interface of the &lt;a href="http://www.rokulabs.com/products_soundbridgeradio.php"&gt;Roku&lt;/a&gt; to be a pain in the neck. It is really hard to navigate and find a CD or podcast I want to listen to via the remote control and the small screen on the Roku. For this reason, we still use a regular CD player from time to time. Ideally, it would be great to have a full fledged iTunes interface, but without the computer. This could almost be achieved through an iPod that we would carry around the house and plug into various iPod-ready radios. The iPod's interface is far superior to that of the Roku. But, iPods cannot stream Internet radio, so that solution is out.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.apple.com/appletv/"&gt;Apple TV&lt;/a&gt; could possibly work, but I want a portable solution that I can carry around the house.&lt;br /&gt;&lt;br /&gt;It is theoretically possible that an &lt;a href="http://www.apple.com/iphone/"&gt;iPhone&lt;/a&gt; could solve all these problems, assuming that you could somehow use the iPhone as a middle tier to the various audio devices sitting around the house. Can the iPhone iTunes connect to to Internet radio?  Can you purchase an iPhone without a phone plan? Maybe there is a business opportunity in here somewhere.&lt;br /&gt;&lt;br /&gt;Still, the Roku remains one of my favorite toys in the house.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;MacBooks&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;I also have a couple of Macbooks which are both really great and naturally hook into the wireless network.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Other networking problems...&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;When I am on my local wireless network, for various reasons, I would really like to see my websites through the regular web address (i.e. &lt;a href="http://www.weathermole.com/"&gt;weathermole.com&lt;/a&gt; NOT 10.0.0.10, the local address). I think that I would have to muck with a configuration file somewhere on the client machine, but I do not  know which one.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-4850826777559813450?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/4850826777559813450/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=4850826777559813450' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4850826777559813450'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4850826777559813450'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/07/my-home-network-joys-and-woes.html' title='My Home Network Joys and Woes'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_UO4RaoE0QIU/RqgattO5UgI/AAAAAAAAAAU/4i2EXXCQL0I/s72-c/HomeNetwork.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-4849601891787764974</id><published>2007-07-13T20:35:00.000-07:00</published><updated>2007-07-13T21:12:41.875-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='HPC'/><category scheme='http://www.blogger.com/atom/ns#' term='X10'/><category scheme='http://www.blogger.com/atom/ns#' term='SuperComputing'/><category scheme='http://www.blogger.com/atom/ns#' term='Fortress'/><title type='text'>Sea Change Coming for Scientific High Performance Computing Languages?</title><content type='html'>I work at an &lt;a href="http://www.ucar.edu/"&gt;institution&lt;/a&gt; where scientists and engineers are busy predicting the weather and the Earth's climate in decades to come. These predictions are done by simulations on very specialized super-computers and high performance computing (HPC) platforms such as the IBM &lt;a href="http://en.wikipedia.org/wiki/Blue_Gene"&gt;Blue Gene&lt;/a&gt; machines.&lt;br /&gt;&lt;br /&gt;Unfortunately, there has not been a lot of modern programming language support to take advantage of these parallel processing behemoths, mainly because of their highly specialized and narrow use in the fields of climate and weather forecasting, nuclear reaction simulations, etc. The languages that are supported are typically Fortran, C, and C++.&lt;br /&gt;&lt;br /&gt;As a younger generation software engineer, I am a fan of more modern programming languages such as Java, C#, Python, etc., so the prospect of developing software on HPC platforms has not always been my cup of tea. Those old-school languages seem to lack many features that make life easier for programmers -- e.g. virtual machines to address portability concerns, simpler builds, more developer buy-in leading to rich community support etc. Moreover, as far as Fortran is concerned, there does not seem to be much in terms language support such as numerous open source libraries or sophisticated IDEs. Plus, I prefer modern OO languages for their notions of encapsulation and polymorphism that, if done correctly,  ultimately reduce complexity and let programmers achieve more with less code.&lt;br /&gt;&lt;br /&gt;As far as the scientific HPC programming language landscape is concerned, Fortran has been the status quo for a few decades now. I suspect that there is a sea change coming, however, in the world of HPC languages. This speculation is, of course, fueled by &lt;a href="http://www.gotw.ca/publications/concurrency-ddj.htm"&gt;multi-core revolution&lt;/a&gt; sweeping across desktop and even laptop computers. As single CPUs have hit the wall in terms of performance, the only option is to add more CPUs (cores) per processor and shove more processors into the computer. The computer that I am using right now is a laptop with 2 cores. Apple just released an &lt;a href="http://www.apple.com/macpro/"&gt;8 core&lt;/a&gt; (2 quad core processors) machine. This trend hints at the fact that desktops and laptops are becoming HPC platforms.&lt;br /&gt;&lt;br /&gt;As we start seeing a preponderance of these types of architectures, programming languages and software engineers are having to adapt. In particular, languages are going to make greater use of threads and other concurrency features to take advantage of the multi-cores. All this is not really news to anyone who has cracked open a &lt;a href="http://www.ddj.com/"&gt;DDJ&lt;/a&gt; in the last three years.&lt;br /&gt;&lt;br /&gt;What is interesting to think about is how these changes will affect the rarefied world of HPC and supercomputing. I speculate that tomorrow's weather and climate simulation super-computers are going to be the same kinds of multi-core computers that run on our desktops, but just with a bunch more processors. The simple explanation is that this will be the path of least resistance to building a big parallel processor, rather than creating custom, one-off solutions. (A corollary perhaps is that super-computers could become cheaper. We have really seen all of this before with off-the-shelf linux clusters and the Beowulf type machines.)&lt;br /&gt;&lt;br /&gt;In other words, the architecture will be similar enough that standard desktop applications could run on a 1024 processor machine in the not too distant future. This assumes, of course, that desktop applications will have been ported to the new multi-core architectures, but this is inevitable over time as the multi-cores become prevalent. More apropos,  we could see Java Virtual Machines running on big multi-processors. And with Java's built-in support for threads, and the forthcoming &lt;a href="http://gee.cs.oswego.edu/dl/jsr166/dist/jsr166ydocs/"&gt;fork-join framework&lt;/a&gt;, using Java as an HPC language remains in the realm of possibility. Software developers are already running Java on big parallel machines at places like &lt;a href="http://www.azulsystems.com/"&gt;Azul Systems&lt;/a&gt;, but as far as I know, they are not doing scientific programming.&lt;br /&gt;&lt;br /&gt;For various reasons, however, Java is not the best language for scientific HPC. For one thing, there is no operator over-loading in Java. That makes dealing with complex numbers (which must necessarily be represented as objects) annoying because developers have to therefore rely on method calls that can be unwieldy for arithmetic operations. There are a multitude of other reasons why Java is poorly suited to scientific programming that go beyond what I want to write about here. With the possible exception of C++, the difficult truth is that while Fortran is not a great language, until now there has been little or nothing better to address scientific HPC domain.&lt;br /&gt;&lt;br /&gt;Fortunately, computer scientists at various research centers are busy developing new programming languages that are well suited to the multi-core world of today and also have the potential to address various scientific-computing problems. In particular, a couple have been receiving some attention: &lt;a href="http://fortress.sunsource.net/"&gt;Fortress&lt;/a&gt; from Sun, and &lt;a href="http://www.research.ibm.com/x10/"&gt;X10&lt;/a&gt; from IBM.&lt;br /&gt;&lt;br /&gt;What is promising is that these languages are new (especially compared to Fortran) with modern programming notions like object orientation, but also address scientific HPC needs. Here are just a few highlights of features that look interesting:&lt;br /&gt;&lt;br /&gt;Easy parallel task decomposition - They make it straightforward to break up work for parallel execution. For loops are parallel, by default, in Fortress. X10 has a number of built-in concurrency idioms.&lt;br /&gt;&lt;br /&gt;Science oriented - Fortress and X10 both allow operator overloading, for example. Fortress accommodates Unicode characters in identifiers allowing for Greek symbols in code. Fortress also allows static checking of physical units and dimensions and multidimensional arrays.&lt;br /&gt;&lt;br /&gt;Portable by way of virtual machines - The project websites of both these projects claim the languages will run on the Java Virtual Machine. Not only does this have the potential to solve all sorts of portability concerns, but, speaking speculatively, they could take advantage of any jar bytecode library that can run on the JVM. No need to write a separate lexer parser for XML in X10, in theory.&lt;br /&gt;&lt;br /&gt;Supported by the &lt;a href="http://www.eclipse.org/"&gt;Eclipse IDE&lt;/a&gt; - Fortress and X10 have Eclipse plug-ins.&lt;br /&gt;&lt;br /&gt;There are also many other improvements over previous languages which you can read about &lt;a href="http://research.sun.com/projects/plrg/fortress.pdf"&gt;here&lt;/a&gt; and &lt;a href="http://x10.sourceforge.net/docs/x10-101.pdf"&gt;here&lt;/a&gt;. But in conclusion, scientific programmers may finally have access to several modern programming languages that may, at long last, get us past Fortran.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-4849601891787764974?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/4849601891787764974/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=4849601891787764974' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4849601891787764974'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/4849601891787764974'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/07/sea-change-coming-for-scientific-high.html' title='Sea Change Coming for Scientific High Performance Computing Languages?'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-7589906424693529758</id><published>2007-06-24T19:36:00.001-07:00</published><updated>2007-11-13T15:40:25.253-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='java generics'/><category scheme='http://www.blogger.com/atom/ns#' term='generics'/><title type='text'>Java Generics, Finally Drinking the Kool-Aid.</title><content type='html'>For a long time, I was unhappy with Java generics, a language feature that was introduced in Java 1.5. Java generics are supposed to give Java programmers the ability to write code with greater type safety. Unfortunately, Java generics have also introduced a lot of complexity into the language:&lt;br /&gt;&lt;br /&gt;Here are some of my main complaints with generics:&lt;br /&gt;&lt;br /&gt;#1 Confusing and difficult-to-understand syntax.&lt;br /&gt;&lt;br /&gt;Here is an example:&lt;br /&gt;&lt;br /&gt;class Box&amp;lt; T extends Comparable&amp;lt;T&amp;gt; &amp; Cloneable&amp;gt; implements Comparable&amp;lt;Box&amp;lt;T&amp;gt;&amp;gt;, Cloneable&lt;br /&gt;&lt;br /&gt;I would prefer not to parse the class declaration for several minutes to figure out what is going on.&lt;br /&gt;&lt;br /&gt;#2 Java generics do not seem to be generic.&lt;br /&gt;&lt;br /&gt;Before:&lt;br /&gt;&lt;br /&gt;Map map = new HashMap();&lt;br /&gt;&lt;br /&gt;The Map declaration is nice, clean, simple, and GENERIC. It will contain any key value object pair.&lt;br /&gt;&lt;br /&gt;After:&lt;br /&gt;&lt;br /&gt;Map&amp;lt;String,String&amp;gt; map = new HashMap&amp;lt;String,String&amp;gt;();&lt;br /&gt;&lt;br /&gt;The Map declaration is no longer generic but rather specific and now must hold String for both key and value. That is not generic.&lt;br /&gt;&lt;br /&gt;#3 Poor cost-to-benefit ratio.&lt;br /&gt;&lt;br /&gt;Much complexity has been introduced into the language as a result of generics that is time consuming to learn.&lt;br /&gt;&lt;br /&gt;Fortunately, there are resources like Angelika Langer's 425-page &lt;a href="http://angelikalanger.com/GenericsFAQ/JavaGenericsFAQ.html"&gt;FAQ&lt;/a&gt;. Yes, it is really 425 pages. I consider this to be one of the most valuable Java resources on the web. Indeed, if her FAQ did not exist, we would all have given up by now on Java generics. (I am hoping to read the whole thing and I am about a 1/3 of the way through it.)&lt;br /&gt;&lt;br /&gt;But on the flip-side, if it takes me 425 pages to understand something, I'd better be getting some really great features. I do not anticipate these benefits with Java generics.&lt;br /&gt;&lt;br /&gt;I realize that much of the complexity associated with Java generics is to accommodate backwards compatibility concerns. Brian Goetz wrote a nice &lt;a href="http://www-128.ibm.com/developerworks/java/library/j-jtp01255.html"&gt;article&lt;/a&gt; that touches upon this issue and others surrounding Java generics. Maybe if the powers that be were to get rid of raw types, generics could be simplified. The Java Language Specification states that raw types are strongly discouraged and may not be supported in future versions of Java.&lt;br /&gt;&lt;br /&gt;#4 Did I mention the syntax?&lt;br /&gt;&lt;br /&gt;Here is an example of a Collection data structure:&lt;br /&gt;&lt;br /&gt;Collection&amp;lt; ? extends Pair&amp;lt;String, ?&amp;gt;&amp;gt; c = new ArrayList&amp;lt;Pair&amp;lt;String,?&amp;gt;&amp;gt;();&lt;br /&gt;&lt;br /&gt;I would prefer not to study the Collection declaration for 10 minutes to figure out what it holds.&lt;br /&gt;&lt;br /&gt;Or here is one I really like:&lt;br /&gt;&lt;br /&gt;Enum&amp;lt;E extends Enum&amp;lt;E&amp;gt;&amp;gt;&lt;br /&gt;&lt;br /&gt;Huh? I feel my mind over-heating.&lt;br /&gt;&lt;br /&gt;Actually, this is explained in Angelika's FAQ.&lt;br /&gt;&lt;br /&gt;Experienced developers have been struggling with generics. Where does that leave junior programmers attracted to Java supposedly because it is simpler and more elegant than other OO programming languages?&lt;br /&gt;&lt;br /&gt;The whole thing almost smells of a political dispute within the Java language designer community. Why didn't they introduce generics from the start instead of adding it piecemeal halfway through? Is the state of type theory really that much more advanced than in 1995 when Java was introduced? Indeed, this would have made things a lot easier since a large part of why Java generics are so confusing is because of backwards compatibility issues.&lt;br /&gt;&lt;br /&gt;Despite all these misgivings, I have been moving over to generics and in some cases genericizing some of my APIs. Part of the reason I am doing this is that I am forced to. If I want to be a decent Java programmer, I have to know how to use generics. I've heard that it is even starting to crop up in job interview questions.&lt;br /&gt;&lt;br /&gt;Also, it does seem to make code a bit more readable if the type parameters are simple.&lt;br /&gt;&lt;br /&gt;List&amp;lt;Integer&amp;gt; list = new ArrayList&amp;lt;Integer&amp;gt;(); //Not so bad to understand.&lt;br /&gt;&lt;br /&gt;The new &lt;a href="http://code.google.com/p/google-guice/"&gt;Guice&lt;/a&gt; IOC container from Google also makes heavy use of generics. I haven't used Guice yet, but I look forward to seeing how Java generics play out in this context.&lt;br /&gt;&lt;br /&gt;I am starting to get used to generics, but I also feel like I have a long way to go before I can completely master this challenging subject .&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-7589906424693529758?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/7589906424693529758/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=7589906424693529758' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/7589906424693529758'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/7589906424693529758'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/06/java-generics-finally-drinking-kool-aid.html' title='Java Generics, Finally Drinking the Kool-Aid.'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-7033735639680913694.post-5613914110223704767</id><published>2007-06-13T19:32:00.000-07:00</published><updated>2007-08-17T20:37:14.713-07:00</updated><title type='text'>Welcome to RadioEiffel</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_UO4RaoE0QIU/RnCyV6JVNGI/AAAAAAAAAAM/xlHEvIkYVAA/s1600-h/JuujWerks2.jpg"&gt;&lt;img style="margin: 0pt 10px 10px 0pt; float: left; cursor: pointer;" src="http://3.bp.blogspot.com/_UO4RaoE0QIU/RnCyV6JVNGI/AAAAAAAAAAM/xlHEvIkYVAA/s320/JuujWerks2.jpg" alt="" id="BLOGGER_PHOTO_ID_5075752869501940834" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Welcome to RadioEiffel. I am finally joining the 21st Century and starting a blog. I intend to ruminate about software development; my profession as well as my hobby. Thanks for reading!&lt;br /&gt;Oh and here is a funny picture  of  my baby and me.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/7033735639680913694-5613914110223704767?l=radioeiffel.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://radioeiffel.blogspot.com/feeds/5613914110223704767/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=7033735639680913694&amp;postID=5613914110223704767' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5613914110223704767'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/7033735639680913694/posts/default/5613914110223704767'/><link rel='alternate' type='text/html' href='http://radioeiffel.blogspot.com/2007/06/welcome-to-juujwerks.html' title='Welcome to RadioEiffel'/><author><name>Julien Chastang</name><uri>http://www.blogger.com/profile/12092321608747060004</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='24' src='http://4.bp.blogspot.com/_UO4RaoE0QIU/SPqu6pVFeWI/AAAAAAAAABU/FMbDtkR29q0/S220/DSCN5379.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://3.bp.blogspot.com/_UO4RaoE0QIU/RnCyV6JVNGI/AAAAAAAAAAM/xlHEvIkYVAA/s72-c/JuujWerks2.jpg' height='72' width='72'/><thr:total>0</thr:total></entry></feed>
