Re: variant visit not pure?

2020-05-08 Thread Dukc via Digitalmars-d-learn

On Thursday, 7 May 2020 at 20:12:03 UTC, learner wrote:


Modules of D standard library aren't in a good shape, if 
everyone suggests alternatives for a basic building block as 
variant.


I don't think Variant as a whole is the problem, when one uses it 
as the infinite variant it does fairly much what one can expect. 
The finite-field specialization of it is the one that's badly 
implemented.




The types VariantN can hold are known at compile time, why 
can't it be specialized?


It could, probably. This shows the biggest weakness (and 
strength) of D development: It's voluntary, so people work on 
that they happen to want to. That makes it unevenly developed 
compared to financially backed projects. We have both plenty of 
cool & rare features and lack of many relatively basic ones at 
the same time.


Re: variant visit not pure?

2020-05-08 Thread Dukc via Digitalmars-d-learn

On Thursday, 7 May 2020 at 15:36:36 UTC, Ben Jones wrote:
I've been using SumType... What are the main differences 
between it and TaggedAlgebraic?


I have not used the the algebraic type of Taggedalgebraic tbh, 
but it also has a tagged union type that I have good experiences 
with. Unlike Phobos algebraic or SumType, it can have multiple 
fields of same type that are still separate by the tag value. 
Also unlike the two others I mentioned, you can handily define a 
`Void` field (or many of them) if you want special values for the 
tag that don't come with a value. In essence, 
`Taggedalgebraic.TaggedUnion` it's the D equivalent of Rust 
`enum`[1].


1: https://doc.rust-lang.org/book/ch06-00-enums.html


Re: variant visit not pure?

2020-05-08 Thread Dukc via Digitalmars-d-learn

On Thursday, 7 May 2020 at 10:21:26 UTC, Dukc wrote:


that's the reason why `std.range.enumerate` does not infer 
attributes for example


This was wrong. `enumerate` can infer. It's `lockstep` that 
cannot.





Re: variant visit not pure?

2020-05-07 Thread learner via Digitalmars-d-learn
On Thursday, 7 May 2020 at 14:53:10 UTC, Steven Schveighoffer 
wrote:

On 5/7/20 5:22 AM, learner wrote:

[...]


Because VariantN (the base of Algebraic) can literally hold 
anything, it cannot be pure, @safe, nothrow, @nogc.


As others have recommended, I suggest using TaggedAlgebraic. I 
recently have been using it to create an algebraic type to hold 
a MYSQL value, so I can migrate the mysql-native library to be 
@safe (mysql-native currently uses Variant for everything).


I added a special UDA to TaggedAlgebraic, so you can guarantee 
only @safe calls are allowed (for instance, if it can hold a 
pointer and an int, then opBinary!"+" can be marked as @safe if 
the operation fails when it's a pointer).


TaggedAlgebraic could probably do the same for pure, but not 
sure about nothrow and @nogc, since it uses exceptions when 
things aren't valid.


-Steve


Modules of D standard library aren't in a good shape, if everyone 
suggests alternatives for a basic building block as variant.


The types VariantN can hold are known at compile time, why can't 
it be specialized?





Re: variant visit not pure?

2020-05-07 Thread Paul Backus via Digitalmars-d-learn

On Thursday, 7 May 2020 at 15:36:36 UTC, Ben Jones wrote:
On Thursday, 7 May 2020 at 14:53:10 UTC, Steven Schveighoffer 
wrote:


As others have recommended, I suggest using TaggedAlgebraic. I 
recently have been using it to create an algebraic type to 
hold a MYSQL value, so I can migrate the mysql-native library 
to be @safe (mysql-native currently uses Variant for 
everything).


-Steve


I've been using SumType... What are the main differences 
between it and TaggedAlgebraic?


As far as I can tell, there are two main differences:

1. TaggedAlgebraic has some convenient operator overloads that 
can assert at runtime if called improperly (i.e., when the 
contained type does not support the operation). SumType never 
asserts at runtime, and instead requires you to use `match` for 
these operations to ensure that they are only performed on the 
appropriate types.


2. TaggedAlgebraic requires you to declare a union type as a 
"base", whereas SumType takes the list of member types directly 
as template arguments.


If you want more detailed information, both have online 
documentation:


TaggedAlgebraic: 
https://vibed.org/api/taggedalgebraic.taggedalgebraic/

SumType: https://pbackus.github.io/sumtype/sumtype.html


Re: variant visit not pure?

2020-05-07 Thread Ben Jones via Digitalmars-d-learn
On Thursday, 7 May 2020 at 14:53:10 UTC, Steven Schveighoffer 
wrote:


As others have recommended, I suggest using TaggedAlgebraic. I 
recently have been using it to create an algebraic type to hold 
a MYSQL value, so I can migrate the mysql-native library to be 
@safe (mysql-native currently uses Variant for everything).


-Steve


I've been using SumType... What are the main differences between 
it and TaggedAlgebraic?





Re: variant visit not pure?

2020-05-07 Thread Steven Schveighoffer via Digitalmars-d-learn

On 5/7/20 5:22 AM, learner wrote:

Good morning,

Is there a reason why std.variant.visit is not inferring pure?

```
void test() pure {
     Algebraic!(int, string) alg;
     visit!( (string) => 0, (int) => 0)(alg);
}

Error: pure function test cannot call impure function 
test.visit!(VariantN!(16LU, int, string)).visit

```

Thank you


Because VariantN (the base of Algebraic) can literally hold anything, it 
cannot be pure, @safe, nothrow, @nogc.


As others have recommended, I suggest using TaggedAlgebraic. I recently 
have been using it to create an algebraic type to hold a MYSQL value, so 
I can migrate the mysql-native library to be @safe (mysql-native 
currently uses Variant for everything).


I added a special UDA to TaggedAlgebraic, so you can guarantee only 
@safe calls are allowed (for instance, if it can hold a pointer and an 
int, then opBinary!"+" can be marked as @safe if the operation fails 
when it's a pointer).


TaggedAlgebraic could probably do the same for pure, but not sure about 
nothrow and @nogc, since it uses exceptions when things aren't valid.


-Steve


Re: variant visit not pure?

2020-05-07 Thread Dukc via Digitalmars-d-learn

On Thursday, 7 May 2020 at 13:17:21 UTC, learner wrote:

I've find this: https://issues.dlang.org/show_bug.cgi?id=16662


Hmm, that explains why it can't infer attributes. An unlimited 
variant could contain an object, and using it might or might not 
be .


Of course, it could still infer the attribute for algebraic types 
were the wrapper a bit smarter. But `Algebraic` is inferior to 
the DUB packages anyway. Bad performance like Simen said, and can 
always be `null` regardless of requested types. With 
Taggedalgebraic, you can insert `Void` to allowed types if you 
want `null` value but you don't have it just because.


Re: variant visit not pure?

2020-05-07 Thread learner via Digitalmars-d-learn

On Thursday, 7 May 2020 at 10:41:01 UTC, Simen Kjærås wrote:

On Thursday, 7 May 2020 at 09:22:28 UTC, learner wrote:

Good morning,

Is there a reason why std.variant.visit is not inferring pure?

```
void test() pure {
Algebraic!(int, string) alg;
visit!( (string) => 0, (int) => 0)(alg);
}

Error: pure function test cannot call impure function 
test.visit!(VariantN!(16LU, int, string)).visit

```


std.variant.Algebraic is essentially a std.variant.Variant in 
different clothes. Variant is very flexible, and this comes at 
a cost (and isn't used in Algebraic, meaning you pay for things 
you don't use). Like Dukc said, you might be better off with 
Taggedalgebraic or SumType 
(https://code.dlang.org/packages/sumtype).



Variant uses runtime type information to hold *any* type. Since 
Algebraic specifically only holds a few types, all the 
framework that's in place for Variant is wasted on Algebraic, 
and makes it less useful and less performant.


--
  Simen


Thank you Simon and Dukc,

I've find this: https://issues.dlang.org/show_bug.cgi?id=16662

So, it seems that Phobos isn't in a good shape ... what a pity!


Re: variant visit not pure?

2020-05-07 Thread Simen Kjærås via Digitalmars-d-learn

On Thursday, 7 May 2020 at 09:22:28 UTC, learner wrote:

Good morning,

Is there a reason why std.variant.visit is not inferring pure?

```
void test() pure {
Algebraic!(int, string) alg;
visit!( (string) => 0, (int) => 0)(alg);
}

Error: pure function test cannot call impure function 
test.visit!(VariantN!(16LU, int, string)).visit

```


std.variant.Algebraic is essentially a std.variant.Variant in 
different clothes. Variant is very flexible, and this comes at a 
cost (and isn't used in Algebraic, meaning you pay for things you 
don't use). Like Dukc said, you might be better off with 
Taggedalgebraic or SumType 
(https://code.dlang.org/packages/sumtype).



Variant uses runtime type information to hold *any* type. Since 
Algebraic specifically only holds a few types, all the framework 
that's in place for Variant is wasted on Algebraic, and makes it 
less useful and less performant.


--
  Simen


Re: variant visit not pure?

2020-05-07 Thread Dukc via Digitalmars-d-learn

On Thursday, 7 May 2020 at 09:22:28 UTC, learner wrote:

Good morning,

Is there a reason why std.variant.visit is not inferring pure?



I think `variant` will not infer any trributes. I'm not sure why. 
It could be some language limitation (that's the reason why 
`std.range.enumerate` does not infer attributes for example). Or 
it could be just badly implemented.


Either way, there are DUB packages that are better in this (and 
other) regards. I recommend Taggedalgebraic[1].


[1] https://code.dlang.org/packages/taggedalgebraic



variant visit not pure?

2020-05-07 Thread learner via Digitalmars-d-learn

Good morning,

Is there a reason why std.variant.visit is not inferring pure?

```
void test() pure {
Algebraic!(int, string) alg;
visit!( (string) => 0, (int) => 0)(alg);
}

Error: pure function test cannot call impure function 
test.visit!(VariantN!(16LU, int, string)).visit

```

Thank you