Thread overview |
---|
May 01, 2015 Factory pattern in D | ||||
---|---|---|---|---|
| ||||
What would be the D equivalent of the factory pattern? This obviously doesn't work: struct A { int x = 42; } struct B { int x = 7; } auto factory(string type) { if (type == "A") return A(); else if (type == "B") return B(); else return A(); // default } void main() { auto a = factory("A"); } Error: mismatched function return type inference of B and A (dmd 2.067.1) |
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Chris | How about this: ---- struct A { int x = 42; } struct B { int x = 7; } T factory(T)() { return T(); } void main() { auto a = factory!(A); } ---- |
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Chris | On 1/05/2015 10:01 p.m., Chris wrote:
> What would be the D equivalent of the factory pattern? This obviously
> doesn't work:
>
> struct A {
> int x = 42;
> }
>
> struct B {
> int x = 7;
> }
>
> auto factory(string type) {
> if (type == "A")
> return A();
> else if (type == "B")
> return B();
> else
> return A(); // default
> }
>
> void main()
> {
> auto a = factory("A");
> }
>
> Error: mismatched function return type inference of B and A
>
> (dmd 2.067.1)
Interfaces/classes not structs.
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Namespace | On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote:
> How about this:
>
> ----
> struct A {
> int x = 42;
> }
>
> struct B {
> int x = 7;
> }
>
> T factory(T)() {
> return T();
> }
>
> void main()
> {
> auto a = factory!(A);
> }
> ----
Of course, you can restrict the type to A or B, or both:
----
T factory(T)() if (is(T == A) || is(T == B)) {
return T();
}
----
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Namespace | On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote:
> How about this:
>
> ----
> struct A {
> int x = 42;
> }
>
> struct B {
> int x = 7;
> }
>
> T factory(T)() {
> return T();
> }
>
> void main()
> {
> auto a = factory!(A);
> }
> ----
That's what I was looking for, I just couldn't get it right. Thanks.
Rikki:
I wanted to avoid classes and interfaces.
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Chris | On Friday, 1 May 2015 at 10:12:36 UTC, Chris wrote:
> On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote:
>> How about this:
>>
>> ----
>> struct A {
>> int x = 42;
>> }
>>
>> struct B {
>> int x = 7;
>> }
>>
>> T factory(T)() {
>> return T();
>> }
>>
>> void main()
>> {
>> auto a = factory!(A);
>> }
>> ----
>
> That's what I was looking for, I just couldn't get it right. Thanks.
>
> Rikki:
>
> I wanted to avoid classes and interfaces.
This might be a bit more useful:
---
struct A {
int x = 42;
}
struct B {
int x = 7;
}
auto factory(string type = "")() {
static if (type == "A")
return A();
else static if (type == "B")
return B();
else
return A(); // default
}
void main()
{
auto a = factory!"A";
auto b = factory!"B";
auto x = factory;
}
---
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to biozic | On Friday, 1 May 2015 at 10:27:16 UTC, biozic wrote:
> On Friday, 1 May 2015 at 10:12:36 UTC, Chris wrote:
>> On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote:
>>> How about this:
>>>
>>> ----
>>> struct A {
>>> int x = 42;
>>> }
>>>
>>> struct B {
>>> int x = 7;
>>> }
>>>
>>> T factory(T)() {
>>> return T();
>>> }
>>>
>>> void main()
>>> {
>>> auto a = factory!(A);
>>> }
>>> ----
>>
>> That's what I was looking for, I just couldn't get it right. Thanks.
>>
>> Rikki:
>>
>> I wanted to avoid classes and interfaces.
>
> This might be a bit more useful:
> ---
> struct A {
> int x = 42;
> }
>
> struct B {
> int x = 7;
> }
>
> auto factory(string type = "")() {
> static if (type == "A")
> return A();
> else static if (type == "B")
> return B();
> else
> return A(); // default
> }
>
> void main()
> {
> auto a = factory!"A";
> auto b = factory!"B";
> auto x = factory;
> }
> ---
Duh, I tried `static if` yesterday and I still got "Error: mismatched function return type inference of B and A". Now it works! Sure, I must have overlooked something. Sometimes it's better to go home and call it a day than to try to get something to work.
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Chris | On Friday, 1 May 2015 at 10:46:20 UTC, Chris wrote:
> On Friday, 1 May 2015 at 10:27:16 UTC, biozic wrote:
>> On Friday, 1 May 2015 at 10:12:36 UTC, Chris wrote:
>>> On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote:
>>>> How about this:
>>>>
>>>> ----
>>>> struct A {
>>>> int x = 42;
>>>> }
>>>>
>>>> struct B {
>>>> int x = 7;
>>>> }
>>>>
>>>> T factory(T)() {
>>>> return T();
>>>> }
>>>>
>>>> void main()
>>>> {
>>>> auto a = factory!(A);
>>>> }
>>>> ----
>>>
>>> That's what I was looking for, I just couldn't get it right. Thanks.
>>>
>>> Rikki:
>>>
>>> I wanted to avoid classes and interfaces.
>>
>> This might be a bit more useful:
>> ---
>> struct A {
>> int x = 42;
>> }
>>
>> struct B {
>> int x = 7;
>> }
>>
>> auto factory(string type = "")() {
>> static if (type == "A")
>> return A();
>> else static if (type == "B")
>> return B();
>> else
>> return A(); // default
>> }
>>
>> void main()
>> {
>> auto a = factory!"A";
>> auto b = factory!"B";
>> auto x = factory;
>> }
>> ---
>
> Duh, I tried `static if` yesterday and I still got "Error: mismatched function return type inference of B and A". Now it works! Sure, I must have overlooked something. Sometimes it's better to go home and call it a day than to try to get something to work.
And thanks, by the way!
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Chris | On Friday, 1 May 2015 at 10:47:22 UTC, Chris wrote:
> On Friday, 1 May 2015 at 10:46:20 UTC, Chris wrote:
>> On Friday, 1 May 2015 at 10:27:16 UTC, biozic wrote:
>>> On Friday, 1 May 2015 at 10:12:36 UTC, Chris wrote:
>>>> On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote:
>>>>> How about this:
>>>>>
>>>>> ----
>>>>> struct A {
>>>>> int x = 42;
>>>>> }
>>>>>
>>>>> struct B {
>>>>> int x = 7;
>>>>> }
>>>>>
>>>>> T factory(T)() {
>>>>> return T();
>>>>> }
>>>>>
>>>>> void main()
>>>>> {
>>>>> auto a = factory!(A);
>>>>> }
>>>>> ----
>>>>
>>>> That's what I was looking for, I just couldn't get it right. Thanks.
>>>>
>>>> Rikki:
>>>>
>>>> I wanted to avoid classes and interfaces.
>>>
>>> This might be a bit more useful:
>>> ---
>>> struct A {
>>> int x = 42;
>>> }
>>>
>>> struct B {
>>> int x = 7;
>>> }
>>>
>>> auto factory(string type = "")() {
>>> static if (type == "A")
>>> return A();
>>> else static if (type == "B")
>>> return B();
>>> else
>>> return A(); // default
>>> }
>>>
>>> void main()
>>> {
>>> auto a = factory!"A";
>>> auto b = factory!"B";
>>> auto x = factory;
>>> }
>>> ---
>>
>> Duh, I tried `static if` yesterday and I still got "Error: mismatched function return type inference of B and A". Now it works! Sure, I must have overlooked something. Sometimes it's better to go home and call it a day than to try to get something to work.
>
> And thanks, by the way!
Thinking about it,
T factory(T)() {
return T();
}
is better suited for a factory (with static type checks).
This aside, how would I get something to load dynamically? It's either "mismatched function return type" or (with type check) "variable X cannot be read at compile time":
void main(string[] args) {
auto type = args[1];
auto myType = factory!type();
}
So it's back to classes/interfaces again? Hmmmm.
|
May 01, 2015 Re: Factory pattern in D | ||||
---|---|---|---|---|
| ||||
Posted in reply to Chris | On Friday, 1 May 2015 at 11:01:29 UTC, Chris wrote: > On Friday, 1 May 2015 at 10:47:22 UTC, Chris wrote: >> On Friday, 1 May 2015 at 10:46:20 UTC, Chris wrote: >>> On Friday, 1 May 2015 at 10:27:16 UTC, biozic wrote: >>>> On Friday, 1 May 2015 at 10:12:36 UTC, Chris wrote: >>>>> On Friday, 1 May 2015 at 10:04:46 UTC, Namespace wrote: >>>>>> How about this: >>>>>> >>>>>> ---- >>>>>> struct A { >>>>>> int x = 42; >>>>>> } >>>>>> >>>>>> struct B { >>>>>> int x = 7; >>>>>> } >>>>>> >>>>>> T factory(T)() { >>>>>> return T(); >>>>>> } >>>>>> >>>>>> void main() >>>>>> { >>>>>> auto a = factory!(A); >>>>>> } >>>>>> ---- >>>>> >>>>> That's what I was looking for, I just couldn't get it right. Thanks. >>>>> >>>>> Rikki: >>>>> >>>>> I wanted to avoid classes and interfaces. >>>> >>>> This might be a bit more useful: >>>> --- >>>> struct A { >>>> int x = 42; >>>> } >>>> >>>> struct B { >>>> int x = 7; >>>> } >>>> >>>> auto factory(string type = "")() { >>>> static if (type == "A") >>>> return A(); >>>> else static if (type == "B") >>>> return B(); >>>> else >>>> return A(); // default >>>> } >>>> >>>> void main() >>>> { >>>> auto a = factory!"A"; >>>> auto b = factory!"B"; >>>> auto x = factory; >>>> } >>>> --- >>> >>> Duh, I tried `static if` yesterday and I still got "Error: mismatched function return type inference of B and A". Now it works! Sure, I must have overlooked something. Sometimes it's better to go home and call it a day than to try to get something to work. >> >> And thanks, by the way! > > Thinking about it, > > T factory(T)() { > return T(); > } > > is better suited for a factory (with static type checks). But then I don't know what factory!X() provides that X() alone doesn't. > This aside, how would I get something to load dynamically? It's either "mismatched function return type" or (with type check) "variable X cannot be read at compile time": > > void main(string[] args) { > auto type = args[1]; > auto myType = factory!type(); > } > > So it's back to classes/interfaces again? Hmmmm. Indeed. Runtime polymorphism is based on classes and interfaces. The struct and template solutions can only make "compile-time factories". |
Copyright © 1999-2021 by the D Language Foundation