On 8/3/17 4:30 AM, Olivier FAURE wrote:

I understand the general concept you're describing, but what exactly are tail modifiers? It's the first time I see this name, and my google-fu gives me nothing.

tail modifiers are modifiers that only apply to the "tail" of the type.

For example const(int)* is applying const to the "tail" of the int pointer, that is, the int that it points at. It's not applying to the actual pointer itself (we call that the "head").

Another way to look at it is that when you copy a variable you always make a copy of the head, and you don't make a copy of the tail. For this reason, the fully-modified and tail-modified types are implicitly castable, and this is the important property we need to duplicate.

A tail-modified struct would be something like this:

struct S
{
   int * x;
}

const(S) s;

This looks like this:

struct ConstS
{
   const(int *) x;
}

A tail-const S would look like this:

struct TailConstS
{
   const(int)* x;
}

That is, everything the struct points at remains const, but the actual data of the struct is now mutable.

Note that TailConstS and ConstS can implicitly convert.

This is how arrays work. An array T[] is really:

struct Array
{
   size_t length;
   T* ptr;
}

A tail-const array const(T)[] is really:

struct TailConstArray
{
   size_t length; // mutable
   const(T)* ptr; // mutable, but points at const data
}

This property of implicit casting is what's needed to fully realize custom ranges and const together. The way to get it is to define tail-modifier syntax for all types, not just arrays and pointers.

-Steve

Reply via email to