Monday, April 30, 2007 

Metaphors and Design

I've been arguing for a while that good architects (not software architects) are usually familiar with the work of other good, renowned architects. Not only do they know about their works, they often know the inner vision behind those works, mostly because many famous architects have taken the time to talk and write about their inner vision, their approach with materials, with space, with shape. If they didn't, some critics did (a profession we seem to lack in software design).

This careful scrutiny of works and visions is something we seldom do in the software realm. Many software engineers are too concerned with the latest newfangled technology to give a damn about what some guy said 50 years ago (or 5, or 1). That has rather dramatic consequences on the overall maturity of the field. Good design requires vision. Vision (almost by definition :-) won't come from blindly following a trendy technology.

Unfortunately, even if we do want to learn from great software thinkers, there is a dearth of valuable material. I've often suggested to get acquainted with the works of David Parnas, whose influence on modern programming paradigms is undisputed. I can also recommend to read some of the Edsger W. Dijkstra manuscripts.
A nice start could be My recollections of operating system design. Sure, you won't find anything about the latest trends, but hey, here he's talking about inventing the concept of interrupt, the difficulty of separation of concern, early concurrency, and most importantly, about a discipline of thinking.

An interesting passage: "[...] created a host of new problems, so new that we didn't really know how to think and talk about them and what metaphors to use".
Abstraction is a cornerstone of software development (once you outgrow small programs, where programming on the metal is often the best thing). Yet abstraction is not enough: we need to find the right metaphors; poor metaphors are poor thinking tools.

It is interesting to see how people often try to sidestep metaphors, looking for a more machine-oriented way of thinking. This can be useful when you are trying to get familiar with some new concepts: for many years, people have found it useful to understand the mechanics behind inheritance, as a way to learn some OOP concepts. Of course, you can't effectively think at that level all the time: sooner or later, the whole inheritance+polymorphism metaphor must kick in, freeing you from low-level concerns.

This concept is also central in a short paper by Gregor Kiczales (It's Not Metaprogramming) about a "direct semantics" for AOP.
Kiczales is right claiming that although both metaprogramming and AOP might be seen as ways to manipulate code (through code generation or by method interception), this is a low-level view, and we should move toward more abstract thinking to design AO systems.
Unfortunately, it seems to me that the usual AOP concepts are still somewhat too low-level to engage in abstract thinking and modeling, and that some progress is still needed to find the appropriate metaphors. Maybe they'll emerge as AOP patterns, as the AOP dictionary seems quite established by now.

Curiously enough, Kiczales talks about virtual machines as a metaprogramming concept, while I see them as valuable AOD metaphors (for some problems - it's not a universal metaphor). I think that the main distinction is that he's talking about building a virtual machine at the extra-linguistic level, while I'm talking about building a virtual machine (so to speak) at the programming language level. I'll soon elaborate this concepts in a few posts.

Labels: , ,

Comments:
Credo che mi sia chiara la parte sulle metafore :D ma c'ho qualche problemino quando dici: "Curiously enough, Kiczales talks about virtual machines as a metaprogramming concept, while I see them as valuable AOD metaphors (for some problems - it's not a universal metaphor)." Io davvero proprio non riesco a vedercele le virtual machine come AOD metaphors, puoi spiegarti meglio? (qualche metafora sarebbe utile :D)
 
Sara' piu' utile un esempio... ci sto pensando, alla fine credo servira' piu' di un post per completarlo... forse in settimana scrivo il 1o della serie.
 
L'idea di utilizzare la macchina virtuale come metafora per meglio individuare e modellare i concern non funzionali piace anche a me (benche' non abbia fatto nessuna prova sul campo).
Mi sembra pero' che la metafora si fermi alla fase di design e non arrivi a quella di implementazione a meno di non avere risorse sufficienti per costruire veramente quella macchina virtuale.
Mi spiego meglio. Altrove tu dici che "application design is language design" e dici anche che non sempre c'e' l'opportunita' di costruire un compilatore per quel linguaggio applicativo ma ci si puo' accontentare di una approssimazione ottenuta in linguaggi a "due livelli" come il c++.
Vale la stessa cosa per la macchina virtuale mi pare. Se ho un linguaggio AO la implemento come aspetti, se ho gia' una macchina virtuale spero di poterla estendere tramite meta-object protocol o simili. Se non ho nessuna di queste opportunita' avro' un'alta impedenza tra design e implementazione. E' come avere un linguaggio "ad un livello" per il caso precedente.
Ho inteso bene? Ho hai anche qualche idea di come ci si possa approssimare ad una macchina virtuale in linguaggi come il c++?
 
Michelangelo, hai inteso benissimo.
E' esattamente una metafora per guidare il design (in alcune situazioni che si prestano bene), cui segue una implementazione "ideale" in termini di aspetti o MOP.

In linguaggi/ambienti run-time che non prevedono nulla di simile, l'impedenza di un design VM-based e' probabilmente troppo forte per ottenere un mapping sensato. Si puo' sempre fare qualcosa (come implementare l'OOP in C), ma difficilmente il risultato complessivo brilla per chiarezza.

Per un po' ho provato a giocare con l'idea che opportune classi contenitore in C++ potessero mappare alcune virtual machine elementari, ma non si va molto avanti su questa strada (peraltro gia' battuta da altri, magari senza riferimenti al parallelo con le VM).

Peraltro credo che un design VM-inspired si mappi relativamente male anche in un linguaggio a mixin layers, ma qui dovrei decisamente pensarci meglio.

D'altra parte, la strada per arrivare a delle buone tecniche di aspect oriented design (nel senso piu' ampio) mi pare ancora piuttosto lunga, ed ogni volta che identifico un concetto potenzialmente buono sono gia' contento ;-)
 
Post a Comment

<< Home