Jump to page: 1 2 3
Thread overview
Understanding isInfinite(Range)
Sep 03, 2010
Andrej Mitrovic
Sep 03, 2010
Andrej Mitrovic
Sep 04, 2010
Peter Alexander
Sep 04, 2010
Simen kjaeraas
Sep 06, 2010
Pelle
Sep 06, 2010
Philippe Sigaud
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
Stanislav Blinov
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
Stanislav Blinov
Sep 06, 2010
Stanislav Blinov
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
Stanislav Blinov
Sep 06, 2010
Philippe Sigaud
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
bearophile
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
Andrej Mitrovic
Sep 07, 2010
Pelle
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
Stanislav Blinov
Sep 06, 2010
Mafi
Sep 06, 2010
Pelle
Sep 06, 2010
Andrej Mitrovic
Sep 06, 2010
bearophile
September 03, 2010
I was reading about the various range templates in std.range and I found this:

http://www.digitalmars.com/d/2.0/phobos/std_range.html#isInfinite

Seems simple enough. But I dont understand it's implementation, this from range.d:

template isInfinite(Range)
{
    static if (isInputRange!Range && is(char[1 + Range.empty]))
        enum bool isInfinite = !Range.empty;
    else
        enum bool isInfinite = false;
}

What does char[1 + Range.empty] do? It looks rather cryptic..
September 03, 2010
On Fri, 03 Sep 2010 11:12:29 -0400, Andrej Mitrovic <andrej.mitrovich@test.com> wrote:

> I was reading about the various range templates in std.range and I found this:
>
> http://www.digitalmars.com/d/2.0/phobos/std_range.html#isInfinite
>
> Seems simple enough. But I dont understand it's implementation, this from range.d:
>
> template isInfinite(Range)
> {
>     static if (isInputRange!Range && is(char[1 + Range.empty]))
>         enum bool isInfinite = !Range.empty;
>     else
>         enum bool isInfinite = false;
> }
>
> What does char[1 + Range.empty] do? It looks rather cryptic..

char[1+Range.empty] is a type.  If Range.empty is a compile-time constant, then this type is valid, otherwise it's not valid (the is expression results to true if the argument is a valid type).

If it's valid, then Range.empty never changes.  If it never changes and it's always false, then it's infinite.

-Steve
September 03, 2010
Ah, you're right. Whenever I see the square brackets my brain automatically things "we're indexing something". I'll blame that on C. :p

Thanks.

Steven Schveighoffer Wrote:

> On Fri, 03 Sep 2010 11:12:29 -0400, Andrej Mitrovic <andrej.mitrovich@test.com> wrote:
> 
> > I was reading about the various range templates in std.range and I found this:
> >
> > http://www.digitalmars.com/d/2.0/phobos/std_range.html#isInfinite
> >
> > Seems simple enough. But I dont understand it's implementation, this from range.d:
> >
> > template isInfinite(Range)
> > {
> >     static if (isInputRange!Range && is(char[1 + Range.empty]))
> >         enum bool isInfinite = !Range.empty;
> >     else
> >         enum bool isInfinite = false;
> > }
> >
> > What does char[1 + Range.empty] do? It looks rather cryptic..
> 
> char[1+Range.empty] is a type.  If Range.empty is a compile-time constant, then this type is valid, otherwise it's not valid (the is expression results to true if the argument is a valid type).
> 
> If it's valid, then Range.empty never changes.  If it never changes and it's always false, then it's infinite.
> 
> -Steve

September 04, 2010
== Quote from Steven Schveighoffer (schveiguy@yahoo.com)'s article
> On Fri, 03 Sep 2010 11:12:29 -0400, Andrej Mitrovic <andrej.mitrovich@test.com> wrote:
> > What does char[1 + Range.empty] do? It looks rather cryptic..
> char[1+Range.empty] is a type.  If Range.empty is a compile-time constant,
> then this type is valid, otherwise it's not valid (the is expression
> results to true if the argument is a valid type).
> If it's valid, then Range.empty never changes.  If it never changes and
> it's always false, then it's infinite.
> -Steve

That's really ugly code :-(

Is there a way you could write an isStatic(expr) template? Using something like that would make the code a hell of a lot more readable. At the moment, the code itself does a very poor job of conveying what it's trying to accomplish.

These SFINAE-like tricks should be black-boxed as much as possible, or (at the very least) commented so that people know what's going on.
September 04, 2010
Peter Alexander <peter.alexander.au@gmail.com> wrote:

> == Quote from Steven Schveighoffer (schveiguy@yahoo.com)'s article
>> On Fri, 03 Sep 2010 11:12:29 -0400, Andrej Mitrovic
>> <andrej.mitrovich@test.com> wrote:
>> > What does char[1 + Range.empty] do? It looks rather cryptic..
>> char[1+Range.empty] is a type.  If Range.empty is a compile-time constant,
>> then this type is valid, otherwise it's not valid (the is expression
>> results to true if the argument is a valid type).
>> If it's valid, then Range.empty never changes.  If it never changes and
>> it's always false, then it's infinite.
>> -Steve
>
> That's really ugly code :-(
>
> Is there a way you could write an isStatic(expr) template? Using something like that would make the
> code a hell of a lot more readable. At the moment, the code itself does a very poor job of conveying
> what it's trying to accomplish.
>
> These SFINAE-like tricks should be black-boxed as much as possible, or (at the very least)
> commented so that people know what's going on.

template isStatic( alias T ) {
    enum isStatic = is( char[1+T] );
}

unittest {
    int n = 3;
    assert( !isStatic!n );
    assert( isStatic!1 );
    enum r = 5;
    assert( isStatic!r );
}
-- 
Simen
September 06, 2010
On 09/04/2010 02:11 PM, Simen kjaeraas wrote:
> Peter Alexander <peter.alexander.au@gmail.com> wrote:
>
>> == Quote from Steven Schveighoffer (schveiguy@yahoo.com)'s article
>>> On Fri, 03 Sep 2010 11:12:29 -0400, Andrej Mitrovic
>>> <andrej.mitrovich@test.com> wrote:
>>> > What does char[1 + Range.empty] do? It looks rather cryptic..
>>> char[1+Range.empty] is a type. If Range.empty is a compile-time
>>> constant,
>>> then this type is valid, otherwise it's not valid (the is expression
>>> results to true if the argument is a valid type).
>>> If it's valid, then Range.empty never changes. If it never changes and
>>> it's always false, then it's infinite.
>>> -Steve
>>
>> That's really ugly code :-(
>>
>> Is there a way you could write an isStatic(expr) template? Using
>> something like that would make the
>> code a hell of a lot more readable. At the moment, the code itself
>> does a very poor job of conveying
>> what it's trying to accomplish.
>>
>> These SFINAE-like tricks should be black-boxed as much as possible, or
>> (at the very least)
>> commented so that people know what's going on.
>
> template isStatic( alias T ) {
> enum isStatic = is( char[1+T] );
> }
>
> unittest {
> int n = 3;
> assert( !isStatic!n );
> assert( isStatic!1 );
> enum r = 5;
> assert( isStatic!r );
> }

enum s = "Hello";

assert (isStatic!s);

Gonna need more work than that.
September 06, 2010
On Mon, Sep 6, 2010 at 18:47, Pelle <pelle.mansson@gmail.com> wrote:

> On 09/04/2010 02:11 PM, Simen kjaeraas wrote:
>
>> Is there a way you could write an isStatic(expr) template? Using
>>>
>>
>> template isStatic( alias T ) {
>> enum isStatic = is( char[1+T] );
>> }
>>
>> unittest {
>> int n = 3;
>> assert( !isStatic!n );
>> assert( isStatic!1 );
>> enum r = 5;
>> assert( isStatic!r );
>> }
>>
>
> enum s = "Hello";
>
> assert (isStatic!s);
>
> Gonna need more work than that.
>

Why? That's exactly the behavior we want, or so it seems to me.


September 06, 2010
Apparently I can't post to D.learn from gmail without waiting for a review? What the..?

Anyway, I've posted this:

On a related note, I always wanted to make a template to replace the
dreaded is(typeof('delegate literal'())); calls.

For example, instead of this:

enum bool isInputRange = is(typeof(
{
   R r;             // can define a range object
   if (r.empty) {}  // can test for empty
   r.popFront;          // can invoke next
   auto h = r.front; // can get the front of the range
}()));

We'd have a much cleaner call like so:

enum bool isInputRange = validate!(
{
   R r;             // can define a range object
   if (r.empty) {}  // can test for empty
   r.popFront;          // can invoke next
   auto h = r.front; // can get the front of the range
});

But I haven't found a way to do it properly. If I call validate on a type R range which doesn't feature the empty() method, then no matter what the definition of validate is the compiler will error out because it sees the call to r.empty() in the function literal, and 'r' doesn't have an empty method.

Philippe Sigaud Wrote:

> On Mon, Sep 6, 2010 at 18:47, Pelle <pelle.mansson@gmail.com> wrote:
> 
> > On 09/04/2010 02:11 PM, Simen kjaeraas wrote:
> >
> >> Is there a way you could write an isStatic(expr) template? Using
> >>>
> >>
> >> template isStatic( alias T ) {
> >> enum isStatic = is( char[1+T] );
> >> }
> >>
> >> unittest {
> >> int n = 3;
> >> assert( !isStatic!n );
> >> assert( isStatic!1 );
> >> enum r = 5;
> >> assert( isStatic!r );
> >> }
> >>
> >
> > enum s = "Hello";
> >
> > assert (isStatic!s);
> >
> > Gonna need more work than that.
> >
> 
> Why? That's exactly the behavior we want, or so it seems to me.
> 
> <div class="gmail_quote">On Mon, Sep 6, 2010 at 18:47, Pelle <span dir="ltr">&lt;<a href="mailto:pelle.mansson@gmail.com">pelle.mansson@gmail.com</a>&gt;</span> wrote:<br><blockquote class="gmail_quote" style="margin: 0pt 0pt 0pt 0.8ex; border-left: 1px solid rgb(204, 204, 204); padding-left: 1ex;">
> <div><div></div><div class="h5">On 09/04/2010 02:11 PM, Simen kjaeraas wrote:<br>
> <blockquote class="gmail_quote" style="margin: 0pt 0pt 0pt 0.8ex; border-left: 1px solid rgb(204, 204, 204); padding-left: 1ex;"><blockquote class="gmail_quote" style="margin: 0pt 0pt 0pt 0.8ex; border-left: 1px solid rgb(204, 204, 204); padding-left: 1ex;">
> 
> Is there a way you could write an isStatic(expr) template? Using<br></blockquote>
> <br>
> template isStatic( alias T ) {<br>
> enum isStatic = is( char[1+T] );<br>
> }<br>
> <br>
> unittest {<br>
> int n = 3;<br>
> assert( !isStatic!n );<br>
> assert( isStatic!1 );<br>
> enum r = 5;<br>
> assert( isStatic!r );<br>
> }<br>
> </blockquote>
> <br></div></div>
> enum s = &quot;Hello&quot;;<br>
> <br>
> assert (isStatic!s);<br>
> <br>
> Gonna need more work than that.<br>
> </blockquote></div><br>Why? That's exactly the behavior we want, or so it seems to me.<br><br><br>
> 

September 06, 2010
Andrej Mitrovic wrote:
> Apparently I can't post to D.learn from gmail without waiting for a review? What the..?
> 
> Anyway, I've posted this:
> 
> On a related note, I always wanted to make a template to replace the
> dreaded is(typeof('delegate literal'())); calls.
> 
> For example, instead of this:
> 
> enum bool isInputRange = is(typeof(
> {
>    R r;             // can define a range object
>    if (r.empty) {}  // can test for empty
>    r.popFront;          // can invoke next
>    auto h = r.front; // can get the front of the range
> }()));
> 
> We'd have a much cleaner call like so:
> 
> enum bool isInputRange = validate!(
> {
>    R r;             // can define a range object
>    if (r.empty) {}  // can test for empty
>    r.popFront;          // can invoke next
>    auto h = r.front; // can get the front of the range
> });
> 
> But I haven't found a way to do it properly. If I call validate on a
> type R range which doesn't feature the empty() method, then no matter
> what the definition of validate is the compiler will error out because
> it sees the call to r.empty() in the function literal, and 'r' doesn't
> have an empty method.
> 

What about __traits(compiles) ?
September 06, 2010
Am 06.09.2010 21:24, schrieb Andrej Mitrovic:
> Apparently I can't post to D.learn from gmail without waiting for a review? What the..?
>
> Anyway, I've posted this:
>
> On a related note, I always wanted to make a template to replace the
> dreaded is(typeof('delegate literal'())); calls.
>
> For example, instead of this:
>
> enum bool isInputRange = is(typeof(
> {
>     R r;             // can define a range object
>     if (r.empty) {}  // can test for empty
>     r.popFront;          // can invoke next
>     auto h = r.front; // can get the front of the range
> }()));
>
> We'd have a much cleaner call like so:
>
> enum bool isInputRange = validate!(
> {
>     R r;             // can define a range object
>     if (r.empty) {}  // can test for empty
>     r.popFront;          // can invoke next
>     auto h = r.front; // can get the front of the range
> });
>
> But I haven't found a way to do it properly. If I call validate on a
> type R range which doesn't feature the empty() method, then no matter
> what the definition of validate is the compiler will error out because
> it sees the call to r.empty() in the function literal, and 'r' doesn't
> have an empty method.
>

You could just let your template get a string. Then
validate!q{....}
should work. It looks almost exactly the same but has a 'q'.

Maybe you could even create an template overload which gets delegate which has always failing static assert with message "you forget the 'q'" but I don't know if template initialization comes before semantic analisys so I'm not sure this will work.

Mafi


« First   ‹ Prev
1 2 3