Thread overview
2 class issues
Mar 07, 2019
spir
Mar 07, 2019
Johannes Loher
Mar 07, 2019
ag0aep6g
March 07, 2019
Hello,

First, I am not very experimented with the combination of static lang (alloc & typing) and OO (class-based). I'm implementing a library for lexical analysis (lexing), with 2 minor issues:

-1- How to enforce that subclasses implement given methods without using "abstract", which seems to make the whole class abstract? (no info found in doc, actually, the page on classes [1] does not seem to even mention abstract classes)

-2- How to have "constant" (predefined) class instances at the module-level? The compiler requires a "static this ()". What does this actually mean (for a constructor)? What are the consequences, for either my code or client code? (The doc on the topic [2] is rather obscure for me, and I could not find better elsewhere.)

I'm also bluffed by "Static constructors have empty parameter lists." Does this mean I should manually fill the fields? (not a big deal, but why???) This may give:
    // Predefined pseudo-pattern "End-of-Text":
    auto EoT = new Pattern() ;       // ???
    EoT.name = "EoT" ;

    // Unique lexeme "end-of-text":
    auto eot = new Lexeme() ;       // ???
    eot.patname = "EoT" ;
    eot.slice = null ;
    eot.index = uint.max ;
Then, why have a constructor at all? This would also prevent me from making classes immutable, while conceptually all are immutable... (no reason for a pattern or a lexeme to change)

Thank you,
diniz

[1] https://dlang.org/spec/class.html
[2] https://dlang.org/spec/class.html#static-constructor
March 07, 2019
Am 07.03.19 um 11:38 schrieb spir:
> Hello,
> 
> First, I am not very experimented with the combination of static lang
> (alloc & typing) and OO (class-based). I'm implementing a library for
> lexical analysis (lexing), with 2 minor issues:
> 
> -1- How to enforce that subclasses implement given methods without using "abstract", which seems to make the whole class abstract? (no info found in doc, actually, the page on classes [1] does not seem to even mention abstract classes)
> 
> -2- How to have "constant" (predefined) class instances at the
> module-level? The compiler requires a "static this ()". What does this
> actually mean (for a constructor)? What are the consequences, for either
> my code or client code? (The doc on the topic [2] is rather obscure for
> me, and I could not find better elsewhere.)
> 
> I'm also bluffed by "Static constructors have empty parameter lists."
> Does this mean I should manually fill the fields? (not a big deal, but
> why???) This may give:
>     // Predefined pseudo-pattern "End-of-Text":
>     auto EoT = new Pattern() ;       // ???
>     EoT.name = "EoT" ;
> 
>     // Unique lexeme "end-of-text":
>     auto eot = new Lexeme() ;       // ???
>     eot.patname = "EoT" ;
>     eot.slice = null ;
>     eot.index = uint.max ;
> Then, why have a constructor at all? This would also prevent me from
> making classes immutable, while conceptually all are immutable... (no
> reason for a pattern or a lexeme to change)
> 
> Thank you,
> diniz
> 
> [1] https://dlang.org/spec/class.html
> [2] https://dlang.org/spec/class.html#static-constructor

Regarding your first point: I don't think it is currently possible to force derived classes to override functions from the base class while also implementing these functions in the base class. What would the usecase of this be anyways?

Regarding your second point: What excatly do you mean by '"constant" (predefined) class'? Do you mean that you want to provide an instant from that class? You can achieve this like the following:

```
class Test
{
}

Test testInstance;

static this() {
    testInstance = new Test();
}
```
If you want the testInstance to be shared across threads:
```
class Test
{
}

shared Test testInstance;

shared static this() {
    testInstance = new Test();
}
```

You seem to be misunderstanding how static class constructors work: They are not invoked when you try to instanciate the class, but when the module in which the class is located is loaded. This also explains why they need to have empty parameter lists: You cannot pass arguments when loading a module  static constructors are usually used to initialize static class variables. Consider the following example:

```
import core.thread: Thread;

class Test
{

    private static ulong i;

    static this() {
        i = Thread.getThis.id;
    }
}
```
You cannot initialize `i` directly in its declaration because
`Thread.getThis.id` is only available at runtime (i.e. `private static
ulong i = Thread.getThis.id;` does not compile). To get around this, you
can use static constructors.

March 07, 2019
On 07.03.19 11:38, spir wrote:
> -1- How to enforce that subclasses implement given methods without using "abstract", which seems to make the whole class abstract?

Not, as far as I can tell. You can't force derived classes to override an existing implementation. And you can't omit the implementation without making the class abstract.

> -2- How to have "constant" (predefined) class instances at the module-level?

Just like so?

const o = new Object; /* works for me */

> The compiler requires a "static this ()".

For what code does it say that?

> What does this actually mean (for a constructor)? What are the consequences, for either my code or client code? (The doc on the topic [2] is rather obscure for me, and I could not find better elsewhere.)
> 
> I'm also bluffed by "Static constructors have empty parameter lists." Does this mean I should manually fill the fields? (not a big deal, but why???) This may give:
>      // Predefined pseudo-pattern "End-of-Text":
>      auto EoT = new Pattern() ;       // ???
>      EoT.name = "EoT" ;
> 
>      // Unique lexeme "end-of-text":
>      auto eot = new Lexeme() ;       // ???
>      eot.patname = "EoT" ;
>      eot.slice = null ;
>      eot.index = uint.max ;
> Then, why have a constructor at all? This would also prevent me from making classes immutable, while conceptually all are immutable... (no reason for a pattern or a lexeme to change)

You're misunderstanding the nature of static constructors.

Static constructors are a special kind of function that runs once at the beginning of the program/thread, automatically. They're not constructors for static objects. You can't call static constructors from your code. `new Foo` calls a (normal) constructor; doesn't matter if you're creating a dynamic instance or a static one.