digitalmars.D.learn - mixin under -betterC
- DLearner (32/32) Nov 23 2023 Code below is intended to test simple mixin with lambda function
- Paul Backus (21/28) Nov 23 2023 This is a known limitation:
- DLearner (8/10) Nov 26 2023 [...]
- Julian Fondren (11/14) Nov 23 2023 If you compile without -betterC, it'll work, but if you examine
- DLearner (7/21) Nov 23 2023 I tried what you suggested, and with no other changes it compiled
- Julian Fondren (5/7) Nov 23 2023 The `enum` answer? That also works, but you have to make a change
- DLearner (7/8) Nov 23 2023 On Thursday, 23 November 2023 at 18:54:09 UTC, Julian Fondren
- Adam D Ruppe (6/16) Nov 26 2023 This function exists at runtime. Another module could, in theory,
- DLearner (33/49) Dec 09 2023 From your comments and others on this thread:
- Basile B. (7/40) Nov 26 2023 You've been explained the reason why that does not work, note
Code below is intended to test simple mixin with lambda function under -betterC. Works with full-D, but fails with 'needs GC' errors under -betterC. Why is this so, bearing in mind the concatenations are executed at compile, not run, time? ``` // Test harness extern(C) void main() { import core.stdc.stdio : printf; import testmod; bool FirstVarGreater; int Var_A = 4; int Var_B = 3; FirstVarGreater = mixin(mxnTest("Var_A", "Var_B")); if (FirstVarGreater) { printf("First Var is Greater\n"); } else { printf("First Var is not Greater\n"); } } // testmod string mxnTest(string strVar1, string strVar2) { return `(int Var1, int Var2) { if (Var1 > Var2) { return true; } else { return false; } }(` ~ strVar1 ~ `,` ~ strVar2 ~ `)`; } ```
Nov 23 2023
On Thursday, 23 November 2023 at 16:33:52 UTC, DLearner wrote:Code below is intended to test simple mixin with lambda function under -betterC. Works with full-D, but fails with 'needs GC' errors under -betterC. Why is this so, bearing in mind the concatenations are executed at compile, not run, time?This is a known limitation: https://issues.dlang.org/show_bug.cgi?id=23637 The easiest way to work around it is to change `mxnTest` from a function to a templated manifest constant: ```d enum mxnTest(string strVar1, string strVar2) = `(int Var1, int Var2) { if (Var1 > Var2) { return true; } else { return false; } }(` ~ strVar1 ~ `,` ~ strVar2 ~ `)`; ``` Keep in mind that you will also have to change the call site to pass `"Var_A"` and `"Var_B"` as template arguments: ```d // Note the ! in front of the argument list FirstVarGreater = mixin(mxnTest!("Var_A", "Var_B")); ```
Nov 23 2023
On Thursday, 23 November 2023 at 17:02:58 UTC, Paul Backus wrote: [...]This is a known limitation: https://issues.dlang.org/show_bug.cgi?id=23637[...] Sorry to come back to this, but the reference above suggests _not_ a bug in the compiler. If not a bug in the compiler, please, what is going on? I repeat that the only possible trigger I see for the GC are the ~ that happen at compile, not run, time.
Nov 26 2023
On Thursday, 23 November 2023 at 16:33:52 UTC, DLearner wrote:Why is this so, bearing in mind the concatenations are executed at compile, not run, time?If you compile without -betterC, it'll work, but if you examine the result you'll find that the mxnTest function is still compiled into the result. D makes it so convenient to use functions at compile-time that there's no clear distinction for functions that should only exist at compile-time. Make mxnTest a template: ```d string mxnTest()(string strVar1, string strVar2) { ^^ ```
Nov 23 2023
On Thursday, 23 November 2023 at 17:03:29 UTC, Julian Fondren wrote:On Thursday, 23 November 2023 at 16:33:52 UTC, DLearner wrote:I tried what you suggested, and with no other changes it compiled and ran correctly. Thanks! I just find it surprising that your suggestion worked, but the (slightly simpler) earlier version did not.Why is this so, bearing in mind the concatenations are executed at compile, not run, time?If you compile without -betterC, it'll work, but if you examine the result you'll find that the mxnTest function is still compiled into the result. D makes it so convenient to use functions at compile-time that there's no clear distinction for functions that should only exist at compile-time. Make mxnTest a template: ```d string mxnTest()(string strVar1, string strVar2) { ^^ ```
Nov 23 2023
On Thursday, 23 November 2023 at 17:46:55 UTC, DLearner wrote:I just find it surprising that your suggestion worked, but the (slightly simpler) earlier version did not.The `enum` answer? That also works, but you have to make a change at the callsite as well, to `mixin(mxnTest!("Var_A", "Var_B"));` - passing the strings as template rather than functional arguments.
Nov 23 2023
On Thursday, 23 November 2023 at 18:54:09 UTC, Julian Fondren wrote: [...]The `enum` answer?[...] No, the 'template' answer. To me, if the 'template' suggestion worked (as it did), then my simple mixin (as in my original post) should also work.
Nov 23 2023
On Thursday, 23 November 2023 at 16:33:52 UTC, DLearner wrote:string mxnTest(string strVar1, string strVar2) { return `(int Var1, int Var2) { if (Var1 > Var2) { return true; } else { return false; } }(` ~ strVar1 ~ `,` ~ strVar2 ~ `)`; } ```This function exists at runtime. Another module could, in theory, import it and call it. A shared library could, in theory, export it. You used it at compile time, but the function is available for other users too. betterC doesn't know the difference between theory and practice.
Nov 26 2023
On Sunday, 26 November 2023 at 15:35:39 UTC, Adam D Ruppe wrote:On Thursday, 23 November 2023 at 16:33:52 UTC, DLearner wrote:From your comments and others on this thread: ``` // Test harness extern(C) void main() { import core.stdc.stdio : printf; import testmod; bool FirstVarGreater; int Var_A = 6; int Var_B = 5; FirstVarGreater = mixin(mxnTest("Var_A", "Var_B")); if (FirstVarGreater) { printf("First Var is Greater\n"); } else { printf("First Var is not Greater\n"); } } // testmod string mxnTest(string strVar1, string strVar2) { if (__ctfe) { return `(int Var1, int Var2) { if (Var1 > Var2) { return true; } else { return false; } }(` ~ strVar1 ~ `,` ~ strVar2 ~ `)`; } else { return ``; } } ``` Works, avoid templates + -betterC compliant, but to me clumsy.string mxnTest(string strVar1, string strVar2) { return `(int Var1, int Var2) { if (Var1 > Var2) { return true; } else { return false; } }(` ~ strVar1 ~ `,` ~ strVar2 ~ `)`; } ```This function exists at runtime. Another module could, in theory, import it and call it. A shared library could, in theory, export it. You used it at compile time, but the function is available for other users too. betterC doesn't know the difference between theory and practice.
Dec 09 2023
On Thursday, 23 November 2023 at 16:33:52 UTC, DLearner wrote:Code below is intended to test simple mixin with lambda function under -betterC. Works with full-D, but fails with 'needs GC' errors under -betterC. Why is this so, bearing in mind the concatenations are executed at compile, not run, time? ``` // Test harness extern(C) void main() { import core.stdc.stdio : printf; import testmod; bool FirstVarGreater; int Var_A = 4; int Var_B = 3; FirstVarGreater = mixin(mxnTest("Var_A", "Var_B")); if (FirstVarGreater) { printf("First Var is Greater\n"); } else { printf("First Var is not Greater\n"); } } // testmod string mxnTest(string strVar1, string strVar2) { return `(int Var1, int Var2) { if (Var1 > Var2) { return true; } else { return false; } }(` ~ strVar1 ~ `,` ~ strVar2 ~ `)`; } ```You've been explained the reason why that does not work, note however that it's not hopeless see - https://forum.dlang.org/thread/ahqnylrdftmmvtyvompr forum.dlang.org - https://github.com/dlang/dmd/pull/15636 unfortunately the PR is stalled since two months.
Nov 26 2023