Why does Dynamic Typing really matter?!?

Alex Martelli aleax at aleax.it
Fri Feb 7 04:59:29 EST 2003


Jason Smith wrote:

> Hi Alex
> 
>> but, it's not a deep and desperate need anyway (I do not know
>> of any case where I'd suffer a BIG loss of productivity if it
>> was impossible to change an object's type on the fly, _IF_
>> the whole system uses signature-polymorphism as below).
> 
> "signature" polymorphism is the same as "explicit" bounded
> quantification over types? i.e. haskell, forall a.b => a -> [String]
> -> b  etc...instead of letting the static inferencing take over..?

Nope.  You can perfectly well let type inferencing do its
job -- but when it sees for example a + b it will infer that
a and b are in SOME type in class Num -- it won't infer the
exact type YET, because all types in class Num have a (+),
e.g. as Prelude.hs says:

class (Eq a, Show a) => Num a where
    (+), (-), (*)  :: a -> a -> a
[etc]

i.e., any type a is in class Num if there exist (+), (-) and (*)
as binary functions onto a (and also belongs to classes Eq and 
Show, etc, etc).

Basically this is signature polymorphism at compile-time --
and so are C++'s templates, in a way that's not quite as
explicit or elegant, but has a few advantages of its own
in practical terms.  Python does it at runtime -- slower
(and you need unit tests to catch some errors Haskell would
catch during the compilation phase -- but, as you DO need
unit tests anyway to catch most errors, no real problem),
not explicit, reasonably elegant IMHO, *very* practical.


> I was under the impression that C++ templates were nothing more then a
> macro hack by the preprocessor, though I would love to hear
> otherwise..? please fill me in...

The preprocessor doesn't know about types, so it can't do
zilch with templates.  If I write, e.g:

template <class T>
T accumulate(T x)
{
    static T gg;
    gg += x;
    return gg;
}

then by C++ semantics, accumulate must be instantiated exactly
once for each different type it's called with -- and implicitly
can only be called with a type that support copy construction
(because the argument x is passed by value, and thus also is
the result returned), default construction (because of the way
gg is declared), and operator +=.  (A type with an inaccessible
destructor would also be inacceptable).  This set of operators
and special methods that must be available on T make up the
(implicit) "signature" T must respect to be acceptable here
to the C++ compiler.

So, I can call accumulate(23) and get one compile-time
instantiation of the template with T set to int, then
accumulate(2.3) and get another with T set to double, and
when I then call accumulate(45) it must be the first one
that's used again (so the result is 68).

(Then it gets hairy because you can, and in some cases must,
explicitly control the instantiations -- but, hey, I NEVER
accused C++ of being _SIMPLE_ in any way...:-).


Alex





More information about the Python-list mailing list