[BTW: Google groups is going away ..]

On 02/03/2012, at 11:56 AM, GitHub wrote:
> 
>  Log Message:
>  -----------
>  Fixed assignment warnings


I actually need to write up some of the important concepts somewhere.
There are some separate "web/docs/*f.doc" files with such stuff.
However the basic website is pretty lame in terms of "appeal" and
navigation etc.

The concept here is basically:

Felix has values and objects. Values are immutable
and movable. Immutability supports functional programming in traditional style.
Mobility is essential for optimisation (copy by value).

Objects are typically mutable and immobile. Objects are interfaced to values
via the concept of a "pointer": pointers are values which can be used to access
objects.

There are three way to get an object: 

1. Through a factory function written in C/C++, typically abstract

2. By copying a value onto the heap using "new", returning a pointer.

3. By storing the value in a variable (var thing) and taking
the address of the variable.

Assignment is used to store a value in a variable. But it is a derived
concept implemented by:

        var = val    ==>  &var <- val

where the fundamental operation is storing a value at a pointer.

Some hackery (sugar) is used to support common operations.
For example

        var x = 1,2;
        x.1 = 42; // assign 42 to second component of x

is actually defined by

        &(x.1) <- 42;

and now &(x.1) is defined as (&x).1. This is necessary since & operator
may only be applied to variables (or dereferenced pointers).

We also allow

        &(f x) = 1;

where f x is the application of a *C binding* f which is marked as an lvalue.
Felix functions (defined in Felix) cannot be marked lvalues.

The lvalue annotation is only there because Felix cannot see into
abstract (C) expressions and so loses the ability to optimise
things.

The current compiler does not support array component assignment:

        s.[i] = 1;

does not work. The reason is that whilst operator dot (.) component
access is done directly by the compiler, array access is implemented
in user space at present, using the subscript operator.

It is quite possible to make subscript an lvalue function, but it doesn't
help because the array access technology has been abstracted and
modelled by a type class.

Ordinary Felix arrays are the same as (properly length managed) C arrays
so a subscript is a reference, and can therefore act as both a value and
an lvalue.

However the abstracted type-class based array concept does NOT support
this view. Instead we consider an array something which supports
indexed get and set methods.

In general, an array simply will NOT support reference semantics:
it's perfectly permissible for the array type to fail to expose the storage
location of a value.

In particular, if you consider bsarray, the bound sparse array,
the "get" of a particular value may simply be returning a 
copy of the default value. You have to call "set" method to store
a non-default value: the storage location may not exist until you do.

Therefore, bsarray cannot support reference semantics for components.
You cannot return a pointer to an arbitrary index's component.

If we requires arrays to do that, bsarray wouldn't classify as an array anymore.

Of course, Felix can distinguish an abstact array (a complex data structure
like dsarray) from a simple Felix array type like char^100. At the moment,
however

        x.[i]

is not a Felix type system primitive operation: the parser maps it to a
call to the function "subscript". Component access like

        x.2

however maps to 


        EXPR_dot (x, literal ("2", integer))


It is not clear what to do :)

For the moment the easy workaround is:

        set(&x, i, v);

which uses the typeclass to map the set call onto the underlying
array, for Felix Farray::array this is the function

        proc unsafe_set[T,N]: array[T,N] * !ints * T  = "$1[$2]=$3;";

For Farray::array the get function really is an lvalue:

        fun unsafe_get[T,N]: array[T,N] * !ints -> T = "$1[$2]";

but it is called indirectly through the typeclass get function
which cannot be. In particular not that the actual typeclass get method
does a bounds check: it's a (non-virtual) Felix function which then
calls the unsafe_set method.

Again: it IS possible for the compiler to do the right thing here:
it CAN tell what an array is.

It's also the case that both varray and darray provide contiguous
internal buffers for the arrays, in fact you can access them with
stl_begin and stl_end. The significance is, of course, that
subscripting is again conceptually an lvalue and the result
of a subscript operation could be addressable.


--
john skaller
skal...@users.sourceforge.net
http://felix-lang.org




------------------------------------------------------------------------------
Virtualization & Cloud Management Using Capacity Planning
Cloud computing makes use of virtualization - but cloud computing 
also focuses on allowing computing to be delivered as a service.
http://www.accelacomm.com/jaw/sfnl/114/51521223/
_______________________________________________
Felix-language mailing list
Felix-language@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/felix-language

Reply via email to