Say no to the EU Constitution

First, let me clarify: I love the idea of a European Constitution. I think it’s the next logical step in taking the EU to the next level. But what should a constitution deliver?

First, there is form. It should be concise, and it shouldn’t be law. It should be a document that enables law-making. This constitution (the annotaded version linked above is over 400 pages!) has many articles that, in my opinion, just don’t fit that criteria – it goes into far too much detail. These details should be laws, interpreted and checked against the constitution.

Second, it should be consistent. Reading the constituion, it feels that the writers had to bend over backwards so many times to address many contradicting concerns. It is not only difficult (if not impossible) to please everybody, doing this will create legal headaches for decades to come. I am sure lawyers specializing in EU law will be the only ones delighted.

But third, and most importantly, it should put the EU on a sustainable, visionary course. And this is where the constitution fails the most. As the Economist puts it:

What is needed instead is a treaty that acknowledges the central popular concern: that an EU that is increasingly remote is also a threat to the diversity of Europe’s nations and thus to national identity. (…) The central thrust of the document is towards more centralisation.

I wish for the constitution to fail, and the lawmakers to get back to the table to draft a new constitution from scratch. Maybe they should read the German or American constitutions for inspiration.

Spamalot on Broadway: lame

So, what was wrong with the show? In one sentence: It was not original at all, and leeched off the Monty Python Franchise. Somebody who had never seen the movie would have been lightly amused by the jokes, and only knowing the film made them hillarious – and the audience loved it.

Maybe it’s me, but I am not easily amused by recycled jokes. They are okay for a stand-up commedian or a Highschool-Theater production. But a Broadway Production, where even the cheapest tickets are barely affordable? Sorry, but then I’d rather see either a show that pushes the Envelope (like Elton John’s Aida), or a really well-acted classical piece, like Marsha Norman’s “night, Mother”.

My recommendation: Rent the movie, Invite a few friends over and crack a few coconuts.

Der verflixte Primary Key

Na ja, eigentlich ist das Thema kein Java Thema – aber hier werde ich Ansätze diskutieren, die Java benutzen.

Warum wollen wir überhaupt verschiedene Datenbanken unterstützen – warum legen wir uns nicht auf eine fest? In meinem Bereich hautpsächlich aus den folgenden zwei Gründen: (1) Entwickler können eine andere (“leichtere”) Datenbank zur Entwicklung benutzen, und eine andere in der Produktion, und (2) Kunden können je nach Bedarf und Preis die Datenbank auswählen (z.B. mysql für kleine Systeme und Oracle für große).

Leider ist die PK-Erzeugung bei kaum einer Datenbank perfekt. Zum einen sind die Mechanismen oft nicht kompatibel – der SQL Dialekt ist zu verschiden. Ausserdem sind fast immer zwei Datenbankoperationen notwendig, obwohl nur eine Operation ausgeführt wird:

  • (1) PK erzeugen, und dann (2) Zeile in die Datenbank einsetzen, oder:
  • (1) Zeile in die Datenbank einsetzen und dabei den PK generieren, und dann (2) den soeben erzeugten PK aus der Datenkbank holen.

Der zweite Fall kann mit manchen Datenbanken auf eine Operation reduziert werden, wenn Stored Procedures benutzt werden – aber das bindet das System noch stärker an eine bestimmte Datenbank.

Wo kommt der PK her? Wie schon angedeutet, kann der PK beim einsetzen einer Zeile in die Datenbank erzeugt werden – MySQL zum Beispiel hat das AUTO_INCREMENT Keyword, und HSQLDB statt dessen IDENTITY. Der andere übliche Weg ist eine SEQUENCE, aber MySQL kennt diesen Datentyp gar nicht.

Ein weiterer Ansatz, der Kompatibilität einfacher macht, ist eine Sequence-Tabelle – eine Tabelle mit dem einzigen Zweck, PKs zu erzeugen. Und Spring’s DataFieldMaxValueIncrementer Implementierungen nutzen diesen Ansatz. Und nun kommen wir zum eigentlichen Thema dieses Artikels: Wie sollte so eine Sequenz-Tabelle implementiert werden?

Caching

Bevor wir ins Detail der Implementierung gehen, möchte ich auf das Sequence Blocks Entwurfsmuster aufmersam machen. Diese Technik erlaubt es uns, das oben beschriebene Problem der doppelten Datenbankoperation zu beseitigen. Dieses Design Pattern wird von Floyd Marinescu in “EJB Design Patterns” beschrieben.

Bei diesem Pattern wird nicht nur eine, sondern ein Block von PKs aus der Datenbank geholt. Dieser Block wird im Speicher behalten. Wenn diese PKs aufgebraucht sind, wird ein neuer Block geholt. Der einzige Nachteil dieser Technik: Sollte der Prozess, der die PKs haelt, abstürzen, so werden die zu dem Zeitpunkt gehaltenen PKs nie benutzt, es ergibt sich also eine “Lücke” in den benutzten PKs. Für die meisten Anwendungen spielt das allerdings keine Rolle. Spring’s DataFieldMaxValueIncrementer kann dieses Muster benutzen.

Eine Sequenztabelle pro PK?

In der Spring Architektur gibt es “ein Sequenzobjekt pro PK”. Das Sequenzobjekt ist eine Tabelle für MySQL und HSQLDB, und eine Sequenz für DB2, Oracle und PostgreSQL. Das ist ein sicherer und effizienter Ansatz, den so können die Fähigkeiten der benutzten Datenbank voll ausgenutzt werden. Allerdings geht damit wieder ein Stück Portabilität verloren – aber wenigstens ist die Anwendung nach wie vor Unabhängig von der Datenbank, auch wenn der Sequenzgenerator datenbankspezifisch konfiguriert werden muss.

Und hier frage ich mich: Gibt es einen besseren, Datenbank-Unabhängingen Ansatz, den PK zu erzeugen? Wenn uns das gelingen sollte, können wir bei einfachen Anwendungen vielleicht sogar Hibernate benutzen, um die Datenbanktablellen für uns zu erzeugen. Aber das Hauptproblem ist Synchronisation. Wir wollen auf keinen Fall, dass zwei unabhängige Prozesse ausversehen den selben PK erzeugen, z.B. folgendermaßen:

  • Prozess 1 erhöht den Zähler
  • Prozess 2 erhöht den Zähler
  • Prozess 1 ließt den Zähler
  • Prozess 2 ließt den Zähler

Selbst wenn wir Transaktionen benutzen, kann dieses Szenario zu doppelten PKs führen (je nachdem, wie Locking implementiert ist, aber darauf wollen können wir uns nicht verlassen). Allerdings können wir explizit die Tabelle (oder besser, Zeile) sperren, und dann wird es funktionieren.

Die letzte Frage ist dann: brauchen wir nach wie vor eine Tabelle pro Sequenz, oder können wir alle Sequenzen mit einer Tabelle bedienen, zum Beispiel so:

 +------+-------+ | name | value | +------+-------+ | seq1 |     5 | | seq2 |   383 | +------+-------+ 

Wenn wir einzelne Zeilen sperren können, ist das ein legitimer Ansatz. Falls allerdings die gesamte Tabelle gesperrt werden muss (bei wenigen Datenbanken der Fall), kann es zu Performanzproblemen kommen, erst recht, wenn das Sequence Block Muster nicht genutzt wird.

Die Praxis

Wie sieht das ganze in der Praxis aus? Ich teste diesen Ansatz im Moment mit einer Hibernate/Spring Implementierung. Der wichtigste Aspekt ist natürlich rigeroses Testen, was gar nicht so einfach ist, da es hier ja um Raceconditions geht. Ich werde diesen Artikel in ein paar Tagen erweitern, sobald ich mit meinem Ansatz zufrieden bin.

1400×1050 with Intel Mobile 915GM

I started off with a clean Suse 9.2 installation. After various dead ends, this is what I did so far:

  • Reinstall X.org (X11R6.8.2) from the sources. This seems necessary to compile the Intel drivers.
  • Install Intel’s linux driver. Without recompiling X first, this kind of fails, but still seems to do something to the system. After the above reinstallation, the installation succeeds without an error.
  • Run “modprobe intel-agp” before starting X. Obviously, this should be automated, once everything is working.
  • Set 1400×1050 as a legal resolution in the Video Bios using 855resolution. However, this doesn’t seem to work with my Bios.
  • I guess I’ll have to update 855resolution. That doesn’t seem so difficult after all. the trick seems to be to make the video bios writable by talking to the right ports. Fortunately, the Intel 915GM Specification is freely available. Thanks, Intel!
  • It turns out there is a tool that tweaks the 915GM!!! The tools is available on Steve Tomljenovic Geocities site (thank you, Steve!!!), and I got pointed there by Christian Zietz on the XFree86.Org Developers Mailing List (thank you, Christian!!!).
  • The tool 915resolution must run on every start – just put the following in /etc/rc.d/boot.local: “915resolution 5c 1400 1050” (on Suse)

Windows Refund for Laptops…?

The short answer is no.

The long story: I looked on the web, but there was suspiciously little information available. The best I found was this Linux Journal Article, and going to court sounded like too much trouble for me. I also Asked Slashdot, and while the discussion was interesting, there was little useful information there.

But here is the interesting twist: I went to Microsoft’s web site and checked out the Windows XP Professional License, which definitely sounded like I could return the software and keep the computer:

“This EULA is a legal agreement (…) for the Microsoft software product identified above (…) (“Product”). (…) IF YOU DO NOT AGREE, DO NOT INSTALL OR USE THE PRODUCT; YOU MAY RETURN IT TO YOUR PLACE OF PURCHASE FOR A FULL REFUND.”

However, when I actually looked at the license of the laptop I bought, it turned out that it had a different license! And it was very specific about not being able to return the software without returning the computer at the same time:

“This EULA is a legal agreement between you (…) and the manufacturer of the computer system or computer system (“HARDWARE”) with which you acquired the Microsoft software product(s) identified on the Certificate of Authenticity (“COA”) affixed to the HARDWARE. (…) IF YOU DO NOT AGREE TO THE TERMS OF THIS EULA (…) YOU SHOULD PROMPTLY CONTACT MANUFACTURER FOR INSTRUCTIONS ON RETURN OF THE UNUSED PRODUCT(S) FOR A REFUND. (…) The SOFTWARE is licensed with the COMPUTER as a single integrated product.

How twisted! Not only do they explicitly state that I cannot return the software, they also state that the software is “bound” to this computer. Well, on the other hand, by using a license like this, they probably only payed a fraction of the official XP price for the software. I’ll keep Windows around on a small partition, as a backup, but this license still bothers me.

Tricks mit Collections

Hash und Tree Implementierungen

Ich gehe mal davon aus, dass der Leser die Collection Interfaces List, Set und Map kennt. Reden wir doch mal ein bisschen über Sets:

Set fruit = new HashSet(); fruit.add("Apple"); fruit.add("Orange"); fruit.add("Banana"); fruit.add("Cherry"); System.out.println(fruit); 

[Apple, Orange, Banana, Cherry]

Soweit, so gut. Was aber, wenn wir die Früchte alphabetisch sotiert haben wollen? Das erreichen wir ganz einfach, indem wir statt einem HashSet ein TreeSet benutzen:

Set fruit = new TreeSet(); 

[Apple, Banana, Cherry, Orange]

Warum funktioniert das? Weil im zweiten Fall die Implementierung den Inhalt des Sets in einer Baumstruktur speichert, und damit garantiert, dass Einträge in log(n) gefunden werden können. Beim HashSet hingegen kann die Performanz an die Bedürfnisse gut angepaßt werden, indem beim Instantiieren die Anzahl der “Buckets” der Anwendung entsprechend gesetzt wird.

Im allgemeinen sind die Hash-Funktionen schneller, aber ein sortiertes Set zu haben, kann unbezahlbar sein. Ein paar Dinge sind zu beachten: Elemente im TreeSet müssen Comparable implementieren, sonst wird eine Exception geworfen. Außerdem kann ein HashSet null enthalten, TreeSet nicht.

Initialisierung

In dem Beispiel weiter oben wollen wir vier Früchte in unserem Set haben. leider können wir diese nicht dem Konstruktor mitgeben. Aber mit einem Trick wir können eine Klasse ableiten, die diese Werte in das Set einträgt:

Set fruit = new TreeSet() {{ add("Apple"); add("Orange"); add("Banana"); add("Cherry"); }}; 

Collections Klasse

die Collections Klasse wird oft übersehen, enthält aber einen Haufen unglaublich pratischer statischer Methoden. Diese fallen in die folgenden Kategorien:

Such- und Sortierfunktionen: Kleinstes und größtes Element, oder gleich die ganze Liste sortieren, und mit bestimmten Suchalgorithmen ein Element finden. Es können auch gezielt nur bestimmte Teile einer Liste durchsucht werden.

Kopieren, ersetzen, verdrehen: Collections können per Zufall vermischt werden, Kopien erstellt werden, oder mit einem bestimmten Objekt viele Male gefüllt werden.

Wrapping: Eine unmodifizierbare oder synchronisierte Version einer Collection können erzeugt werden. Besonders das Wrapping ist extrem nützlich. Wenn eine Funktion ein Set zurückgibt, das nicht verändert werden darf, kann das entweder dokumentiert werden (kann ignoriert werden), oder ein neues Set kann erzeugt werden:

return new TreeSet(fruit); 

Oder, die beste Lösung, wir geben ein nicht modifizierbares Set zurück:

return Collections.unmodifiableSet(fruit); 

Anfragen an das zurückgegebene Set werden an das interne Set weitergegeben – aber jeder Versuch, das Set zu ändern, wirft eine UnsupportedOperationException. Das war’s für heute! Zum Abschluß möchte ich noch herzlich den Collections Framework Overview empfehlen, der noch weiter auf die Philosophie der Architektur eingeht. Viel Spaß beim Lesen!

Larry Summers und Diskriminierung gegen Frauen

Was ist der eigentliche Skandal? Das Thema “Akademische Karrieren für Frauen” anzusprechen ist grundsätzlich legitim. Die Frage ist, ob Summers, in der Rolle des Präsidenten von Harvard, dieses Thema ansprechen darf. Vom Economist:

    “And the firestorm is not about one judgment, but about his right to raise the issue of innate differences at all.”

Jetzt, wo die Katze aus dem Sack ist, stellen sich zwei ganz wichtige Fragen: (1) Hat Summers recht oder nicht mit seinen drei Thesen:

  • Discrimination and social pressure might hold women back
  • 80-hour-a-week science careers might be harder for women to take on
  • the outcome might be related to findings that men tend to be over-represented at the top of science-aptitude tests

Und (2), was man deswegen unternehmen sollte.

In Anbetracht der Tatsache, dass Summer gebeten wurde, eine provokative Rede zu halten, und zwar nicht in der Rolle des Harvardpräsidenten, kann ich schon nachvollziehen, wie es zu dieser Rede kam.

    “Note first that this was given in a private capacity to an economics conference, and that he had been briefed to ask provocative questions”

Meine persönliche Meinung: Ich glaube nicht, dass Summers sexistisch ist, oder rücksichtslos. Aber ich glaube auch nicht, dass er diese Rede “aus versehen” gehalten hat, und sich nicht über die Implikationen im Klaren war. Summers hat noch nie etwas davon gehalten, sich auf Zehenspitzen zu bewegen (ich war in Boston, als er das Thema “Grade Inflation” ansprach – das gab auch einen ganz schönen Aufruhr). Ich glaube, dass er das Thema bewusst angesprochen hat, um die Situation zu verbessern. Von seiner Rede:

    “What should we all do? I think the case is overwhelming for employers trying to be the [unintelligible] employer who responds to everybody else’s discrimination by competing effectively to locate people who others are discriminating against, or to provide different compensation packages that will attract the people who would otherwise have enormous difficulty with child care. (…) But I think it’s something that has to be done with very great care because it slides easily into pressure to achieve given fractions in given years, which runs the enormous risk of people who were hired because (…) being seen by others as having been hired for some other reason. And I think that’s something we all need to be enormously careful of as we approach these issues, and it’s something we need to do, but I think it’s something that we need to do with great care. ”

Und damit spricht Summer selbst an, was die Sorge des Authors des Emails war, weswegen ich dies alles schreibe:

    Ein befreundeter Theologe und Unternehmensberater macht mich auf eine Kontroverse bei Harvard aufmerksam, deren Bedeutung weit über diese und andere Universitäten hinausreicht. Es geht um die Frage, wie der möglicherweise unterschiedliche “Erfolg” von Frauen und Männern in der Wissenschaftskarriere zu beurteilen ist, und welche Konsequenzen sich daraus für die Anstellungspraxis ergeben.

Aber hier ist noch ein weiterer, wichtiger Aspekt: Diese Diskussion hat unterschiedliche Implikationen auf den amerikanischen und den deutschen Markt.

Zunächst der Amerikanische: Ich würde behaupten, dass es in dem diskutieren Arbeitsmarkt (Professuren fuer die Ivy League) keine Diskriminierungen gegen Frauen gibt, und gerade in der Einkommensklasse wird penibel auf “Political Correctness” geachtet (uebrigens ist MITs Praesident seit kurzem eine Frau, Susan Hockfield). Als vor kurzem Carly Fiorina, CEO von HP, gefeuert wurde, war sich die Presse einig, dass sie wegen Inkompetenz, und nicht Diskriminierung gehen musste. Dennoch werden lediglich 7 von den Fortune 500 Firmen von Frauen geleitet – warum? Diese Frage versuchte Summers zu beantworten.

Meiner (subjektiven) Meinung nach ist der Deutsche Arbeitsmarkt wesentlich diskriminierender, und nicht nur gegen Frauen, sondern auch ältere Menschen. Hier ist eine Geschichte von einer Freundin (das war Anfang der 90er). Sie bewarb sich um eine Stelle, die sie nicht bekam. Die Personalchefin sagte ihr “unter der Hand”, dass sie zwar kompetent sei, aber sich die Firma es sich nicht leisten kann, eine Frau in den Mitte 20ern einzustellen. Ich weiss nicht, wie sich Deutschland in den letzten 15 Jahren gewandelt hat, aber die Geschichte hat mir doch einen ganz schönen Schrecken eingejagt.

Zum Absschluss noch ein weiteres Zitat aus dem Economist:

    “In the end, the debate about Mr Summers comes down to a simple choice. On one side sit short-term expediency and censorship; on the other, freedom of speech and long-term effectiveness. If Mr Summers’s foes manage to sack or gag him, they may have a happier university in the short term. But they will have snuffed out an invigorating source of criticism in a cosy world. And they will also have endangered the fundamental right of an academic to ask questions. This should be enough to make liberal opinion everywhere start gasping for air.”

“The Gates”

I was lucky enough to see the Exibit, on the second day. It was a beautiful day with blue sky. Conciously, we entered the park on 86th Street (West Side), as we correctly assumed it would be less crowded there than on 59th Street. The first impression was… anticlamactic. After having seen pictures of the German Reichstag, initially, the installation felt small. But after strolling through the park for only a few minutes, everything started to sink in, and it was a beautiful, meditative experience. There was so much to discover, everybody had time and it felt like learning to see all over again. Did you ever have the experience of visiting a new city, looking at every building and going “wow”? Did it ever occur to you that you’d do the same in your home town, if it wouldn’t be your home town?

We strolled through the park for three hours, and it was worth it every minute of it. As a highlight, we saw Christo and Jeanne-Claude drive by in a limo with their entourage. I didn’t feel the need to come back – still today, they day the installation is taken down, I feel a little melancoly and still happy that I was lucky enough to experience this.