why cannot assign to function call
Mark Wooding
mdw at distorted.org.uk
Fri Jan 9 21:40:46 EST 2009
Joe Strout <joe at strout.net> wrote:
> No, actually, that was me. rurpy's list was something like C, FORTRAN,
> Perl, and VBA.
My mistake -- I failed to read the quoting properly. Apologies to all.
We still dealt with C.
Fortran (to give it its modern spelling) has a similar data model to C,
but passes arguments by reference, as described in my Epic Argument
Passing Article; I believe that arbitrary expressions may be used as
arguments, though I'm unsure as to the semantics of modifying parameters
bound to the resulting temporary argument locations.
I must confess to being ignorant of VBA. My excuse is that I avoid
Windows systems as much as practical, and VBA doesn't have a significant
uptake on other systems.
Perl has a very strange data model indeed, and it's hard to get a proper
handle on it without getting into implementation details: unlike Python,
Perl is largely defined /by/ its implementation.
Perl has `references', which are proper (scalar) values through which
one may read and modify other values; i.e., they're what I called
`locatives' elsewhere. Perl provides syntactic sugar, through its
`prototypes' which will convert an actual argument which designates
(e.g.) a list or hash into a reference to that list or hash; prototypes
provide other syntactic shortcuts too, though they have no fundamental
semantic effect. In order to add to the confusion, Perl also provides
`typeglobs', which are a reification of toplevel variable bindings.
Perl's argument passing is fundamentally by /reference/. Given the
function
sub swap { ($_[0], $_[1]) = ($_[1], $_[0]) }
after setting $a = 1, $b = 2, and calling swap $a, $b, we find that $a
has the value 2 and $b is 1.
What's going on here is that a `location' in Perl is an explicit SV, AV
or HV object (for `scalar-', `array-' and `hash-value' respectively.
Calling a subroutine involves marking a position on a stack, pushing a
number of SVs, and then executing the subroutine's code, which receives
the items between the stack pointer and mark in the @_ array. In the
case of argument expressions which designate SVs, those SVs are pushed
directly, and are therefore made available via @_. Arguments which are
arrays or hashes are flattened: their components are pushed onto the
stack. (This use of the stack corresponds to what the Perl manual
refers to as `list context'.)
> Not REALbasic. It's a very modern language with semantics pretty much
> identical to Java.
Very well; thanks for the correction. I might have a look at this at
some point.
> > .NET isn't a language at all: rather, it's a virtual machine,
> > runtime system, class library and family of languages each of which
> > may have idiosyncratic semantics.
>
> But they don't, AFAIK -- they all have the same semantics; only the
> surface syntax differs. And those semantics are the same as REALbasic
> and Java.
There's a .NET implementation of C++, which obviously brings all of
C++'s low-level data model (and it's user-definable assignment and
copying). C#'s data model is more complex than Java's because it
provides mutable compound `value types', i.e., types whose immediate
representations consist of the raw contents of the object rather than a
reference. The mutability allows one to distinguish this IR from a
reference IR. C# is additionally complicated by its automatic boxing
and unboxing rules: an object of value type may under some circumstances
be `boxed', appearing as an object of reference type, and obeying the
reference-type semantics.
> Technically true, in that pointers in C require some special syntax, but
> the common idiom is to hide this away by defining a new type:
>
> typedef Foo* FooPtr;
>
> Now, for any code using the "FooPtr" type, the data model is the same
> as Python (or as Java, RB, .NET, etc., again for code that's using
> only reference types).
This is a syntactic transformation rather than a change to the data
model, though.
-- [mdw]
More information about the Python-list
mailing list