Various (and almost completely unrelated) questions and opini ons

classic Classic list List threaded Threaded
7 messages Options
Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opini ons

James Hague-3
> Have you looked at Oberon? I am somewhat persuaded by the
> Oberon rationale
> against overloaded operators. Oberon is roughly my idea of
> what a C level
> language with objects should have been. They claim extreme
> simplicity is
> a good thing. To back it up, the Oberon language
> specification is coherent
> and complete in something like 28 pages. See other simple
> languages, eg
> R5RS for contrast.

Overloaded operators don't make sense in a functional language, IMO.
Actually, I'd argue that they don't make sense in C++.  If you consider
matrix multiplication, the old style C way was like this:  matmul(result, a,
b).  The pain isn't from having to type "matmul" instead of "*", it's from
having to keep track of temporary variables to hold intermediate results.
This could be rewritten to use returned structures instead:  result =
matmul(a, b).  That takes care of most of the problem.

In functional languages the "structure return" style is the norm, so I don't
see a need for overloaded operators.  In fact, I'd be just fine with having
to type add(X,Y) everywhere instead of A+Y, as long as there were versions
of add that supported different numbers of parameters.  Maybe I'm just weird
:)

James


Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opinions

Chris Pressey
David Gould wrote:
> Have you looked at Oberon?

Only briefly.  I used to use Pascal a lot and Modula-2 some, but
eventually got kind of sick of Wirth languages.

> Anyway, the Oberon argument is that code should be understandable by
> reading it. That is, what is being done and the cost of doing it should
> be apparent by looking at it. The problem with overloading is that "A + B"
> could mean anything, eg "blend these two 80MB images", and it is not obvious
> from the immediate source what the heck is going on or what it might cost.

Well, yes.  That's a valid argument for cost-conscious programming.  Of
course, it also happens to be an argument against polymorphism,
inheritance, and any other feature that makes it hard to "judge the cost
by the syntax."

I mean, you can already say

  add(X,Y) when number(X), number(Y) -> X + Y;
  add(X,Y) when element(1, X) == image -> LiC(X,Y).

which means it's already possible to write Erlang code which is hard to
judge the cost of by looking at the application.

> > only of limited use unless you can have user-defined functions in
> > guards.  This is assuming that the semantics of any overloaded operator
> > are expressed by a user-defined function, and that relational operators
> > can be overloaded.
> I like the rationale for the restrictions on guards, that they are
> restricted to known time or constant time operations without side
> effects.

What is worse to me is the unorthogonality - that I can't say integer(X)
or tuple(X) outside of a guard and mean the same thing.

James Hague wrote:
> Overloaded operators don't make sense in a functional language, IMO.
> Actually, I'd argue that they don't make sense in C++.  If you consider
> matrix multiplication, the old style C way was like this:  matmul(result, a,
> b).  The pain isn't from having to type "matmul" instead of "*", it's from
> having to keep track of temporary variables to hold intermediate results.

Well, actually, for me, the pain is having those parentheses - a nesting
level.  I work with rather long numerical expressions.  And to me it is
much easier to read

  a * b * c * d * e * f * g.

than

  matmul(a, matmul(b, matmul(c, matmul(d, matmul(e, matmul(f, g)))))).

"Gobs and gobs of nested brackets" is not one of elements of the LISP
heritage in Erlang that I particularly like! :-)

But this all points to the fact that what I am thinking of is in fact a
different language than Erlang, and I shan't complain about these
characteristics of Erlang in the future.  No overloading, guards are a
form of type constraint, and so forth, for the sake of predictability
and ease of cost judgement.

_chris

--
"Ten short days ago all I could look forward to was a dead-end job as a
engineer.  Now I have a promising future and make really big Zorkmids."
Chris Pressey, Cat's Eye Technologies, http://www.catseye.mb.ca/
Esoteric Topics Mailing List: http://www.catseye.mb.ca/list.html


Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opinions

David Gould-2
On Wed, Feb 21, 2001 at 03:29:10PM -0600, Chris Pressey wrote:
> David Gould wrote:
> > Have you looked at Oberon?
>
> Only briefly.  I used to use Pascal a lot and Modula-2 some, but
> eventually got kind of sick of Wirth languages.

This happens, but Oberon is I think the nicest of all the Wirth efforts.
 

> Well, yes.  That's a valid argument for cost-conscious programming.  Of
> course, it also happens to be an argument against polymorphism,
> inheritance, and any other feature that makes it hard to "judge the cost
> by the syntax."
>
> I mean, you can already say
>
>   add(X,Y) when number(X), number(Y) -> X + Y;
>   add(X,Y) when element(1, X) == image -> LiC(X,Y).
>
> which means it's already possible to write Erlang code which is hard to
> judge the cost of by looking at the application.

Sure, but by that standard, any function call is obscure at the limit. What
I meant, I think, is that viewing the source text and searching in the
source text gives the reader at least a fighting chance to find what is
going on. In the Erlang example you give, the definition is explicit, the
rule to select which definition is explicit, and text searching will find
the definition. In the countercase (why is it always C++?), overloading
something like "+" combined with some overuse of inheritance and a macro
or two makes it almost impossible to tell what "+" gets resolved to without
stepping it in a debugger or reading the entire program and libraries.


> What is worse to me is the unorthogonality - that I can't say integer(X)
> or tuple(X) outside of a guard and mean the same thing.

Ok, I think I agree. If it looks like a function, it should be a function.

This is my main problem with python, some code things are functions and some
are subroutines that do not return a value.

> But this all points to the fact that what I am thinking of is in fact a
> different language than Erlang, and I shan't complain about these
> characteristics of Erlang in the future.  No overloading, guards are a
> form of type constraint, and so forth, for the sake of predictability
> and ease of cost judgement.

Please do not fall out of love so fast... and I certainly do not speak for
the Erlang designers, so maybe overloading is coming soon.

-dg

--
David Gould                davidg               510 536 1443
If simplicity worked, the world would be overrun with insects.


Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opinions

Chris Pressey
David Gould wrote:
> On Wed, Feb 21, 2001 at 03:29:10PM -0600, Chris Pressey wrote:
> > [...] it's already possible to write Erlang code which is hard to
> > judge the cost of by looking at the application.
> Sure, but by that standard, any function call is obscure at the limit.

OK.  I suppose my point is that this sort of feature can always be
abused.  If you disallow it by not offering the feature, you stop it
from being abused, but you also prevent the possible good uses of it.

I don't think it's really worth the tradeoff, in Erlang.

> > What is worse to me is the unorthogonality - that I can't say integer(X)
> > or tuple(X) outside of a guard and mean the same thing.
> Ok, I think I agree. If it looks like a function, it should be a function.

(Speaking of conformity, almost every other language I've ever seen uses
">=" for "greater than or equal to".  Not Erlang... :-)

> Please do not fall out of love so fast... and I certainly do not speak for
> the Erlang designers, so maybe overloading is coming soon.

Well, I originally thought about overloading because I thought that
maybe with it, I could use Erlang to solve some problems it wasn't
originally designed for, by having it work on a customized primitive
data type.  But that just isn't the case.

And on general principles, I'm no fan of overloading either, because it
does rely on a lot of far-reaching context.  So I am inclined to agree
with the application of an Oberon-like philosophy to overloading in
Erlang.  Keep it predictable; disallow operator overloading.

Polymorphism (such as it is with this LISP-like type system) is probably
a better idea than overloading for a functional language.  The "=="
operator is a good example of good built-in polymorphism.

My desired language differs from Erlang in several ways.  It's more of a
number-crunching language where cost-consciousness isn't a priority but
clarity is.  What I'm going to do instead of using Erlang (and should
have thought about doing from the start) is to *steal* the best ideas
from Erlang for my own use.  :-)

I'll still write the compiler in Erlang though, and probably have it
compile to Erlang as well.  It's probably a little too much to do with a
parse transformation - and I might want to have destination formats
other than Erlang someday - all the more reason for it to be it's own
language.

_chris

--
"Ten short days ago all I could look forward to was a dead-end job as a
engineer.  Now I have a promising future and make really big Zorkmids."
Chris Pressey, Cat's Eye Technologies, http://www.catseye.mb.ca/
Esoteric Topics Mailing List: http://www.catseye.mb.ca/list.html


Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opinions

Steven H. Rogers
Chris Pressey wrote:
>
> ...
> My desired language differs from Erlang in several ways.  It's more of a
> number-crunching language where cost-consciousness isn't a priority but
> clarity is.  What I'm going to do instead of using Erlang (and should
> have thought about doing from the start) is to *steal* the best ideas
> from Erlang for my own use.  :-)
>
> ,,.

You might want to look at A+ (http://www.aplusdev.org), an APL
derivative that Morgan Stanley Dean Witter released as open source last
month.  It has a functional flavor and is good for number crunching.  It
uses the APL character set which, while concise and elegant, makes
setting up a development environment a bit of a hassle if you're not a
*nix font guru.  In addition to the source, binaries are available for
Irix, Linux, and Solaris.  

Regards,
Steve
--
TANSTAAFL


Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opinions

Thomas Lindgren-2
In reply to this post by David Gould-2

David Gould:
> In the countercase (why is it always C++?), overloading something
> like "+" combined with some overuse of inheritance and a macro or
> two makes it almost impossible to tell what "+" gets resolved to
> without stepping it in a debugger or reading the entire program and
> libraries.

So, what can one say about the Erlang construct "F(X1,X2,X3)"?
A casual reader can not in general see what F is supposed to do.

I think the use of higher-order functions suffers from the same defect
as overloading or objects (esp. with before- and after-methods and
suchlike), namely that it is hard to follow what actually will happen
in the general case. (The benefits may outweigh this disadvantage, but
that's beside the point.)

Well-known idioms (foldl, forall) can be managed, but it's easy to get
lost in a maze of anonymous functions and function-valued parameters.
Conclusion: use carefully.

Apply can occasionally be even worse. I _have_ heard one correspondent
on this list defend the use of sending "some term" across the network,
constructing an atom from it and doing an apply on the result. But not
in public :-)

(The idea of doing apply on dynamically constructed atoms has been
independently rediscovered at least once. In the module
lib/asn1/src/asn1rt.erl in R7B0, we find the following code:

encode(ber,Module,Type,Term) ->
    Call = list_to_atom(lists:concat(['enc_',Type])),
    case catch apply(Module,Call,[Term,[]]) of
       ...
    end;
...

)

                        Thomas
--
Thomas Lindgren thomas+junk
Alteon WebSystems


Reply | Threaded
Open this post in threaded view
|

Various (and almost completely unrelated) questions and opinions

Richard Carlsson-4
In reply to this post by Chris Pressey

On Wed, 21 Feb 2001, Chris Pressey wrote:

> What is worse to me is the unorthogonality - that I can't say
> integer(X) or tuple(X) outside of a guard and mean the same thing.

As of the coming R8 release, all the old guard tests `atom', `float',
etc., will have the better synonyms `is_atom', `is_float', and so on.
These can also be called outside of guards as normal boolean functions
(they are bifs, belonging to module `erlang').

        /Richard


Richard Carlsson (richardc)   (This space intentionally left blank.)
E-mail: Richard.Carlsson WWW: http://www.csd.uu.se/~richardc/