Jump to page: 1 2
Thread overview
Only const or immutable class thread local variables are allowed
Dec 08, 2013
Ali Çehreli
Dec 08, 2013
qznc
Dec 09, 2013
Ali Çehreli
Dec 10, 2013
Jonathan M Davis
Dec 09, 2013
qznc
Dec 10, 2013
Jonathan M Davis
Dec 10, 2013
Jonathan M Davis
Dec 10, 2013
qznc
Dec 10, 2013
qznc
December 08, 2013
Hello all,

I have a challenge, which is this: I'd like to have a public property which will return a reference to an internally stored class instance.

    ref MyClass myProperty() @property
    {
        ...
    }

However, this runs into a problem: I can't use "static" to internally store a class instance.

I worked out a cheaty way to get around this which goes like this:

    ref MyClass myProperty() @property
    {
        struct MyCheat
        {
            MyClass whatIReallyWant = new MyClass;
        }

        static MyCheat cheat;
        // ... do other stuff ...
        return cheat.whatIReallyWant;
    }

... but I'm wondering if anyone has any alternative suggestions (or warnings or caveats about the cheaty method).

Thanks & best wishes,

    -- Joe
December 08, 2013
On 12/08/2013 10:00 AM, Joseph Rushton Wakeling wrote:

> I have a challenge, which is this: I'd like to have a public property
> which will return a reference to an internally stored class instance.
>
>      ref MyClass myProperty() @property
>      {
>          ...
>      }

First, the usual question: Since class varibles are already references, do you really need to return ref?

In any case, I think class static this is the solution:

class MyClass
{
    static MyClass whatIReallyWant;

    static this()
    {
        whatIReallyWant = new MyClass;
    }

    /* ref */ MyClass myProperty() @property
    {
        return whatIReallyWant;
    }
}

void main()
{
    auto m = new MyClass;
    auto s = m.myProperty;
}

Ali

December 08, 2013
On 08/12/13 21:12, Ali Çehreli wrote:
> In any case, I think class static this is the solution:

I think I may have misled you by talking about properties, because I _don't_ mean a property of a class.  I mean a public standalone function that is marked as a @property, which returns a persistent instance of some class.

The actual motivation is reimplementing std.random.rndGen but with class-based RNGs instead of structs :-)

A consequence of this is that I don't think a static class instance can work, because the returned class has to be non-const -- it's an RNG that will be updated!
December 08, 2013
On Sunday, 8 December 2013 at 21:32:35 UTC, Joseph Rushton Wakeling wrote:
> On 08/12/13 21:12, Ali Çehreli wrote:
>> In any case, I think class static this is the solution:
>
> I think I may have misled you by talking about properties, because I _don't_ mean a property of a class.  I mean a public standalone function that is marked as a @property, which returns a persistent instance of some class.
>
> The actual motivation is reimplementing std.random.rndGen but with class-based RNGs instead of structs :-)
>
> A consequence of this is that I don't think a static class instance can work, because the returned class has to be non-const -- it's an RNG that will be updated!

I understand you are talking about the "Singleton" design pattern.
You might want to look how std.parallelism does it with the default global thread pool.

https://github.com/D-Programming-Language/phobos/blob/master/std/parallelism.d#L3261
December 09, 2013
On 12/08/2013 02:40 PM, qznc wrote:

> I understand you are talking about the "Singleton" design pattern.
> You might want to look how std.parallelism does it with the default
> global thread pool.
>
> https://github.com/D-Programming-Language/phobos/blob/master/std/parallelism.d#L3261

David Simcha presented it as a D-specific pattern and explained how D avoids at least one of the bugs of double-checked locking:


http://www.youtube.com/watch?feature=player_detailpage&v=yMNMV9JlkcQ#t=1676

Ali

December 09, 2013
On Monday, 9 December 2013 at 00:24:44 UTC, Ali Çehreli wrote:
> David Simcha presented it as a D-specific pattern and explained how D avoids at least one of the bugs of double-checked locking:
>
>
> http://www.youtube.com/watch?feature=player_detailpage&v=yMNMV9JlkcQ#t=1676

I will look at this in detail but instinctively based on what I understand a singleton to be for, I'm not sure it's what I want: I'm not looking for something truly global, only thread-global.

Just so you can see, this is what I've got:
https://github.com/WebDrake/std.random2/blob/master/std/random2/generator.d#L18
https://github.com/WebDrake/std.random2/blob/master/std/random2/generator.d#L688

... and this is what it's designed to replace:
https://github.com/D-Programming-Language/phobos/blob/master/std/random.d#L1148
https://github.com/D-Programming-Language/phobos/blob/master/std/random.d#L1104

December 09, 2013
On 09/12/13 01:24, Ali Çehreli wrote:
> On 12/08/2013 02:40 PM, qznc wrote:
>
>> I understand you are talking about the "Singleton" design pattern.
>> You might want to look how std.parallelism does it with the default
>> global thread pool.
>>
>> https://github.com/D-Programming-Language/phobos/blob/master/std/parallelism.d#L3261
>
> David Simcha presented it as a D-specific pattern and explained how D avoids at
> least one of the bugs of double-checked locking:

(i) That's very cool :-D

(ii) I still think it's not what I want.  The "static" class instance doesn't need to be globally global, I want the default thread-local storage as per the existing std.random.rndGen.  Hence the solution I arrived at, but which I'm sure could be improved.
December 09, 2013
On Monday, 9 December 2013 at 06:43:05 UTC, Joseph Rushton Wakeling wrote:
> On 09/12/13 01:24, Ali Çehreli wrote:
>> On 12/08/2013 02:40 PM, qznc wrote:
>>
>>> I understand you are talking about the "Singleton" design pattern.
>>> You might want to look how std.parallelism does it with the default
>>> global thread pool.
>>>
>>> https://github.com/D-Programming-Language/phobos/blob/master/std/parallelism.d#L3261
>
> (ii) I still think it's not what I want.  The "static" class instance doesn't need to be globally global, I want the default thread-local storage as per the existing std.random.rndGen.  Hence the solution I arrived at, but which I'm sure could be improved.

class Foo {
	private static Foo singleton = null;
	@property public static Foo global() {
		if (singleton is null)
			singleton = new Foo();
		return singleton;
	}
}

Running example: http://www.dpaste.dzfl.pl/f65513fa
December 10, 2013
On Monday, December 09, 2013 06:19:19 Joseph Rushton Wakeling wrote:
> On Monday, 9 December 2013 at 00:24:44 UTC, Ali Çehreli wrote:
> > David Simcha presented it as a D-specific pattern and explained how D avoids at least one of the bugs of double-checked locking:
> > 
> > 
> > http://www.youtube.com/watch?feature=player_detailpage&v=yMNMV9JlkcQ#t=167 6
> 
> I will look at this in detail but instinctively based on what I understand a singleton to be for, I'm not sure it's what I want: I'm not looking for something truly global, only thread-global.

It's still essentially a singleton - it's just that it's a single instance per thread in that case instead of per program. And you avoid all of the threading-related initialization issues with singletons if it's thread-local. Just check whether it's null, initialize it if it is (leave it alone if it isn't), and then do whatever you're going to do with it.

- Jonathan M Davis

December 10, 2013
On 10/12/13 06:33, Jonathan M Davis wrote:
> It's still essentially a singleton - it's just that it's a single instance per
> thread in that case instead of per program. And you avoid all of the
> threading-related initialization issues with singletons if it's thread-local.
> Just check whether it's null, initialize it if it is (leave it alone if it
> isn't), and then do whatever you're going to do with it.

So for example the below code as an rndGen where Random is a class, not a struct?

I think I was misled by the "Only const or immutable ..." part of the error message: I'd assumed that any class that actually modified its internal state would be disallowed as a static instance.

///////////////////////////////////////////////////////////////////////////////
ref Random rndGen() @property
{
    static Random result = null;

    if (result is null)
    {
        result = new Random;

        static if (isSeedable!(Random, typeof(repeat(0).map!((a) => unpredictableSeed))))
        {
            result.seed(repeat(0).map!((a) => unpredictableSeed));
        }
        else
        {
            result.seed(unpredictableSeed);
        }
    }

    return result;
}
///////////////////////////////////////////////////////////////////////////////
« First   ‹ Prev
1 2