D issues are now tracked on GitHub. This Bugzilla instance remains as a read-only archive.
Issue 3557 - Struct constructors cannot be declared as pure
Summary: Struct constructors cannot be declared as pure
Status: RESOLVED FIXED
Alias: None
Product: D
Classification: Unclassified
Component: dmd (show other issues)
Version: D2
Hardware: x86 Windows
: P2 normal
Assignee: No Owner
URL:
Keywords: rejects-valid
Depends on:
Blocks:
 
Reported: 2009-11-29 03:19 UTC by Tomasz Sowiński
Modified: 2015-06-09 01:27 UTC (History)
2 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this issue.
Description Tomasz Sowiński 2009-11-29 03:19:44 UTC
struct A {
    float f;
    this (float f) {
        this.f = f;
    }
    static pure A stworz(float f) {
        return A(f);
    }
}

The above doesn't compile:
Error: pure function 'stworz' cannot call impure function 'this'

What's interesting, if stworz signature is one of the below:

static pure stworz(float f);
static pure auto stworz(float f);

then it merrily compiles. So it's sth about the explicit return type.

If I remove the constructor, it also compiles.
If A is a class, it also compiles.
Comment 1 Don 2010-01-10 11:54:44 UTC
It shouldn't compile, since the constructor isn't marked as pure. But if you mark the constructor as pure:

 pure {
     this (float f) {
        this.f = f;
    }
 }

you get:
bug.d(14): Error: cannot modify const/immutable/inout expression this.f

So we definitely have a problem.
Comment 2 Tomasz Sowiński 2010-01-11 13:33:40 UTC
(In reply to comment #1)
> It shouldn't compile, since the constructor isn't marked as pure. But if you
> mark the constructor as pure:
> 
>  pure {
>      this (float f) {
>         this.f = f;
>     }
>  }
> 
> you get:
> bug.d(14): Error: cannot modify const/immutable/inout expression this.f
> 
> So we definitely have a problem.

Yes, I had a feeling compiler should let me have pure ctors..

What about the problem I mentioned at the bottom (if A is a class):

class A {
    float f;
    this (float f) {    // NOT pure
        this.f = f;
    }
    static pure A stworz(float f) {
        return new A(f);
    }
}

This compiles. Should it?
Comment 3 Tomasz Sowiński 2010-01-11 13:40:33 UTC
(In reply to comment #2)
> This compiles. Should it?

I'm now confident it shouldn't:

string global;
class A {
    float f;
    this (float f) {    // NOT pure
        this.f = f;
        global = "BUGABUGA!";
    }
    static pure A stworz(float f) {
        return new A(f);
    }
}
Comment 4 Don 2010-01-12 02:20:30 UTC
(In reply to comment #3)
> (In reply to comment #2)
> > This compiles. Should it?
> 
> I'm now confident it shouldn't:
> 
> string global;
> class A {
>     float f;
>     this (float f) {    // NOT pure
>         this.f = f;
>         global = "BUGABUGA!";
>     }
>     static pure A stworz(float f) {
>         return new A(f);
>     }
> }

That's bug 3573.
Comment 5 yebblies 2011-07-14 21:19:25 UTC
Marking constructors as pure works in current dmd (2.054).

I've put the other case as Issue 6320