Can someone please explain to me why Apple implemented AirTunes in such a way that it seems only iTunes can work with it? That's highly stupid. If I already have a way to connect my stereo system to my Mac, I don't want to use it just for iTunes - at least the DVD Player should get the same comfort. Even better would be a general solution - although I would understand if they didn't do that. After all, AirTunes requires streaming digital music - and in a suitable streaming format. But DVDs already produce that natively, so why can't I select an AirTunes device? Rarely stupid.
FireWire not dead, but it's on life support - but the life support is pretty bad. Just checked again: the new iPods (Nano and Video) no longer have FireWire. Which is quite ridiculous, because my Mac Mini doesn't have USB 2 - and I really don't want to copy my music collection with USB 1. What is Apple thinking with such a stupid thing? FireWire can certainly not be replaced by this miserable USB 2. Even new computers will probably only reluctantly include a FireWire port if the machines from Apple are considered suitable for video content. A real shame, because FireWire is a really useful connection technology that also offers good performance reserves for future devices - and unlike USB 2, it doesn't overload the CPU with data shoveling.
appscript - Python as an alternative to AppleScript. Thus, application control via the AppleScript interfaces directly from Python programs.
PEAK has been offering generic functions similar to CLOS for Python for quite some time. I always wanted to play around with it, but for a long time it was just part of PyProtocols, and the installation was a bit tricky. However, since September of this year, it has been decoupled and much easier to install. So I dove right in.
And I must say: wow. What Phillip J. Eby has accomplished is truly fantastic. The integration with Python (works from Python 2.3 - he even invented his own implementation of decorators for Python 2.3) is superb, even if, of course, some things take a bit of getting used to.
A small example:
import dispatch
[dispatch.generic()]
def anton(a,b):
"handle two objects"
[anton.when('isinstance(a,int) and isinstance(b,int)')]
def anton(a,b):
return a+b
[anton.when('isinstance(a,str) and isinstance(b,str)')]
def anton(a,b):
return a+b
[anton.when('isinstance(a,str) and isinstance(b,int)')]
def anton(a,b):
return a*b
[anton.when('isinstance(a,int) and isinstance(b,str)')]
def anton(a,b):
return b*a
[anton.before('True')]
def anton(a,b):
print type(a), type(b)
This small example simply provides a function called 'anton', which executes different code based on the parameter types. The example is of course completely nonsensical, but it shows some important properties of generic functions:
- Generic functions are - unlike classic object/class methods - not bound to any classes or objects. Instead, they are selected based on their parameter types.
- Parameter types must therefore be defined - this usually happens via a mini-language with which the selection conditions are formulated. This is also the only syntactic part that I don't like so much: the conditions are stored as strings. However, the integration is very good, and you get clean syntax errors already when loading.
- A generic function can be overloaded with any conditions - not just the first parameter is decisive. Conditions can also make decisions based on values - any arbitrary Python expression can be used there.
- With method combinations (methods are the concrete manifestations of a generic function here), you can modify a method before or after its call without touching the code itself. The example uses a before method that is always (hence the 'True') used to generate debugging output. Of course, you can also use conditions with before/after methods to attach to specific manifestations of the call of the generic function - making generic functions a full-fledged event system.
A pretty good article about RuleDispatch (the generic functions package) can be found at Developerworks.
The example, by the way, shows the Python 2.3 syntax for decorators. With Python 2.4, of course, the @ syntax can also be used. One disadvantage should not be kept secret: the definition of generic functions and their methods is not possible interactively - at least not with the Python 2.3 syntax. Unfortunately, you generally have to work with external definitions in files here.
RuleDispatch will definitely find a place in my toolbox - the syntax is simple enough, the possibilities, however, are gigantic. As an event system, it surpasses any other system in flexibility, and as a general way of structuring code, it comes very close to CLOS. It's a shame that Django will likely align with PyDispatch - in my opinion, RuleDispatch would fit much better (as many aspects in Django could be written as dispatch on multiple parameter types).
LTK - The Lisp Toolkit - if it should just be a bit of GUI, but not necessarily the big hammer is needed - LTK offers simple bindings for TK in Common Lisp. Works excellently with OpenMCL together, even CLISP likes it.
Sams Teach Yourself Shell Programming in 24 Hours - A whole book about shell programming. And of course, a pretty good introduction to the various tools that Unix systems provide. Certainly recommended for anyone who, for example, has gotten a root server and now wants to do more with it - but otherwise knows Linux mainly from the GUI.
Thieves with a taste for art?
With the help of a crane, three thieves in Great Britain stole a two-ton bronze sculpture by the world-renowned artist Henry Moore. [...] The police expressed the suspicion that the trio of thieves had their eyes solely on the material value and wanted to melt down the figure.
Melt down? Definitely a taste for art!