Find your next scenic drive!

October 4, 2004

The Pattern-Based Future...

InformationWeek has an article about Grady Booch about the future of software, and it appears that Grady thinks that the future is in Patterns, described as “algorithms that pull together objects.”

As a recap, the Software Patterns Movement started when Design Patterns: Elements of Reusable Object-Oriented Software (affectionately referred to as the GOF book) was published in 1994, and was greatly inspired by the works of Christopher Alexander, such as in The Timeless Ways of Building where Christopher's premise is that by observing and communicating architectural patterns, buildings could be made to perfection by simply assembling compatible patterns. Interestingly enough in Christopher's book, he states that all patterns should be written down, and in another round of the survival of the fittest, only the most fit patterns will spread.

In the software world, when the GOF book was published, an entire myriad of software patterns books were published. These software patterns vary in quality, but there are a lot of design patterns. It has become so uncomfortable to track down software patterns that books like The Pattern Almanac 2000, not to fail to mention a few attempts at publishing such information on-line, help organize them.

The article that started out this entire babbling kind of makes it seem like software patterns are new, but they are not as I have highlighted above. This being said, I still think that software patterns are important and are very much a part of the future. There is a lot to be learned from software patterns. As just a simple example of this, I have recently discussed the scope of class data members as being something fairly new to place data members as private instead of protected, however, if you look at the source within the Design Patterns: Elements of Reusable Object-Oriented Software book, many examples use this technique.

Learning algorithms and patterns is a way to leverage knowledge from before. There are very few problems that we solve that, as much as we would hate to admit, are truly unique. Generally the way that we build software today is by building components and modules and they are combined in ways that make our global application more or less unique, but many of the components created and the interaction between the components are not unique. Software patterns, like algorithms, present us with a catalog, where we can browse through the catalog in order to select patterns that meet the criteria that we are attempting to obtain from the software. In addition to this, it provides a language to communicate with other engineers; without the QuickSort algorithm, how would you describe the QuickSort algorithm? Just the QuickSort name provides a mental pictures in engineers that you do not need to describe the internal workings, such as the partitioning mechanisms, in detail.

Patterns offer the same communication advantage, however, the GOF book has introduced a form that patterns are in that can make patterns better. When dealing with books on algorithms, the algorithms generally only present the algorithm and may describe some areas where the algorithm will perform well and where it will not perform, but the form that algorithms are presented varies greatly from book to book. With software patterns, the GOF book has proposed a form that most software design pattern book follow. This form allows you to quickly look at the description and know what it does, why you may want to use it, how it works, and some consequences of using the pattern. This description provides you sufficient information to decide whether the pattern is applicable to what you are trying to do.

As Christopher Alexander mentions in The Timeless Way of Building, some patterns will eventually become part of your language, whereas others will not. Part of this is applicability, but part of this is also exposure, as Christopher mentions that the initial subset of a language that child learns is based on the set of words that the child is exposed to. As the person is exposed to more and more vocabulary, the person can make the vocabulary part of their language, or the person will simply know what the word means. And this becomes the language that you hear when communicating with them, similar to the words that I use on this blog are in the subset of my language.

The movement from algorithms to design patterns is a natural progression, as I mentioned in Knowing The Language. When we used to develop code line-by-line, it was easier for us to think at the algorithms level, however, with objects and components, it becomes more important to think at a higher level, and to describe the interaction of objects and components. This is where design patterns are incredibly useful, and I agree with Grady that this is not going to change in the immediate future.

Longhorn is a Big CLR Interpreter?

ACM Queue is running an article entitled Longhorn Ties Platform Apps to Core Operating System, which provides a rather fast overview of the Longhorn deliverables, all placed into a table. Of course, this is mostly old news. The only twist that is either new or I did not realize is that Longhorn is now going to be just a huge CLR interpreter, which will protect users from hardware and architecture implementation details, effectively giving each application a sandbox to work in by itself, similar to Java. The only true difference from Java is the fact that CLR is not part of the core operating system, similar to how Mozilla is not part of the core operating system but Internet Explorer is. I suppose that all the security patches in the past bit have not yet sunk in to keep things out of the core operating system...

October 3, 2004

Core Servlets and JavaServer Pages...

A bit ago, I downloaded the first edition of Core Servlets and JavaServer Pages from Javalobby, but electronic books of this length are harder to manipulate than a book, and so I have recently purchased Core Servlets and JavaServer Pages, Volume 1: Core Technologies, Second edition, and over all, I find it a good book. Of course, it should be noted that servlets and web development are not new to me, and as such, I skimmed through large portions of the book.

One of the key things that I enjoyed in this book is the fact that it teaches architecture and design of servlets. Instead of being strictly a HOWTO book, which illustrates samples left and right of how to do something, this book discusses some design issues to consider. For example, they do a good job at comparing Servlets to JSP. In this discussion, he shows how to do some advanced things like why you may want to consider using the MVC Pattern and how this would work with minimal effort. The only part that was lacking, in my opinion, were UML diagrams to show the structure of the classes involved in the MVC.

As another example, they describe cookies at length, discussing some of the pitfalls and some of the advantages, and then compares them with Sessions, which he also provides the same indepth discussion of how to use them, and how to avoid common pitfalls. A similar discussion occurs in the JSP section where they describe the applets; while they make it perfectly clear that applets may not be the best way to go, they go straight in to discuss all the common problems associated with applets, and how to get around them or to work with them.

In addition to focusing on Servlets and JSP, the book also points out some insights into Java. Although a lot of its content I was already very familiar with, I think that it would be a good book for someone who is new to Java. As an example of this, there are chapters that are dedicated to JDBC, and although it does not go deep into the topic, it does provide some good insight to make your queries faster.

Furthermore, the book also provides a good introduction to HTTP, forms, and other web-related technologies.

My only complaint in the entire book its HTML and CSS. The tags are all in caps and the documents are not well formed, making the transition to XHTML more difficult, not to mention harder to read. Regarding CSS, there are a very few references to it, and there is no entry in the index regarding CSS (the acronym or the full content).

Do not get me wrong; I am not saying that it should have a lot of content on CSS, and in fact its omission shows that developers should not be designing the look and feel of a site exclusively. But even with this rational, it would have been a good addition to simple discuss why developers should bother using CSS. Specifically, by defining the right classes, the designer can easily augment a predefined page without asking for code changes by simply changing the CSS file.

Volume II is not yet available, however, I am looking forward to taking a look at it, as it does cover more advanced topics than this particular book, such as JSTL, Apache Struts, JSF, JAXB, advanced JDBC and more.

Another book that has been recently released is Effective Enterprise Java by Ted Neward. This book is in Scott Meyers' Effective Software Development Series. I have only flipped through it so far, but its content looks interesting.

October 2, 2004

Java Generics: Better Code or Worse?

In the latest Java Specialists newsletter, it seems that some people were not comfortable with Generics, so much so that Heinz sent a follow-up, imploring us to send e-mails justifying our position on generics. In addition to sending this to the proper list (people who know me well already know which one), I decided to also say something here.

Prior to getting too involved in this discussion, however, it is important to realize that I have only started playing with Tiger when it was released on Thursday, and with this in mind, my comments are coming mainly from what I have read about Java's generics and what I know about C++'s templates. But really, the answer to this question is not about the language that is being used; it is about the techniques associated with generic programming.

With this in mind, my position is that Generics can make software easier to maintain. Recently, some Java Journalist commented on how the culture in Java would not generally be impressed by a developer who wrote their own container class; a normal reaction to this case would be to reuse one of the containers in the java.util package. In Java, we are more likely to reuse these classes; in other languages like C, where container implementations are not part of the standard library, developers must implement their own containers for each type, and the way that this is generally implemented is in one of two ways:

  • Copy and paste an existing implementation.
  • Roll your own.

While both points have their advantages, such as they can be optimized for your particular environment instead of being a general-purpose container, but both approaches have a similar disadvantage. In the former case, the copy and paste case, it is very likely that you are acquiring a perfectly working piece of code, but it is also possible that the code that you will be primarily using is not presently used, and therefore has bugs. On the same token, as software maintenance goes, the two pieces of code mature differently, such as a developer will modifying one, and forget to the other one. Over all, this is good recipe for disaster. In the latter case, you are reinventing the wheel. While yes, it is cool to show everyone that you still remember your High School lessons of how to write containers, this new implementation will need to be tested, and is is very likely that there will be a few bugs in the new wheel.

In C, a workaround to this situation is to use create container methods for a void* pointer, which basically permits the container to contain any type of data. In essence, this is similar to the java.lang.Object (only void* far worst, lacking, amongst other things, a ClassCastException). Up until J2SE 5.0, we had no alternative than to use a container of raw pointers. On one hand, this ability was good for those rare cases where you have a heterogeneous set of data, but in most cases, you have homogeneous types of data, or at least a common base class or interface that can be used, and constantly casting everything was error prone, in the sense that if you originally wrote a class to have a container of String, and later decided that it would be better to have a StringBuffer, depending on how your code was factored, it could still be possible that a String object either be inserted, removed, or accessed in the container. The only way to find out is to compile, test it, and see if you have any ClassCastException. And if that happens to work, I would just double check your test program to make sure that all the branches are tested in it.

This is one of the areas where generics come into play. In the previous example, if the user had created a LinkedList<String>. and then changed it to a LinkedList<StringBuffer>, then the compiler can catch any improper references that go into the linked list.

One of the other areas that C++ uses generic programming is with algorithms. Consider for a moment the std::distance method, which looks like:

template<class InputInterator>
typename iterator_traits<InputIterator>::difference_type
distance(InputIterator first, InputIterator second)

The above function (the implementation is left as an exercise) essentially takes two iterators and calculates the distance between them, returning the type associated with the container for the length parameter. The class is generic because any class that implements the interface of an InputIterator can execute this method. Now, the attentive reader will note that I just said the word interface; in C++, there is presently no interface support, and therefore, this above mechanism allows C++ the ability to fake interfaces, albeit harsh, in the sense that the exact interface is only supported via template instantiation or documentation (if any exists). The solution in Java would be simple, and it would not require any generics; it would simply require a class that abides to the InputIterator interface.

On the other hand, however, C++'s template specialization allows the for special interpretations of the iterators depending on the exact type of iterator. For example, in the case of a linked list, if you have a pointer at the beginning and one to the end of a sequence, the only way to discover the distance between them is to forward one iterator until they meet. However, in the case of a Vector in C++, where the elements are contiguous, you could subtract the value of the pointer at the end by the value of the pointer at the beginning. While the former approach does work on Vectors also, the latter implementation takes advantage of the underlying implementation, and optimizes this method. This genre of optimization, however, could not be done presently in Java (unless you used a instanceof hack), but this may eventually work. Furthermore, C++ allows the redefinition of types via the typedef keyword, as demonstrated above with the typename iterator_traits<InputIterator>::difference_type; this would allow containers to extensible in number; in other words, if an int were assumed, this would limit the container to having 231-1 entries, however, in C++, this number is defined by the container, and therefore, could be a long, float, or any other value at that.

Just going through some C++-based algorithms that are implemented via generics, I cannot seem to think of any algorithms that could not be rewritten without some proper abstraction of interfaces (perhaps some some generics in them) or members of a class, but I am still convinced that there are generic algorithms that would definitely benefit from Java's generics.

The new syntax of generics is definitely odd to Java developers, and to be honest, many C++ developers are uncomfortable with the syntax. As with any technique, generics could be over used, as mentioned here before. When designing coding, it is important to think about if it is a benefit for a language feature to be used. In my opinion, for C++, generic programming serves no purpose unless you have at least two truly different types using the generic service. With this in mind, if you are writing a class, such as a pool of database connections, then it is probably not a good idea to make the interface to the class generic, however, the internal workings would benefit from the type safety associated with homogeneous, checked containers, and as such, I would recommend it within.

In summary, since many containers of objects are homogeneous, Java's generic support allows this to be enforced by the language. Although interfaces can be used to replace some of the needs for generics, there are algorithms that exist that will truly benefit from the generic support. Between the code reuse and the type safety, I am sure that generics will render code easier to maintain.

October 1, 2004

Buying Borland JBuilder 2005...

On July 30th, I purchased a seat of Borland JBuilder Developer X from Borland's online store for download, but for some odd reason, I never got a download link. As is so trendy these days, Borland has outsourced their on-line store to Digital River, and I was rather persistent in calling, however, Digital River insisted that the problem was with Borland, and that I should e-mail them directly. However, when I e-mailed Borland, no one ever responded.

Around the same time, I purchased a seat of Gentleware's Poseidon for UML, and like many on-line orders, my license information came almost instantly; this is the entire point of on-line orders, though, where impulse buyers simply purchase software.

In the case of my purchase of JBuilder, Digital River required several follow-ups. When JBuilder 2005 was announced, I figured that the reason for the delay was the fact that they were planning to send me 2005. But alas, when Programmers Paradise had JBuilder availability, I started calling more frequently. Finally on Monday, I got to speak to a manager at Digital River, who promised me to open a new order and send a physical shipment of JBuilder, of which I would receive two e-mails. However, come Tuesday, I had not received any e-mails from them, so I followed up with Digital River again. Again they attempted to brush me off the phone, however, when I insisted that the order be canceled, suddenly she placed me on hold, and offered to send me a physical JBuilder Developer 2005 seat. But as this is a new order, their systems must charge me again, and then credit me the previous amount plus shipping and handling; I am not sure exactly how this is going to work, but alas, I have my seat of JBuilder Developer 2005.

The packaging is very cool, and I quickly threw the first CD into my Linux box. It should be noted that officially, Borland only supports RedHat Enterprise Linux or Java Desktop System, whereas I am running SuSE Linux Pro 9.1, but normally this is just normally the fine print.

I saw that it had a install-linux.sh script, so I ran it, and I waited. And waited. And waited. Finally, it came up, but it really took longer than I was expecting, especially for a menu with three options, viz. Install, Web information, and Close. I clicked Install, and again waited. Again, this took longer than I expected, but eventually the installer took over, and this went fairly smoothly.

After it was installed, I started it up, by pecking in /usr/local/JBuilder2005/bin/jbuilder, and shortly thereafter I got:

Invalid maximum heap size: -Xmx-600m
Unable to create JVM.

What? This is weird. After a trying various things, I eventually thought of looking in the /usr/local/JBuilder2005/bin/jbuilder.config file, which read:

vmmemmin 32m
vmmemmax 75%

Because of the 75% bit, I decided to change vmmemmax to 1024M, and finally it started. I guess JBuilder has some problems detecting 75% of 3,371,548 bytes for some reason.

I have not used JBuilder 2005 a lot yet, however, it looks a lot like JBuilder Developer X, but more refined, such as it shows you which files are checked out of CVS, even at the package level. Borland's Code Audit feature is also notably different than other code audits, in that it does not do your entire code-base, but rather the file that you are in. While this is good for new code, it is not possible to get a full report of all your existing code. In addition to this, it does not seem to be as complete as others that I have used, in the sense that its basic goal it to enforce coding style. Other code analysis programs, such as JLint report on thinks like potential deadlocks and other such issues.

Globally, it seems great, but I am still disappointed in the process that I had to go through in order to get my order. Two months to acquire a download purchase is extreme. Not responding to customer's e-mails is not acceptable. Things like this go against the entire premise of on-line ordering, where there is no second guessing. This is similar to web sites that use a mailto: link instead of a form for acquiring e-mail addresses; the mailto: link not only assumes that e-mail is configured, but instead of just a pecking in an e-mail address, customers are presented a message window, which is more of a commitment than sending their e-mail addresses regularly.

One man at Digital River that I spoke to at least twice on different occasions did indicate that he had never seen this before. While I am happy to hear that it was not a regular occurrence, they did not handle it well at all. But I am glad that it is over, and I can finally enjoy my JBuilder Developer 2005 :-).