digitalmars.D - Feature idea: .userinit property (or trait) to retrieve the
- Andrej Mitrovic (69/69) Jul 17 2013 I often need to re-initialize a variable back to its user-defined
- Maxim Fomin (12/45) Jul 17 2013 I think this is not a fair comparison. Your S s could be S s =
- Andrej Mitrovic (4/8) Jul 17 2013 It wasn't meant to be a comparison, but a showcase that we already
- Vladimir Panteleev (6/9) Jul 17 2013 At least once I wanted to reset a variable to its default value
- H. S. Teoh (9/19) Jul 17 2013 How would you handle this case:
I often need to re-initialize a variable back to its user-defined initializer. For variables that have no user-defined initializer, you can simply use .init. For fields of structs or classes you can actually use A.init.field, where A is the aggregate type. For example: ----- struct S { int value = 5; } void main() { S s; s.value += 1; s.value = S.init.value; assert(s.value == 5); // ok } ----- But there's no equivalent for variables which do not belong to any aggregate: ----- void main() { int value = 5; value += 1; // value = ?? assert(value == 5); } ----- One workaround is to factor out the initializer to a manifest constant, for example: ----- void main() { enum valueInit = 5; int value = valueInit; value += 1; value = valueInit; assert(value == 5); } ----- It's a workable solution, but I think we can do better. I'd like us to introduce either a .userinit property, or a compiler trait. For example: ----- template userinit(alias symbol) { enum userinit = __traits(getSymbolInitializer, symbol); } void main() { int value = 5; value += 1; value = userinit!value; assert(value == 5); } ----- The trait version is less intrusive to the language than a .userinit property, although the latter would avoid having to instantiate a template: ----- void main() { int value = 5; value += 1; value = value.userinit; assert(value == 5); } ----- Anyway, I think the feature should be fairly easy to implement, but would anyone else have a use for this?
Jul 17 2013
On Wednesday, 17 July 2013 at 11:28:18 UTC, Andrej Mitrovic wrote:I often need to re-initialize a variable back to its user-defined initializer. For variables that have no user-defined initializer, you can simply use .init. For fields of structs or classes you can actually use A.init.field, where A is the aggregate type. For example: ----- struct S { int value = 5; } void main() { S s; s.value += 1; s.value = S.init.value; assert(s.value == 5); // ok } ----- But there's no equivalent for variables which do not belong to any aggregate: ----- void main() { int value = 5; value += 1; // value = ?? assert(value == 5); } -----I think this is not a fair comparison. Your S s could be S s = S(2) and you cannot retrieve S(2) just like in case with int value = 5. I see no difference between basic type variables and user-defined variables here. Also, this reminds me replacing typedef by alias with loosing one nice feature - you could do typedef MyInt int = 5; but not with alias.One workaround is to factor out the initializer to a manifest constant, for example:Other approach is to use UDA, it may be better then enum, but one still need extra typing. Having new trait seems to be a good idea but it needs to be figured out how it behaves in different contexts.
Jul 17 2013
On 7/17/13, Maxim Fomin <maxim maxim-fomin.ru> wrote:I think this is not a fair comparison. Your S s could be S s = S(2) and you cannot retrieve S(2) just like in case with int value = 5. I see no difference between basic type variables and user-defined variables here.It wasn't meant to be a comparison, but a showcase that we already have /some/ form of retrieving the initializer, but I want to expand this for all variables and not just fields of aggregates.
Jul 17 2013
On Wednesday, 17 July 2013 at 11:28:18 UTC, Andrej Mitrovic wrote:Anyway, I think the feature should be fairly easy to implement, but would anyone else have a use for this?At least once I wanted to reset a variable to its default value (which wasn't in a manifest constant). Would it make sense to [ab]use the "default" keyword for this, to avoid introducing a new property which might collide with existing code?
Jul 17 2013
On Thu, Jul 18, 2013 at 12:33:20AM +0200, Vladimir Panteleev wrote:On Wednesday, 17 July 2013 at 11:28:18 UTC, Andrej Mitrovic wrote:How would you handle this case: int x = funcWithSideEffects(); x = 123; x = x.default; // what is the value of x now? ? T -- Two wrongs don't make a right; but three rights do make a left...Anyway, I think the feature should be fairly easy to implement, but would anyone else have a use for this?At least once I wanted to reset a variable to its default value (which wasn't in a manifest constant). Would it make sense to [ab]use the "default" keyword for this, to avoid introducing a new property which might collide with existing code?
Jul 17 2013