Jump to page: 1 2
Thread overview
What's the deal with __buck?
Jan 29, 2009
Bill Baxter
Jan 29, 2009
Bill Baxter
Jan 29, 2009
BCS
Jan 29, 2009
Don
Jan 29, 2009
Bill Baxter
Jan 29, 2009
Don
Jan 29, 2009
Bill Baxter
Jan 30, 2009
Don
January 29, 2009
I stumbled upon a very interesting problem. Consider an infinite range that generates the numbers 1, 2, 3, ...

That range doesn't have a "length" member. However, it is a random access range, which makes things rather interesting. Now consider I want to advance 10 steps in that range. Being an obedient D programmer I'd write:

auto r = iota(1);
// skip 10 steps
r = r[10 .. $];

Now this is very cool. If a range is infinite, I can use the $ symbol in the right position, but nothing else. So I tried to effect that and got the following to compile:

struct DollarType {}
enum DollarType __dollar = DollarType();

struct S
{
    void opSlice(uint, DollarType)
    {
    }
}

void main()
{
    S s;
    s[0 .. $];
}

This is cool because it allows detection of passing $. Now the problem is, I can't seem to get rid of the __dollar definition! Has anyone found a general-enough trick? I'd want a[...$...] to morph the $ into a.length *iff* a defines length, and go with the __dollar otherwise.


Thanks,

Andrei
January 29, 2009
On Thu, Jan 29, 2009 at 1:37 PM, Andrei Alexandrescu <SeeWebsiteForEmail@erdani.org> wrote:
> I stumbled upon a very interesting problem. Consider an infinite range that generates the numbers 1, 2, 3, ...
>
> That range doesn't have a "length" member. However, it is a random access range, which makes things rather interesting. Now consider I want to advance 10 steps in that range. Being an obedient D programmer I'd write:
>
> auto r = iota(1);
> // skip 10 steps
> r = r[10 .. $];
>
> Now this is very cool. If a range is infinite, I can use the $ symbol in the right position, but nothing else. So I tried to effect that and got the following to compile:
>
> struct DollarType {}
> enum DollarType __dollar = DollarType();
>
> struct S
> {
>    void opSlice(uint, DollarType)
>    {
>    }
> }
>
> void main()
> {
>    S s;
>    s[0 .. $];
> }
>
> This is cool because it allows detection of passing $. Now the problem is, I can't seem to get rid of the __dollar definition! Has anyone found a general-enough trick? I'd want a[...$...] to morph the $ into a.length *iff* a defines length, and go with the __dollar otherwise.

You need to give your DollarType an int and some arithmetic operators
and have it represent an /offset/ from the end rather than signifying
the end itself.
Otherwise  a[$-1] can't work.

Once you do that, then you can do things like
struct S
{
   T opSlice(uint a,  DollarType b) {
      return opSlice(a, length+b.offset);
   }
   T opSlice(uint a, uint b) {
           ....
   }
   ...
}

--bb
January 29, 2009
On Thu, Jan 29, 2009 at 1:48 PM, Bill Baxter <wbaxter@gmail.com> wrote:
> On Thu, Jan 29, 2009 at 1:37 PM, Andrei Alexandrescu <SeeWebsiteForEmail@erdani.org> wrote:
>> I stumbled upon a very interesting problem. Consider an infinite range that generates the numbers 1, 2, 3, ...
>>
>> That range doesn't have a "length" member. However, it is a random access range, which makes things rather interesting. Now consider I want to advance 10 steps in that range. Being an obedient D programmer I'd write:
>>
>> auto r = iota(1);
>> // skip 10 steps
>> r = r[10 .. $];
>>
>> Now this is very cool. If a range is infinite, I can use the $ symbol in the right position, but nothing else. So I tried to effect that and got the following to compile:
>>
>> struct DollarType {}
>> enum DollarType __dollar = DollarType();
>>
>> struct S
>> {
>>    void opSlice(uint, DollarType)
>>    {
>>    }
>> }
>>
>> void main()
>> {
>>    S s;
>>    s[0 .. $];
>> }
>>
>> This is cool because it allows detection of passing $. Now the problem is, I can't seem to get rid of the __dollar definition! Has anyone found a general-enough trick? I'd want a[...$...] to morph the $ into a.length *iff* a defines length, and go with the __dollar otherwise.
>
> You need to give your DollarType an int and some arithmetic operators
> and have it represent an /offset/ from the end rather than signifying
> the end itself.
> Otherwise  a[$-1] can't work.
>
> Once you do that, then you can do things like
> struct S
> {
>   T opSlice(uint a,  DollarType b) {
>      return opSlice(a, length+b.offset);
>   }
>   T opSlice(uint a, uint b) {
>           ....
>   }
>   ...
> }

Nevermind, it just sunk in what you meant.
I think it's only a problem when you want to have some things in a
module with special __dollar and some with not?

Or I suppose you're probably trying to make template things which may or may not be infinite?

I guess what's required is the ability to define the __dollar in the scope of a class/struct/template.

--bb
January 29, 2009
Hello Bill,
> 
> I guess what's required is the ability to define the __dollar in the
> scope of a class/struct/template.

I think that is the correct solution.

> 
> --bb
> 


January 29, 2009
BCS wrote:
> Hello Bill,
>>
>> I guess what's required is the ability to define the __dollar in the
>> scope of a class/struct/template.
> 
> I think that is the correct solution.

Ok, thanks to all. So __dollar is looked up at module scope for anything
that's not a built-in array.

I thought some more about it and I think there's no need for __dollar.
It's enough that:

a) In slice expressions and index expressions with one argument, $ expands to value.length, where value is the object being indexed/sliced (if an unnamed temporary, the value is of course only evaluated once)

b) In index expressions with multiple arguments, $ expand to value.length(i), where i is the zero-based argument position.

This is exactly enough what's needed to make it all work. Infinite
ranges may define a symbolic infinite length and overload slicing on it.


Andrei



Andrei
January 29, 2009
On Thu, Jan 29, 2009 at 12:48 PM, Andrei Alexandrescu <SeeWebsiteForEmail@erdani.org> wrote:
> BCS wrote:
>>
>> Hello Bill,
>>>
>>> I guess what's required is the ability to define the __dollar in the scope of a class/struct/template.
>>
>> I think that is the correct solution.
>
> Ok, thanks to all. So __dollar is looked up at module scope for anything that's not a built-in array.
>
> I thought some more about it and I think there's no need for __dollar. It's enough that:
>
> a) In slice expressions and index expressions with one argument, $ expands to value.length, where value is the object being indexed/sliced (if an unnamed temporary, the value is of course only evaluated once)
>
> b) In index expressions with multiple arguments, $ expand to
> value.length(i), where i is the zero-based argument position.
>
> This is exactly enough what's needed to make it all work. Infinite ranges may define a symbolic infinite length and overload slicing on it.

Sounds good.  Question - since length will work for multiple indices, will it ever be possible to have .. multiple slices?

a[x1 .. x2, y1 .. y2] = b;
January 29, 2009
Jarrett Billingsley wrote:
> On Thu, Jan 29, 2009 at 12:48 PM, Andrei Alexandrescu
> <SeeWebsiteForEmail@erdani.org> wrote:
>> BCS wrote:
>>> Hello Bill,
>>>> I guess what's required is the ability to define the __dollar in the
>>>> scope of a class/struct/template.
>>> I think that is the correct solution.
>> Ok, thanks to all. So __dollar is looked up at module scope for anything
>> that's not a built-in array.
>>
>> I thought some more about it and I think there's no need for __dollar.
>> It's enough that:
>>
>> a) In slice expressions and index expressions with one argument, $ expands
>> to value.length, where value is the object being indexed/sliced (if an
>> unnamed temporary, the value is of course only evaluated once)
>>
>> b) In index expressions with multiple arguments, $ expand to
>> value.length(i), where i is the zero-based argument position.
>>
>> This is exactly enough what's needed to make it all work. Infinite
>> ranges may define a symbolic infinite length and overload slicing on it.
> 
> Sounds good.  Question - since length will work for multiple indices,
> will it ever be possible to have .. multiple slices?
> 
> a[x1 .. x2, y1 .. y2] = b;

You can do that with opIndex already.
January 29, 2009
On Fri, Jan 30, 2009 at 5:58 AM, Don <nospam@nospam.com> wrote:
> Jarrett Billingsley wrote:
>>
>> On Thu, Jan 29, 2009 at 12:48 PM, Andrei Alexandrescu <SeeWebsiteForEmail@erdani.org> wrote:
>>>
>>> BCS wrote:
>>>>
>>>> Hello Bill,
>>>>>
>>>>> I guess what's required is the ability to define the __dollar in the scope of a class/struct/template.
>>>>
>>>> I think that is the correct solution.
>>>
>>> Ok, thanks to all. So __dollar is looked up at module scope for anything that's not a built-in array.
>>>
>>> I thought some more about it and I think there's no need for __dollar. It's enough that:
>>>
>>> a) In slice expressions and index expressions with one argument, $
>>> expands
>>> to value.length, where value is the object being indexed/sliced (if an
>>> unnamed temporary, the value is of course only evaluated once)
>>>
>>> b) In index expressions with multiple arguments, $ expand to
>>> value.length(i), where i is the zero-based argument position.
>>>
>>> This is exactly enough what's needed to make it all work. Infinite ranges may define a symbolic infinite length and overload slicing on it.
>>
>> Sounds good.  Question - since length will work for multiple indices, will it ever be possible to have .. multiple slices?
>>
>> a[x1 .. x2, y1 .. y2] = b;
>
> You can do that with opIndex already.

Can you?  How?  As far as I know any index expression with more than one  ..  in it automatically generates a compiler error.

--bb
January 29, 2009
Bill Baxter wrote:
> On Fri, Jan 30, 2009 at 5:58 AM, Don <nospam@nospam.com> wrote:
>> Jarrett Billingsley wrote:
>>> On Thu, Jan 29, 2009 at 12:48 PM, Andrei Alexandrescu
>>> <SeeWebsiteForEmail@erdani.org> wrote:
>>>> BCS wrote:
>>>>> Hello Bill,
>>>>>> I guess what's required is the ability to define the __dollar in the
>>>>>> scope of a class/struct/template.
>>>>> I think that is the correct solution.
>>>> Ok, thanks to all. So __dollar is looked up at module scope for anything
>>>> that's not a built-in array.
>>>>
>>>> I thought some more about it and I think there's no need for __dollar.
>>>> It's enough that:
>>>>
>>>> a) In slice expressions and index expressions with one argument, $
>>>> expands
>>>> to value.length, where value is the object being indexed/sliced (if an
>>>> unnamed temporary, the value is of course only evaluated once)
>>>>
>>>> b) In index expressions with multiple arguments, $ expand to
>>>> value.length(i), where i is the zero-based argument position.
>>>>
>>>> This is exactly enough what's needed to make it all work. Infinite
>>>> ranges may define a symbolic infinite length and overload slicing on it.
>>> Sounds good.  Question - since length will work for multiple indices,
>>> will it ever be possible to have .. multiple slices?
>>>
>>> a[x1 .. x2, y1 .. y2] = b;
>> You can do that with opIndex already.
> 
> Can you?  How?  As far as I know any index expression with more than
> one  ..  in it automatically generates a compiler error.

Aargh, you're right. I remembered that I'd got it to generate an AST for me, but I forgot that I had put in a hack for ..
January 29, 2009
Jarrett Billingsley wrote:
> On Thu, Jan 29, 2009 at 12:48 PM, Andrei Alexandrescu
> <SeeWebsiteForEmail@erdani.org> wrote:
>> BCS wrote:
>>> Hello Bill,
>>>> I guess what's required is the ability to define the __dollar in the
>>>> scope of a class/struct/template.
>>> I think that is the correct solution.
>> Ok, thanks to all. So __dollar is looked up at module scope for anything
>> that's not a built-in array.
>>
>> I thought some more about it and I think there's no need for __dollar.
>> It's enough that:
>>
>> a) In slice expressions and index expressions with one argument, $ expands
>> to value.length, where value is the object being indexed/sliced (if an
>> unnamed temporary, the value is of course only evaluated once)
>>
>> b) In index expressions with multiple arguments, $ expand to
>> value.length(i), where i is the zero-based argument position.
>>
>> This is exactly enough what's needed to make it all work. Infinite
>> ranges may define a symbolic infinite length and overload slicing on it.
> 
> Sounds good.  Question - since length will work for multiple indices,
> will it ever be possible to have .. multiple slices?
> 
> a[x1 .. x2, y1 .. y2] = b;

That's rather exotic. After that the road is opened for free-form combinations of a .. b and a. But I can definitely see some good uses for it.

Andrei
« First   ‹ Prev
1 2