Re: how to benchmark pure functions?
On Thursday, 27 October 2022 at 17:17:01 UTC, ab wrote: Hi, when trying to compare different implementations of the optimized builds of a pure function using benchmark from std.datetime.stopwatch, I get times equal to zero, I suppose because the functions are not executed as they do not have side effects. The same happens with the example from the documentation: https://dlang.org/library/std/datetime/stopwatch/benchmark.html How can I prevent the compiler from removing the code I want to measure? Is there some utility in the standard library or pragma that I should use? Thanks AB Thanks to H.S. Teoh and Dennis for the suggestions, they both work. I like the empty asm block a bit more because it is less invasive, but it only works with ldc. @Imperatorn see Dennis code for an example. std.datetime.benchmark works, but at high optimization level (-O2, -O3) the loop can be removed and the time brought down to 0hnsec. E.g. try "ldc2 -O3 -run dennis.d". AB
how to benchmark pure functions?
Hi, when trying to compare different implementations of the optimized builds of a pure function using benchmark from std.datetime.stopwatch, I get times equal to zero, I suppose because the functions are not executed as they do not have side effects. The same happens with the example from the documentation: https://dlang.org/library/std/datetime/stopwatch/benchmark.html How can I prevent the compiler from removing the code I want to measure? Is there some utility in the standard library or pragma that I should use? Thanks AB
Re: vibe.d / experience / feedback
On Thursday, 1 October 2020 at 06:32:23 UTC, Robert M. Münch wrote: 3. Vibe can't handle GET & POST on the same URL... we solved this one as well: fortunately (and: of course) vibe can handle this. what lead us to believe otherwise, was that, unfortunately, one of the handlers crashed (effectively due to a `cast(JSONValue)` of a `Json.Undefined`), without any visible error output; and the only visible error was a "no route matches path" output from vibe. sorry for the confusion.
Re: vibe.d / experience / feedback
On Thursday, 1 October 2020 at 06:39:39 UTC, mipri wrote: On Thursday, 1 October 2020 at 06:32:23 UTC, Robert M. Münch wrote: 5. One can't access the raw HTTP request body, things must be go through Vibe's JSON parser. To get access to the raw body, a lot of workarounds are necessary. given an HTTPServerRequest req, req.bodyReader.readAll for binary data and .readAllUTF8 for text. thanks. that was tough to find from https://vibed.org/api/vibe.core.stream/InputStream (because it's located and thus documented in the helper module https://vibed.org/api/vibe.stream.operations/). a link from InputStream to vibe.stream.operations would be super-good.
Re: My RPN calculator code review?
On Saturday, 18 July 2020 at 10:33:23 UTC, Anonymouse wrote: I'm not happy about the looping and allocating replacements of spaced_args, Actually, I got rid of that code entirely in order to support negative values: -5 -6 * == 30
My RPN calculator code review?
Hello, inspired by the "Tiny RPN calculator" example seen on the dlang homepage, I wanted to create my own version. I'd appreciate your opinions regarding style, mistakes/code smell/bad practice. Thank you. import std.array; import std.conv; import std.stdio; void main(string[] args) { if (args.length == 1) { writeln("usage examples:\n\t", args[0], " 5 3 + 2 *\n\t", args[0], " 12.1 11 /"); return; } immutable string valid_ops = "+-*/"; string spaced_args = args[1 .. $].join(" "); // this is done to correctly handle "messy" inputs such as "5 3 2*+" foreach (o; valid_ops) { spaced_args = spaced_args.replace(o, " " ~ o ~ " "); } real[] stack; foreach (op; spaced_args.split) { LabeledSwitch: switch (op) // operator or operand? { static foreach (o; valid_ops) { case [o]: stack = stack[0 .. $ - 2] ~ mixin("stack[$ - 2]" ~ o ~ "stack[$ - 1]"); break LabeledSwitch; } default: // assume it's an operand, a real number stack ~= to!real(op); break; } } writeln(stack); }
Progress printing with threads?
Hello. I am unsure how to proceed about printing progress in my program. Suppose the program is processing a very big file and is iterating the file's bytes using a for loop. The processing takes several minutes and I want a progress percentage be printed every 2 seconds in this manner: Progress: 0.40% Progress: 3.20% Progress: 5.73% Is it a good idea to std.concurrency.spawn a new thread and pass to it cast(float)i * 100 / fileSize somehow? If not, what's a better way to do this? This example code shows my situation: MmFile input = new MmFile(/* ... */); ulong fileSize= input.length; for (ulong i = 0; i < fileSize; ++i) { // ... } Thanks in advance.
Re: Converting Lua source to D
On Thursday, 5 March 2020 at 07:44:21 UTC, Jesse Phillips wrote: I am making an attempt convert Lua to D. This is less about the conversion and more about exploring the tooling to make it happen. I have chosen to do this file by file and attempting to start with linint. I wanted to make use of dpp, however I hit a segmentation fault and reduced dependency. https://github.com/JesseKPhillips/lua/blob/dpp/init/linit.d I wasn't able to get a core dump for debugging. Anyone willing to give some advice or solution? I have gone through a number of compilers and better. I have implemented a build pipeline but didn't incorporate the D portion at this time. I am only guessing, but I think the problem is line 87. Arrays and slices in D contain a length field and thus do not need to be null terminated. The foreach at line 96 iterates on all valid indices and thus in the last iteration you call luaL_requiref(L, null, null, 1). Try changing static const luaL_Reg[] loadedlibs = [ ... {LUA_DBLIBNAME, &luaopen_debug}, {null, null} ]; to static const luaL_Reg[] loadedlibs = [ ... {LUA_DBLIBNAME, &luaopen_debug} ];
Re: How to sum multidimensional arrays?
On Saturday, 29 February 2020 at 19:04:12 UTC, p.shkadzko wrote: On Friday, 28 February 2020 at 16:51:10 UTC, AB wrote: On Thursday, 27 February 2020 at 14:15:26 UTC, p.shkadzko wrote: [...] Your Example with a minimal 2D array. module test2; import std.random : Xorshift, unpredictableSeed, uniform; import std.range : generate, take, chunks; import std.array : array; import std.stdio : writeln; struct Matrix(T) { int rows; T[] data; alias data this; int cols() {return cast(int) data.length/rows;} this(int r, int c) { data=new int[r*c]; rows=r;} this(int r, int c, T[] d) {assert(r*c==data.length); data=d; rows=r; } auto opIndex(int r, int c) {return data[rows*c+r];} } Can you please explain what is the purpose of "alias data this" in your Matrix struct? As I remember "alias this" is used for implicit type conversions but I don't see where "data" is converted. Without "alias data this" the call c[] = m1[] + m2[]; should be written as c.data[] = m1.data[] + m2.data[]; With "alias data this" if some members of Matrix are not defined, but they are available for Matrix.data, the members of Matrix.data will be used. It is more about names lookup rules than type conversions.
Re: How to sum multidimensional arrays?
On Thursday, 27 February 2020 at 14:15:26 UTC, p.shkadzko wrote: I'd like to sum 2D arrays. Let's create 2 random 2D arrays and sum them. ``` import std.random : Xorshift, unpredictableSeed, uniform; import std.range : generate, take, chunks; import std.array : array; static T[][] rndMatrix(T)(T max, in int rows, in int cols) { Xorshift rnd; rnd.seed(unpredictableSeed); const amount = rows * cols; return generate(() => uniform(0, max, rnd)).take(amount).array.chunks(cols).array; } void main() { int[][] m1 = rndMatrix(10, 2, 3); int[][] m2 = rndMatrix(10, 2, 3); auto c = m1[] + m2[]; } ``` Maybe this is already clear, but it is important to highlight that 2D arrays and arrays of arrays are two different things. int[][] is an array of arrays, for each outer index the element is an array that has its own allocated memory and length. 2D arrays are not provided by the language, but can be implemented by defining a type with the required operator overloads. Using an array of arrays for a 1x1 matrix requires 10001 allocations while a dedicated 2D array implementation needs only 1; Example of an array of arrays where the inner arrays have different lengths: module test; void main() { import std.stdio; int[][] a; a.length=3; a[0]=[1,2,3]; a[1]=[3,4]; a[2]=[]; writeln(a); } Your Example with a minimal 2D array. module test2; import std.random : Xorshift, unpredictableSeed, uniform; import std.range : generate, take, chunks; import std.array : array; import std.stdio : writeln; struct Matrix(T) { int rows; T[] data; alias data this; int cols() {return cast(int) data.length/rows;} this(int r, int c) { data=new int[r*c]; rows=r;} this(int r, int c, T[] d) {assert(r*c==data.length); data=d; rows=r; } auto opIndex(int r, int c) {return data[rows*c+r];} } auto rndMatrix(T)(T max, in int rows, in int cols) { Xorshift rnd; rnd.seed(unpredictableSeed); const amount = rows * cols; return Matrix!T(rows,cols,generate(() => uniform(0, max, rnd)).take(amount).array); } void main() { auto m1 = rndMatrix(10, 2, 3); auto m2 = rndMatrix(10, 2, 3); auto c = Matrix!int(2,3); c[] = m1[] + m2[]; writeln(m1[1,2]); writeln(m2[1,2]); writeln(c[1,2]); } See https://dlang.org/spec/operatoroverloading.html#array-ops for a better overview of the required operators or mir.ndslice for an nD implementation.