digitalmars.D.learn - CTFE question
- Danny Arends (24/24) Aug 28 2012 I have the following code:
- Chris Cain (30/33) Aug 28 2012 You're doing something wrong, but I can see why the error message
- Danny Arends (11/45) Aug 28 2012 Ahhh I understand...
- Chris Cain (6/13) Aug 28 2012 I'm pretty sure there isn't. However, if you're just trying to
- Danny Arends (10/16) Aug 28 2012 Well it just seems some compilation runs take way longer (and
- bearophile (8/10) Aug 28 2012 The ending newline is bad, because it unnecessarily kills some
- Philippe Sigaud (38/54) Aug 28 2012 Godd adivce, except beware of using ++ and --, they don't work at
- Don Clugston (2/24) Sep 03 2012 Really? That's scary. Is there a bug report for this?
- Philippe Sigaud (26/30) Sep 03 2012 I re-tried this and I was mistaken: it's not ++ or --, it's changing
- bearophile (19/20) Sep 03 2012 Yeah. CTFE must give the same results when CTFE works.
- Philippe Sigaud (2/4) Sep 03 2012 http://d.puremagic.com/issues/show_bug.cgi?id=8614
I have the following code: ------------------------------------ import std.stdio; import std.metastrings; pure int[] testCTFE(){ int[] r; pragma(msg, "Testing CTFE"); foreach(i; 0 .. 360){ r ~= i; pragma(msg, Format!("Loop: %d",i)); } pragma(msg, "Done CTFE test"); return r; } immutable CTFEdata = testCTFE(); void main(string[] args){ } ---------------------------------- I expected this would compile and during compilation print: Loop: 1 Loop:2, etc However, I get a compilation error: ctfe.d(9): Error: variable i cannot be read at compile time Is this a bug or am I doing something wrong ?? Danny Arends http://www.dannyarends.nl
Aug 28 2012
On Tuesday, 28 August 2012 at 11:13:40 UTC, Danny Arends wrote:Is this a bug or am I doing something wrong ?? Danny Arends http://www.dannyarends.nlYou're doing something wrong, but I can see why the error message would confuse you. Your problem is using those pragma(msg, ...) lines... They produce a message while something is being compiled, right? The CTFE function is ran _after_ it has been compiled. Hence i can't be read while the CTFE function is compiled. So, to be clear, doing this: ----- import std.stdio; import std.metastrings; pure int[] testCTFE(){ int[] r; pragma(msg, "Testing CTFE"); foreach(i; 0 .. 360){ r ~= i; //pragma(msg, Format!("Loop: %d",i)); } pragma(msg, "Done CTFE test"); return r; } immutable CTFEdata = testCTFE(); immutable CTFEdata2 = testCTFE(); void main(string[] args){ } ---- Produces just one output: Testing CTFE Done CTFE test Because the pragmas are done _as it's compiled_, not as it's ran (even though CTFE is done "at compile time").
Aug 28 2012
Ahhh I understand... As a follow up, is it then possible to 'track' filling a large enum / immutable on compile time by outputting a msg every for ? I'm generating rotation matrices for yaw, pitch and roll at compile time which can take a long time depending on how fine grained I create them. Gr, Danny Arends http://www.dannyarends.nl On Tuesday, 28 August 2012 at 11:29:32 UTC, Chris Cain wrote:On Tuesday, 28 August 2012 at 11:13:40 UTC, Danny Arends wrote:Is this a bug or am I doing something wrong ?? Danny Arends http://www.dannyarends.nlYou're doing something wrong, but I can see why the error message would confuse you. Your problem is using those pragma(msg, ...) lines... They produce a message while something is being compiled, right? The CTFE function is ran _after_ it has been compiled. Hence i can't be read while the CTFE function is compiled. So, to be clear, doing this: ----- import std.stdio; import std.metastrings; pure int[] testCTFE(){ int[] r; pragma(msg, "Testing CTFE"); foreach(i; 0 .. 360){ r ~= i; //pragma(msg, Format!("Loop: %d",i)); } pragma(msg, "Done CTFE test"); return r; } immutable CTFEdata = testCTFE(); immutable CTFEdata2 = testCTFE(); void main(string[] args){ } ---- Produces just one output: Testing CTFE Done CTFE test Because the pragmas are done _as it's compiled_, not as it's ran (even though CTFE is done "at compile time").
Aug 28 2012
On Tuesday, 28 August 2012 at 11:39:20 UTC, Danny Arends wrote:Ahhh I understand... As a follow up, is it then possible to 'track' filling a large enum / immutable on compile time by outputting a msg every for ? I'm generating rotation matrices for yaw, pitch and roll at compile time which can take a long time depending on how fine grained I create them.I'm pretty sure there isn't. However, if you're just trying to develop/test your algorithm, you could write a program that runs it as a normal function (and just use writeln) as you develop it. After it's done, you remove the writelns, mark the function as pure and it should work exactly the same in CTFE.
Aug 28 2012
On Tuesday, 28 August 2012 at 12:07:07 UTC, Chris Cain wrote:On Tuesday, 28 August 2012 at 11:39:20 UTC, Danny Arends wrote: I'm pretty sure there isn't. However, if you're just trying to develop/test your algorithm, you could write a program that runs it as a normal function (and just use writeln) as you develop it. After it's done, you remove the writelns, mark the function as pure and it should work exactly the same in CTFE.Well it just seems some compilation runs take way longer (and more memory) then others..Googling I found that I just got to wait for: https://github.com/D-Programming-Language/dmd/pull/692 to be accepted. Seems a bit strange that a discussion about yes/no newline is keeping this from getting into DMD. Just basic ctfewrite support would help me a lot. Gr, Danny Arends
Aug 28 2012
Danny Arends:Seems a bit strange that a discussion about yes/no newline is keeping this from getting into DMD.The ending newline is bad, because it unnecessarily kills some use cases for this feature. But I think the newline is not what is keeping it out of DMD. It's just there are about a hundred open patches, and Walter is currently implementing 64bits on Windows. Bye, bearophile
Aug 28 2012
On Tue, Aug 28, 2012 at 2:07 PM, Chris Cain <clcain uncg.edu> wrote:On Tuesday, 28 August 2012 at 11:39:20 UTC, Danny Arends wrote:Godd adivce, except beware of using ++ and --, they don't work at compile-time. I'm regularly caught unaware by this, particularly while looping. Danny is also using 0..360, which is a runtime value. There exists a compile-time version of foreach which is automatically invoked whenever you use foreach on a compile-time 'range' (aka, typetuple) So: template Loop(T...) { /* some code */ foreach(i,Type; T) pragma(msg, i); } will work. So, a way to get what the OP wanted is to create a tuple of the required length. Since integers are valid template arguments, we can use them directly like this: template staticRange(uint upto) { static if (upto == 0) alias TypeTuple!() staticRange; else alias TypeTuple!(staticRange!(upto-1), upto-1) staticRange; } So staticRange!3 is the tuple 0,1,2. (staticRange!0 is empty) You can foreach on it: pure int[] testCTFE(){ int[] r; pragma(msg, "Testing CTFE"); foreach(i; staticRange!360){ r ~= i; pragma(msg, i); } pragma(msg, "Done CTFE test"); return r; } Of course, that means knowing the upper value at compile-time.Ahhh I understand... As a follow up, is it then possible to 'track' filling a large enum / immutable on compile time by outputting a msg every for ? I'm generating rotation matrices for yaw, pitch and roll at compile time which can take a long time depending on how fine grained I create them.I'm pretty sure there isn't. However, if you're just trying to develop/test your algorithm, you could write a program that runs it as a normal function (and just use writeln) as you develop it. After it's done, you remove the writelns, mark the function as pure and it should work exactly the same in CTFE.
Aug 28 2012
On 28/08/12 19:40, Philippe Sigaud wrote:On Tue, Aug 28, 2012 at 2:07 PM, Chris Cain <clcain uncg.edu> wrote:Really? That's scary. Is there a bug report for this?On Tuesday, 28 August 2012 at 11:39:20 UTC, Danny Arends wrote:Godd adivce, except beware of using ++ and --, they don't work at compile-time. I'm regularly caught unaware by this, particularly while looping.Ahhh I understand... As a follow up, is it then possible to 'track' filling a large enum / immutable on compile time by outputting a msg every for ? I'm generating rotation matrices for yaw, pitch and roll at compile time which can take a long time depending on how fine grained I create them.I'm pretty sure there isn't. However, if you're just trying to develop/test your algorithm, you could write a program that runs it as a normal function (and just use writeln) as you develop it. After it's done, you remove the writelns, mark the function as pure and it should work exactly the same in CTFE.
Sep 03 2012
On Mon, Sep 3, 2012 at 1:27 PM, Don Clugston <dac nospam.com> wrote:I re-tried this and I was mistaken: it's not ++ or --, it's changing an iteration index at compile-time. My bad. int[] indices(string s) { int[] store; foreach(i,ch; s[0..$-1]) { store ~= i; if (s[i..i+2] == "aa") i += 1; // also ++i or i++, no difference here } return store; } void main() { enum result1 = indices("aaabc"); auto result2 = indices("aaabc"); writeln(result1); // [0,1,2,3] writeln(result2); // [0,2,3] } I know changing 'i' while iterating is not a good idea, but at least in this case, CT-executed and RT-execution give a different result. All my other tests with ++ and -- give correct results, sorry for the bad publicity. Worth a bug report?Godd adivce, except beware of using ++ and --, they don't work at compile-time. I'm regularly caught unaware by this, particularly while looping.Really? That's scary. Is there a bug report for this?
Sep 03 2012
Philippe Sigaud:Worth a bug report?Yeah. CTFE must give the same results when CTFE works. A simpler test case for Bugzilla: import std.stdio; int[] foo(int[] data) { foreach (i, ref x; data) { x++; i++; } return data; } void main() { enum result1 = foo([10, 20, 30, 40]); auto result2 = foo([10, 20, 30, 40]); writeln(result1); // [11, 21, 31, 41] writeln(result2); // [11, 20, 31, 40] } Bye, bearophile
Sep 03 2012
On Mon, Sep 3, 2012 at 4:08 PM, bearophile <bearophileHUGS lycos.com> wrote:http://d.puremagic.com/issues/show_bug.cgi?id=8614Worth a bug report?Yeah. CTFE must give the same results when CTFE works.
Sep 03 2012