`this` template params for struct not expressing constness.

evilrat evilrat666 at gmail.com
Mon Jun 8 08:07:26 UTC 2020


On Monday, 8 June 2020 at 07:35:12 UTC, adnan338 wrote:
> Hi, as far as I understand, the `this` template parameter 
> includes constness qualifiers as seen in 
> https://ddili.org/ders/d.en/templates_more.html
>
> To apply this I have this following struct:
>
> module bst;
>
> struct Tree(T) {
>     T item;
>     Tree!T* parent, left, right;
>
>     this(T item) {
>         this.item = item;
>     }
>
>     Self* searchTree(this Self)(auto in ref T item) const {
>         if (&this is null)
>             return null;
>         if (this.item == item)
>             return &this;
>         return (this.item < item) ? this.right.searchTree(item) 
> : this.right.searchTree(item);
>     }
> }
>
> unittest {
>     auto text1 = "Hello", text2 = "World";
>
>     auto tree2 = Tree!string(text1);
>     assert(tree2.searchTree(text2) is null);
>     assert(tree2.searchTree(text1) !is null);
>
>     auto tree1 = Tree!int(4);
>     assert(tree1.searchTree(5) is null);
>     assert(tree1.searchTree(4) !is null);
>
> }
>
>
> When I run the unittest the compiler complains:
>
> cannot implicitly convert expression &this of type 
> const(Tree!string)* to Tree!string*
>
> Run link: https://run.dlang.io/is/b76DND
>
> Why does this happen?

If I correctly understand what you are trying to do the answer is 
- in D const is transitive (unlike the C++ where it isn't).

And in your searchTree() method you are basically trying to 
escape that constness. You can change the signature to return 
const(Self)*, or maybe add non-const overload depending on your 
needs.

Don't even think about casting away const with `return 
cast(Self*) &this;` as this UB in D, and it will bite you 
somewhere later because compiler might rely on const for 
optimization.



More information about the Digitalmars-d-learn mailing list