IsValueType template? std.traits.hasAliasing?

Bill Baxter wbaxter at gmail.com
Tue Jan 27 18:18:00 PST 2009


On Wed, Jan 28, 2009 at 11:09 AM, dsimcha <dsimcha at yahoo.com> wrote:
> == Quote from Bill Baxter (wbaxter at gmail.com)'s article
>> Does anyone have a good template for checking if a struct is
>> semantically a pure value type or not?
>> I found "hasAliasing" in D2 which is close, but it seems to report
>> true even for static arrays.
>> struct X { float[3] vals; }
>> pragma(msg, hasAliasing!(X)?"true":"false"); --> true
>> Maybe that's just a bug in hasAliasing?
>> What I want to know is if     X=Y will give me an X that is
>> independent of Y.  I think that is the same question hasAliasing is
>> trying to answer.  If so then it's a bug.
>> --bb
>
> Here's a really ugly, brute force hack that does what you need:
>
> http://dsource.org/projects/dstats/browser/trunk/alloc.d
>
> I actually needed it in dstats to support newVoid(), which is a speed hack to
> allocate arrays w/o initializing the contents, to tell the GC whether to scan for
> pointers.  Actually, on looking at it again, it should probably be changed to make
> function pointers and delegates return false.
>
> Not sure if this is what you were looking for.  By semantically a pure value type,
> do you mean that immutable reference data should or sould not be included?

D1, so it doesn't matter, but if it were D2 that would be ok.
What I want to know is if I do A=B will changes to A possibly affect B or not.

std.traits.hasAliasing seems to do the trick also with the addition of
a small isStaticArray!(T) check.
There's a port of it I did in std2.

Anyway, here it is for the record:

/// Part of IsValueType implementation
private template HasRawPointerImpl(T...)
{
    static if (T.length == 0)
    {
        const result = false;
    }
    else
    {
        static if (is(T[0] U : U*))
            const hasRawAliasing = true;
        else static if (is(T[0] U : U[]))
            const hasRawAliasing = !stdTraits.isStaticArray!(T[0]);
        else
            const hasRawAliasing = false;
        const result = hasRawAliasing || HasRawPointerImpl!(T[1 .. $]).result;
    }
}
/// Part of the IsValueType implementation
private template HasRawAliasing(T...)
{
    const HasRawAliasing
        = HasRawPointerImpl!(stdTraits.RepresentationTypeTuple!(T)).result;
}
/// Part of the IsValueType implementation
private template HasAliasing(T...)
{
    const HasAliasing = HasRawAliasing!(T) || stdTraits.hasObjects!(T);
}
/// The IsValueType template
private template IsValueType(T...)
{
    const IsValueType = !HasAliasing!(T);
}


I suppose technically D will allow you to set the static array .ptr to
point to something else.  But I'm just not going to do that.  :-)

--bb


--bb



More information about the Digitalmars-d mailing list