Re: mixin template can't contain statements: workaround?
On Sun, 15 Mar 2015 13:28:33 +, ketmar wrote: template Foo(int a, string b) { import std.format : format; enum Foo = q{ { import std.conv : to; return %2$s+to!string(%1$s); } }.format(a, b.stringof); } positional args, syntax highlighting, usage like `mixin(Foo!(42, z));`. maybe this will help. ah, that `+`... ;-) signature.asc Description: PGP signature
Re: mixin template can't contain statements: workaround?
On Sat, 14 Mar 2015 18:20:47 -0700, Timothee Cour via Digitalmars-d-learn wrote: Why can't we allow mixin templates to contain statements, as is the case for regular mixins? Is there a workaround? here's a dummy example: template mixin Foo{ //some statement, eg: 'return;' } void fun(){ mixin Foo; } Note that I can do this with a regular mixin, but template mixins are cleaner (esp in more complex examples). template Foo(int a, string b) { import std.format : format; enum Foo = q{ { import std.conv : to; return %2$s+to!string(%1$s); } }.format(a, b.stringof); } positional args, syntax highlighting, usage like `mixin(Foo!(42, z));`. maybe this will help. signature.asc Description: PGP signature
Re: Using std.format required std.string?
On Sunday, 15 March 2015 at 15:48:34 UTC, Robert M. Münch wrote: Hi, wondering why this happens: import std.format; void ods(T...)(auto ref T args){ format(args).ptr; return; } ods(%s @ %s, mystring, mystring.ptr); Error: undefined identifier format If I add: import std.string; everything compiles and works. Since the docs of std.format contains all the format specifier description etc. I would expect that only including std.format should be enough. For whatever reasons, format() used to be defined in std.string. Indeed it's unintuitive to have it there, and it also pulls in lots of other unrelated things like Unicode tables when you import std.string. That's why it was moved into std.format in this PR: https://github.com/D-Programming-Language/phobos/pull/2732 It will be available in 2.067, soon to be released.
Re: Garbage collector returning pointers
On 2015-03-14 20:45:21 +, Marc Schütz said: As long as the pointer remains on the stack or in a register, the GC will keep the allocation alive. Hi Marc, ok, got it. Thanks. But if your C code stores the pointer on the C heap or in a global, the GC won't know anything about it and can free it. Ok. I need to dig into how the interpreter handles the returned pointer and how the stack is handled. -- Robert M. Münch http://www.saphirion.com smarter | better | faster
Using std.format required std.string?
Hi, wondering why this happens: import std.format; void ods(T...)(auto ref T args){ format(args).ptr; return; } ods(%s @ %s, mystring, mystring.ptr); Error: undefined identifier format If I add: import std.string; everything compiles and works. Since the docs of std.format contains all the format specifier description etc. I would expect that only including std.format should be enough. -- Robert M. Münch http://www.saphirion.com smarter | better | faster
Testing implicit conversion to template instance with is() expression
Should this work? struct V(string s) { } struct S(int U) { V!xyz x; alias x this; } void main() { S!10 a; static assert(is(a : V!Args, Args...)); } With DMD Git master, the static assert() fails. Should it? Am I doing something wrong? How can I test whether something is implicitly convertible to any instance of a particular template?
Re: Garbage collector returning pointers
On Sunday, 15 March 2015 at 15:08:43 UTC, Robert M. Münch wrote: On 2015-03-14 20:45:21 +, Marc Schütz said: As long as the pointer remains on the stack or in a register, the GC will keep the allocation alive. Hi Marc, ok, got it. Thanks. But if your C code stores the pointer on the C heap or in a global, the GC won't know anything about it and can free it. Ok. I need to dig into how the interpreter handles the returned pointer and how the stack is handled. C usually uses manual memory management, therefore I would expect that the interpreter actually documents whom the pointer belongs to, and who is responsible for cleaning it up. If the interpreter takes ownership, you should just allocate the data with malloc(), and the interpreter will then call free() on it when it doesn't need it any longer. Not sure whether .dup is compatible with that, maybe you'd need to write a small helper that copies things to the C heap. Otherwise, maybe the interpreter will call you back when it wants to free the memory. In both cases, you don't need to use GC pointers at all, because it's actually doing manual memory management.
Re: Dlang seems like java now,but why not let d more like C# Style?
On Sunday, 15 March 2015 at 00:56:24 UTC, Ellery Newcomer wrote: On Saturday, 14 March 2015 at 23:57:33 UTC, weaselcat wrote: On Saturday, 14 March 2015 at 23:46:28 UTC, Ellery Newcomer wrote: And C# has LINQ, which when combined with the last point is fricken awesome. what does LINQ offer that UFCS-style functional programming does not? LINQ basically is a UFCS-style api. AST reflection is what makes it nice. consider: X.Where(x = x.Members.Count() == x.Admins.Count()) straightforward in both D and C# when X is an array or container type. When X is a table in a database, things get tricky for D. C# can interpret the lambda as an ExpressionFunc (an AST type), so the implementation of X can reflect over the body of the lambda and use it to generate the appropriate SQL. ORMs such as entity framework and nhibernate do this now. Even if we can't get the lambdas as syntax tress, the fact that we can send whatever types we want to the delegates and overload operators and stuff means we can still convert the lambdas into SQL. Here is a very crude, very basic example: http://dpaste.dzfl.pl/94d851d7ca63. An enterprise implementation will be much bigger and much more complicated - but so is the C# implementation. At any rate, I really don't like what C# did with LINQ-to-SQL. The whole special-syntax to functional-style to syntax-tree to SQL is too overcomplicated - a simply lisp-style macro system(like what they have in Scala or Rust) could have done the trick in a simpler and faster way.
Re: Formatting floats and ints
On Sunday, 15 March 2015 at 15:41:09 UTC, Darts wrote: Hey, I'm just looking for how to turn some numbers into strings in particualr ways. Specifically, I want to force some ints (and maybe floats too) to give me a string that consists of exactly four numbers ( 3005, 0038, 0130, etc ). I'd also like to know how to format a float to give me only one decimal place. If there are ways to print out in hex or scientific notation I'd also like to know about those too! import std.stdio; int x = 42; writefln(int: %04d, x); float f = 3.14159; writefln(float: %.1f, f); writefln(hex: 0x%08x, x); If you need to work with the string instead of printing it, use format(): import std.string : format; // in not-yet released DMD 2.067 // import std.format : format; // is also possible string s = format(%04d, 42); Here's the explanation of the format strings: http://dlang.org/phobos/std_format.html Unfortunately the layout is broken at the moment. Anyway, if you're unfamiliar with format strings, it may be better to read one of the existing format string tutorials. Randomly picked one of the Google results: http://www.cprogramming.com/tutorial/printf-format-strings.html This one is about C's printf() function, but it's applicable to D, too, because format strings are almost identical in both languages.
Formatting floats and ints
Hey, I'm just looking for how to turn some numbers into strings in particualr ways. Specifically, I want to force some ints (and maybe floats too) to give me a string that consists of exactly four numbers ( 3005, 0038, 0130, etc ). I'd also like to know how to format a float to give me only one decimal place. If there are ways to print out in hex or scientific notation I'd also like to know about those too! Sorry if this is a dumb question, I've been looking through the documentation but I don't know which words apply to this kind of thing so I'm just not sure if I'm meant to be looking for conversion, casting, parsing, formatting, trunicating, or something else .__.; Also is there a way to tell google that I never mean golang when I write dlang in a search? I'm this close to trying Bing just to see if it lets me look for D related stuff without giving me Go related stuff.
Re: Dlang seems like java now,but why not let d more like C# Style?
On Saturday, 14 March 2015 at 09:59:05 UTC, dnewer wrote: yes,java is good lang,but i dont think it's better than c#,if no oracle or google support java will less and less. C# is a good and easy lang. i like C# . but,C# cant compiled to native code. So far, I have been searching for a language, like c # write efficiency, but more secure than that of c #, more efficient (runs), stronger (system-level, driving level) More like C#? How? Convert all names to PascalCase?
Re: OutputDebugString()
On 2015-03-14 22:55:57 +, Jonathan M Davis via Digitalmars-d-learn said: In case you didn't know, if you're not running the program in visual studio, you should see the output in in DebugView: https://technet.microsoft.com/en-us/library/bb896647.aspx Hi, yes I know, nevertheless thanks for letting me know. The problem was, that I needed the newest version for Win-10 and than it worked again. DebugView is really a great tool, especially if you want to debug DLLs. -- Robert M. Münch http://www.saphirion.com smarter | better | faster
Re: Using std.format required std.string?
On 2015-03-15 17:36:24 +, Robert M. Münch said: Is there a way to use version(...) to have code sections depending on compiler version? Something like: version(dmd = 2.067) or version(dmd 2.067)? Answerting myself: static if (__traits(compiles, version_minor 67)) import std.string; // format() for versions 2.0.67 else import std.format; // format() for versions = 2.0.67 -- Robert M. Münch http://www.saphirion.com smarter | better | faster
What is: Orphan format arguments: args[0..1]
What is: Orphan format arguments: args[0..1] It appears to come from within unittest at the line: strings={0}.format(cast(int)d2[i]); d2 is: ubyted2[]; It should be 512 bytes long, but that hasn't been checked at the point of the error. The compilation used was: rdmd --main -unittest -Dddocs blockf.d (but dmd gave the same error on a slightly mover complex version) The compiler was: DMD64 D Compiler v2.066.1 Copyright (c) 1999-2014 by Digital Mars written by Walter Bright and the system was debian testing Linux.
Re: Using std.format required std.string?
On Sunday, 15 March 2015 at 18:03:55 UTC, Robert M. Münch wrote: On 2015-03-15 17:36:24 +, Robert M. Münch said: Is there a way to use version(...) to have code sections depending on compiler version? Something like: version(dmd = 2.067) or version(dmd 2.067)? Answerting myself: static if (__traits(compiles, version_minor 67)) import std.string; // format() for versions 2.0.67 else import std.format; // format() for versions = 2.0.67 That doesn't do what you want. You need to `import std.compiler;` for version_minor. Without that import, `__traits(compiles, version_minor 67)` is always false, because version_minor is undefined. And if you add the import, `__traits(compiles, version_minor 67)` is always true, no matter the value of version_minor. Use `static if(version_minor 67)` instead. Also, if you check version_minor, it's probably a good idea to check (or static assert) version_major, too. Finally, there's need for this (yet). `std.string.format` is fine with 2.067, too. So unless you're going for (far) future compatiblity, you can just do `import std.string;`.
Re: Testing implicit conversion to template instance with is() expression
On 03/15/2015 08:47 AM, Marc =?UTF-8?B?U2Now7x0eiI=?= schue...@gmx.net wrote: Should this work? struct V(string s) { } struct S(int U) { V!xyz x; alias x this; } void main() { S!10 a; static assert(is(a : V!Args, Args...)); } With DMD Git master, the static assert() fails. Should it? Am I doing something wrong? How can I test whether something is implicitly convertible to any instance of a particular template? There is no way other than checking for compile-time duck typing (see the implementations of isInputRange and others). One reason is that the compiler does not have the concept of an instance of a template. Templates are for code generation and only the end-result (i.e. S!10) lives as a concept when compiling. Ali
Re: Testing implicit conversion to template instance with is() expression
On Sunday, 15 March 2015 at 16:44:14 UTC, Ali Çehreli wrote: On 03/15/2015 08:47 AM, Marc =?UTF-8?B?U2Now7x0eiI=?= schue...@gmx.net wrote: Should this work? struct V(string s) { } struct S(int U) { V!xyz x; alias x this; } void main() { S!10 a; static assert(is(a : V!Args, Args...)); } With DMD Git master, the static assert() fails. Should it? Am I doing something wrong? How can I test whether something is implicitly convertible to any instance of a particular template? There is no way other than checking for compile-time duck typing (see the implementations of isInputRange and others). One reason is that the compiler does not have the concept of an instance of a template. Templates are for code generation and only the end-result (i.e. S!10) lives as a concept when compiling. The code contained a small mistake, I forgot a `typeof()`: // static assert(is(a : V!Args, Args...)); // should be: static assert(is(typeof(a) : V!Args, Args...)); This still fails, but it works when I change it to: static assert(is(typeof(a) : S!Args, Args...)); This means I can indeed test whether something _is_ an instance of a template. It just doesn't take the `alias this` into account. So I guess that's a bug?
Re: Testing implicit conversion to template instance with is() expression
https://issues.dlang.org/show_bug.cgi?id=14286 In the meantime, does someone know of a suitable workaround?
Re: Dlang seems like java now,but why not let d more like C# Style?
On Sunday, 15 March 2015 at 14:58:54 UTC, Idan Arye wrote: On Sunday, 15 March 2015 at 00:56:24 UTC, Ellery Newcomer wrote: On Saturday, 14 March 2015 at 23:57:33 UTC, weaselcat wrote: On Saturday, 14 March 2015 at 23:46:28 UTC, Ellery Newcomer wrote: And C# has LINQ, which when combined with the last point is fricken awesome. what does LINQ offer that UFCS-style functional programming does not? LINQ basically is a UFCS-style api. AST reflection is what makes it nice. consider: X.Where(x = x.Members.Count() == x.Admins.Count()) straightforward in both D and C# when X is an array or container type. When X is a table in a database, things get tricky for D. C# can interpret the lambda as an ExpressionFunc (an AST type), so the implementation of X can reflect over the body of the lambda and use it to generate the appropriate SQL. ORMs such as entity framework and nhibernate do this now. Even if we can't get the lambdas as syntax tress, the fact that we can send whatever types we want to the delegates and overload operators and stuff means we can still convert the lambdas into SQL. Here is a very crude, very basic example: http://dpaste.dzfl.pl/94d851d7ca63. An enterprise implementation will be much bigger and much more complicated - but so is the C# implementation. At any rate, I really don't like what C# did with LINQ-to-SQL. The whole special-syntax to functional-style to syntax-tree to SQL is too overcomplicated - a simply lisp-style macro system(like what they have in Scala or Rust) could have done the trick in a simpler and faster way. i dont think linq is good.(its make C# bloated, huge, slow!) i think just class library structure,and class library IntelliSense! Take its essence to the dregs! D language has its own characteristics, such as the lower.Should be maintained and developed.
Re: Testing implicit conversion to template instance with is() expression
On Sunday, 15 March 2015 at 16:53:34 UTC, Marc Schütz wrote: On Sunday, 15 March 2015 at 16:44:14 UTC, Ali Çehreli wrote: On 03/15/2015 08:47 AM, Marc =?UTF-8?B?U2Now7x0eiI=?= schue...@gmx.net wrote: Should this work? struct V(string s) { } struct S(int U) { V!xyz x; alias x this; } void main() { S!10 a; static assert(is(a : V!Args, Args...)); } With DMD Git master, the static assert() fails. Should it? Am I doing something wrong? How can I test whether something is implicitly convertible to any instance of a particular template? There is no way other than checking for compile-time duck typing (see the implementations of isInputRange and others). One reason is that the compiler does not have the concept of an instance of a template. Templates are for code generation and only the end-result (i.e. S!10) lives as a concept when compiling. The code contained a small mistake, I forgot a `typeof()`: // static assert(is(a : V!Args, Args...)); // should be: static assert(is(typeof(a) : V!Args, Args...)); This still fails, but it works when I change it to: static assert(is(typeof(a) : S!Args, Args...)); This means I can indeed test whether something _is_ an instance of a template. It just doesn't take the `alias this` into account. So I guess that's a bug? Ok, now I'm pretty sure: class V(string s) { } class S(int U) : V!xyz { } void main() { S!10 a; static if(is(typeof(a) : V!Args, Args...)) pragma(msg, Args); } This works, and it even correctly infers `Args` to be `tuple(xyz)`. As `alias this` is supposed to be interchangeable with subtyping, it must be a bug.
Re: Testing implicit conversion to template instance with is() expression
On Sunday, 15 March 2015 at 18:53:33 UTC, Nicolas Sicard wrote: Can be reduced to: struct Foo(int i) {} alias Foo1 = Foo!1; static assert(is(Foo!2 == Foo1!T, T...)); // OK I think it's another bug. Right, I've filed another report: https://issues.dlang.org/show_bug.cgi?id=14290
Re: Formatting floats and ints
Thanks! That works perfectly! ;) I'll remember they're called Format Strings now. Tangentially related follow up: if I want to cast a string to a dstring... what are the rules for that? I'm getting an object.Error@(0): array cast misalignment message when my program crashes tring to convert a string to a dstring...
Re: Using std.format required std.string?
On 2015-03-15 16:22:03 +, Marc Schütz said: For whatever reasons, format() used to be defined in std.string. Indeed it's unintuitive to have it there, and it also pulls in lots of other unrelated things like Unicode tables when you import std.string. That's why it was moved into std.format in this PR: https://github.com/D-Programming-Language/phobos/pull/2732 It will be available in 2.067, soon to be released. Ok, good to here. Didn't cath/remember this one. Is there a way to use version(...) to have code sections depending on compiler version? Something like: version(dmd = 2.067) or version(dmd 2.067)? -- Robert M. Münch http://www.saphirion.com smarter | better | faster
Re: Dlang seems like java now,but why not let d more like C# Style?
On Saturday, 14 March 2015 at 09:59:05 UTC, dnewer wrote: yes,java is good lang,but i dont think it's better than c#,if no oracle or google support java will less and less. C# is a good and easy lang. i like C# . Not sure what do you mean. D has classes, interfaces and foreach, that should be enough to make a C#.
Re: Formatting floats and ints
On Sunday, 15 March 2015 at 18:52:29 UTC, Marc Schütz wrote: On Sunday, 15 March 2015 at 17:11:07 UTC, Darts wrote: Thanks! That works perfectly! ;) I'll remember they're called Format Strings now. Tangentially related follow up: if I want to cast a string to a dstring... what are the rules for that? I'm getting an object.Error@(0): array cast misalignment message when my program crashes tring to convert a string to a dstring... Casting in this case means reinterpreting the bytes of the `string` as if it were a `dstring`. For this to work, the string would have to start at an address and have and address divisible by 4, which it evidently doesn't. Anyway, what you want is: import std.conv : to; string a = Hello, world!; dstring b = a.to!dstring; Addendum: In general, prefer std.conv.to over casts. They're supposed to be a low-level operation and can be dangerous if pointers or other reference types are involved. std.conv.to is more powerful (e.g. it can convert strings to ints, i.e. 42 = 42), and it also checks for overflow.
Re: Testing implicit conversion to template instance with is() expression
On Sunday, 15 March 2015 at 17:03:42 UTC, Marc Schütz wrote: https://issues.dlang.org/show_bug.cgi?id=14286 In the meantime, does someone know of a suitable workaround? I found the following workaround. Not beautiful, but it works: enum isValue(alias T) = __traits(compiles, typeof(T)); template isConvertibleToInstanceOf(alias From, alias To) if(isValue!From) { enum isConvertibleToInstanceOf = isConvertibleToInstanceOf!(typeof(From), To); } template isConvertibleToInstanceOf(From, alias To) if(!is(From == struct) !is(From == class) !is(From == interface)) { enum isConvertibleToInstanceOf = false; } template isConvertibleToInstanceOf(From, alias To) if(is(From == struct) || is(From == class) || is(From == interface)) { // workaround for https://issues.dlang.org/show_bug.cgi?id=14286 import std.typetuple : anySatisfy; enum aliasThisConvertible(string name) = isConvertibleToInstanceOf!(mixin(typeof(From. ~ name ~ )), To); enum isConvertibleToInstanceOf = anySatisfy!(aliasThisConvertible, __traits(getAliasThis, From)) || is(From : To!Args, Args...); }
Re: Dlang seems like java now,but why not let d more like C# Style?
On Sunday, 15 March 2015 at 14:58:54 UTC, Idan Arye wrote: Here is a very crude, very basic example: http://dpaste.dzfl.pl/94d851d7ca63. U++ approach will probably give more succinct result. Not sure how it fares against D philosophy: does it replace range primitives with whole new thing?
Re: Testing implicit conversion to template instance with is() expression
On Sunday, 15 March 2015 at 18:33:32 UTC, Marc Schütz wrote: On Sunday, 15 March 2015 at 17:03:42 UTC, Marc Schütz wrote: https://issues.dlang.org/show_bug.cgi?id=14286 In the meantime, does someone know of a suitable workaround? I found the following workaround. Not beautiful, but it works: enum isValue(alias T) = __traits(compiles, typeof(T)); template isConvertibleToInstanceOf(alias From, alias To) if(isValue!From) { enum isConvertibleToInstanceOf = isConvertibleToInstanceOf!(typeof(From), To); } template isConvertibleToInstanceOf(From, alias To) if(!is(From == struct) !is(From == class) !is(From == interface)) { enum isConvertibleToInstanceOf = false; } template isConvertibleToInstanceOf(From, alias To) if(is(From == struct) || is(From == class) || is(From == interface)) { // workaround for https://issues.dlang.org/show_bug.cgi?id=14286 import std.typetuple : anySatisfy; enum aliasThisConvertible(string name) = isConvertibleToInstanceOf!(mixin(typeof(From. ~ name ~ )), To); enum isConvertibleToInstanceOf = anySatisfy!(aliasThisConvertible, __traits(getAliasThis, From)) || is(From : To!Args, Args...); } It works for your previous code example: static assert(isConvertibleToInstanceOf!(S!10, V)); // OK But this also works: static assert(!isConvertibleToInstanceOf!(S!10, V!abc)); // OK Can be reduced to: struct Foo(int i) {} alias Foo1 = Foo!1; static assert(is(Foo!2 == Foo1!T, T...)); // OK I think it's another bug.
Re: Formatting floats and ints
On Sunday, 15 March 2015 at 17:11:07 UTC, Darts wrote: Thanks! That works perfectly! ;) I'll remember they're called Format Strings now. Tangentially related follow up: if I want to cast a string to a dstring... what are the rules for that? I'm getting an object.Error@(0): array cast misalignment message when my program crashes tring to convert a string to a dstring... Casting in this case means reinterpreting the bytes of the `string` as if it were a `dstring`. For this to work, the string would have to start at an address and have and address divisible by 4, which it evidently doesn't. Anyway, what you want is: import std.conv : to; string a = Hello, world!; dstring b = a.to!dstring;
Re: What is: Orphan format arguments: args[0..1]
On Sunday, 15 March 2015 at 18:46:52 UTC, Charles Hixson wrote: What is: Orphan format arguments: args[0..1] It appears to come from within unittest at the line: strings={0}.format(cast(int)d2[i]); It means you gave `format` more arguments than placeholders. `format` uses C style % placeholders, not the brace syntax like C#(?). So make that: strings=%s.format(cast(int)d2[i]); By the way, I don't see a need for the cast.
What is the best practice of organization multi-threading ?
I have App that read config sections. If the section is true I want to run it in new thread. if (parseconfig.obsmpplots_load == true) { auto obsmpplots = new ObsmpPlots(db); auto theTask = task(obsmpplots.getPlots); theTask.executeInNewThread(); } if(parseconfig.nadisa_load == true) { auto nadisa = new Nadisa(db); auto theTask = task(nadisa.getPlots); theTask.executeInNewThread(); } It's seems work, but I do not sure that I doing it's right.
Re: get from tuple by type
On Sunday, 15 March 2015 at 23:13:58 UTC, Charles Cooper wrote: And yes, I could use names. But then you are subject to name clashes and using strings instead of types as member identifiers is more prone to error anyways. Ever gotten this wrong before -- void CRITICAL_TO_GET_THIS_RIGHT(uint cents, uint dollars); alias params_t = Tuple!(uint, dollars, uint, cents); params_t params; params.dollars = 0; params.cents = 99; CRITICAL_TO_GET_THIS_RIGHT(params.expand); // compilation succeeds, bank fails. How would GetByType help here? Both members are uint, so you can't distinguish them by type. And if you gave them distinct types, the bad example here wouldn't compile anymore either.
Re: struct / cast / ? design problem
On Sun, 15 Mar 2015 16:34:14 -0700, Charles Hixson via Digitalmars-d-learn wrote: if you know the exact layouts of `spare`, you can use union for that: struct S { // ... union { ulong[61] spare; struct { int vala; ubyte valb; } // etc. } } and then you can use it like this: auto s = S(); s.vala = 42; assert(s.spare[0] == 42); you can also write a CTFE function that builds struct to cast where `spare` is changed to something else, using `S` as a source, but this solution will not be pretty. ;-) signature.asc Description: PGP signature
Re: get from tuple by type
On Sunday, 15 March 2015 at 21:59:18 UTC, Charles Cooper wrote: C++14 has: templateclass T, class... Types constexpr T get(tupleTypes... t); Which allows you to get a member of the tuple struct by type. Is there an idiomatic / library way to do this in D? Preferably by indexing. I don't think there is. I don't know if there should be. Distinguishing tuple fields by their type doesn't seem very useful to me, since multiple fields can have the same type. Here is what I have, it is ugly but works: /* CODE */ static import std.stdio; static import std.typecons; template GetByType(alias tuple_instance, member_t) { ref member_t GetByType() nothrow @nogc @safe { alias tuple_t = typeof(tuple_instance); static assert(std.typecons.isTuple!tuple_t); enum long idx = std.typetuple.staticIndexOf!(member_t, tuple_instance.Types); static if(-1 != idx) return tuple_instance[idx]; else static assert(false); //better error message } } static assert(2.5 == GetByType!(std.typecons.tuple(1,2.5), double)); static assert(2.5 == GetByType!(std.typecons.tuple(1,2.5,3.1), double)); void main() { auto foo = std.typecons.tuple(1,2.5); std.stdio.writeln(GetByType!(foo, double)); } /* CODE */ Is there a better way to do this? I went over it (some notes below): import std.typecons: Tuple; auto ref inout(T) getFirst(T, Types ...)(auto ref inout(Tuple!Types) t) { import std.typetuple: staticIndexOf; enum idx = staticIndexOf!(T, Types); static if(-1 != idx) return t[idx]; else static assert(false); //better error message } unittest { import std.typecons: tuple; assert(2.5 == tuple(1, 2.5).getFirst!double); assert(2.5 == tuple(1, 2.5, 3.1).getFirst!double); static assert(2.5 == tuple(1, 2.5).getFirst!double); // CTFE static assert(!__traits(compiles, tuple(1, 2.5).getFirst!string)); // lvalue tuple = lvalue result auto m = tuple(1, 2.5); m.getFirst!double = 2.1; assert(m[1] == 2.1); // rvalue tuple = rvalue result static assert(!__traits(compiles, tuple(1, 2.5).getFirst!double)); // immutable/const immutable i = tuple(1, 2.5); assert(2.5 == i.getFirst!double); const c = tuple(1, 2.5); assert(2.5 == c.getFirst!double); } void main() { import std.stdio: writeln; import std.typecons: tuple; auto foo = tuple(1, 2.5); writeln(foo.getFirst!double); } Using combined syntax for function template. Made the tuple a function parameter like in the C++ version. I don't see the point in having it a template alias parameter. Dropped `nothrow @nogc @safe`, since copying the member might not be any of that. They are inferred when possible. Employing inout and `auto ref`. More tests. unittest block instead of `static assert`s. Bikeshedding: Changed name to getFirst, since subsequent values of the same type are ignored. Named things more like the C++ version: member_t - T, tuple_instance - t. Use selective imports instead of static imports. Use more common casing: types and type templates are PascalCased, everything else is camelCased. Brace placement.
Re: get from tuple by type
foo[1] is sometimes better, but not always. One has to go back to the definition of the thing and literally calculate by hand which element of the tuple you want, and then try compiling it, and so forth. Although the type system will guarantee that you eventually get it right it is a waste of time. void external_api1_react_to_event(meters_t, time_t); void external_api2_react_to_event(time_t, meters_t); alias event_t = Tuple!(time_t, meters_t) // .. some time later.. external_api1_react_to_event(event_t.get(meters_t), event_t.get(time_t)); Yes, I could say external_api1_react_to_event(event_t[1], event_t[0]) .. but that is barbaric. It's a productivity sink because I have to go back to the original definition, align the arguments, and then context switch back to whatever I was working on before. And yes, I could use names. But then you are subject to name clashes and using strings instead of types as member identifiers is more prone to error anyways. Ever gotten this wrong before -- void CRITICAL_TO_GET_THIS_RIGHT(uint cents, uint dollars); alias params_t = Tuple!(uint, dollars, uint, cents); params_t params; params.dollars = 0; params.cents = 99; CRITICAL_TO_GET_THIS_RIGHT(params.expand); // compilation succeeds, bank fails. In conclusion: this is an important feature because it allows you to enforce type safety when working with tuples (e.g. in function parameters) efficiently, without taking too much of the programmer's time. On Sunday, 15 March 2015 at 22:32:48 UTC, bearophile wrote: Charles Cooper: Is there a better way to do this? Can you show some use cases for this, and isn't foo[1] better? Bye, bearophile
struct / cast / ? design problem
I've got, say, a file header in a routine that looks like: structBlockHead { uintmagic=20150312;//block magic uintmagic2;//magic for use by the using routine uintblockSize; uintunused1; ulongunused2; ulongspare[61]; } The unused vars are intended to be reserved for future use. The spare vars are intended for use by another routine that uses the routines of the owner of BlockHead to deal with basic things. So it needs to define the data in spare. How? The only almost nice way I've thought of is with a struct pointer to spare, and calling that nice is a statement about how bad the other ways I've thought of are. (E.g., redefining spare as a ubyte vector and then casting the struct of the using program as a ubyte vector and copying it over.) I'm sure that there must be a better way, but I can't think of what it is. BlockHead needs to be a struct to allow the data to be written with a writeBlock. I don't want to use a buffered file because this needs random access. Perhaps I just shouldn't define spare, but then I wouldn't retrieve the data with the readBlock. So I'd double the number of disk accesses (to the BlockHead). One alternative is to have each using routine define it's own header struct, and to cast each BlockHead to the appropriate routine's own header type, but that begs for errors to creep in if any of the structs isn't the right length, of ever becomes modified to not be the correct length. Every way I've thought of looks like something that's just begging for errors to creep into the code, if not now then later...so *is* there a good way?
Re: get from tuple by type
Not offended at all :), in fact it was not even my suggestion that it be included in the standard. I was just knee jerk reacting to the comment that, just because something is simple to do precludes it from getting standardized On Sunday, 15 March 2015 at 23:28:18 UTC, ketmar wrote: sorry if you feel offended, i never meant that. what i meant is that it's hard in c++, but easy in D when one knows how to do that. i've learned D mostly by reading other people code, and there is nothing wrong in asking questions, quite the contrary. but the requested solution is not universal enough to be included in Phobos (what if i want an index instead of a value? or (index, value) tuple? or just check if it is there? or find either `int` or `double`?). it's easier to write specialized template for required cases than to try to make it generic (and complex) enough. but it's much harder to write that in c++, to the extent that it's easier to include that things in standard. just stay with us and you will see that D shines in such things (and in many other areas too ;-).
Re: get from tuple by type
Charles Cooper: Yes, I could say external_api1_react_to_event(event_t[1], event_t[0]) .. but that is barbaric. It's a productivity sink because I have to go back to the original definition, align the arguments, and then context switch back to whatever I was working on before. If you are experiencing those problems it's probably the way D/Phobos to tell you to not use basic tuples for your purpose. Use tuples with named fields (or even structs). Take also a look at Algebraic in std.variant. Bye, bearophile
get from tuple by type
C++14 has: templateclass T, class... Types constexpr T get(tupleTypes... t); Which allows you to get a member of the tuple struct by type. Is there an idiomatic / library way to do this in D? Preferably by indexing. Here is what I have, it is ugly but works: /* CODE */ static import std.stdio; static import std.typecons; template GetByType(alias tuple_instance, member_t) { ref member_t GetByType() nothrow @nogc @safe { alias tuple_t = typeof(tuple_instance); static assert(std.typecons.isTuple!tuple_t); enum long idx = std.typetuple.staticIndexOf!(member_t, tuple_instance.Types); static if(-1 != idx) return tuple_instance[idx]; else static assert(false); //better error message } } static assert(2.5 == GetByType!(std.typecons.tuple(1,2.5), double)); static assert(2.5 == GetByType!(std.typecons.tuple(1,2.5,3.1), double)); void main() { auto foo = std.typecons.tuple(1,2.5); std.stdio.writeln(GetByType!(foo, double)); } /* CODE */ Is there a better way to do this?
Re: get from tuple by type
On Sun, 15 Mar 2015 22:35:03 +, weaselcat wrote: Seems like a useful feature(useful enough to get past the C++ standards committee,) consider submitting a phobos PR? ah, c++ committee accepts by randomness. ;-) honestly, i can't see why it's useful and where it can be used. and it's so easy to write anyway, so i think that there is virtually no sense in adding something like this to Phobos. signature.asc Description: PGP signature
Re: get from tuple by type
p.s. to be clear: it's freaking hard to do metaprogramming and template functional programming in c++, that's why c++ committee accepts such things. and it's very easy to write such code in D, so this is a good excersise for newcomers and almost no-brainer for expirienced D user. signature.asc Description: PGP signature
Re: get from tuple by type
Thanks for the style recommendations. On Sunday, 15 March 2015 at 23:14:32 UTC, anonymous wrote: I don't think there is. I don't know if there should be. Distinguishing tuple fields by their type doesn't seem very useful to me, since multiple fields can have the same type. Using combined syntax for function template. Made the tuple a function parameter like in the C++ version. I don't see the point in having it a template alias parameter. Dropped `nothrow @nogc @safe`, since copying the member might not be any of that. They are inferred when possible. Employing inout and `auto ref`. More tests. unittest block instead of `static assert`s. Bikeshedding: Changed name to getFirst, since subsequent values of the same type are ignored. Named things more like the C++ version: member_t - T, tuple_instance - t. Use selective imports instead of static imports. Use more common casing: types and type templates are PascalCased, everything else is camelCased. Brace placement.
Re: get from tuple by type
Sure. It is also easy to write merge sort. Or std.typetuple.Erase. Or Tuple.opIndex(size_t). But that doesn't mean everybody does it. Some utilities (and I am not saying this is, but it could be) are widely used enough that it makes sense to put them in the standard. On Sunday, 15 March 2015 at 22:44:21 UTC, ketmar wrote: p.s. to be clear: it's freaking hard to do metaprogramming and template functional programming in c++, that's why c++ committee accepts such things. and it's very easy to write such code in D, so this is a good excersise for newcomers and almost no-brainer for expirienced D user.
Re: get from tuple by type
On Sun, 15 Mar 2015 23:30:48 +, Charles Cooper wrote: Not offended at all :), in fact it was not even my suggestion that it be included in the standard. I was just knee jerk reacting to the comment that, just because something is simple to do precludes it from getting standardized ah, i see. but this has disadvantages too: it's hard to remember everything the std has, and people will write simple things again and again just 'cause it is faster than trying to find the corresponding function in standard library. search is not of great help here too (unless search engine can read programmer's mind and understand what he really wants ;-). and i still can't see when this can be handy. i'm almost sure that there is a better way to do the thing programmer wants to achieve with such code. signature.asc Description: PGP signature
Re: get from tuple by type
http://dlang.org/phobos/std_variant.html#.Algebraic Thanks! This is fascinating, really a breath of fresh air coming from the C++ way of doing things. On Sunday, 15 March 2015 at 23:31:59 UTC, bearophile wrote: If you are experiencing those problems it's probably the way D/Phobos to tell you to not use basic tuples for your purpose. Use tuples with named fields (or even structs). Take also a look at Algebraic in std.variant. Bye, bearophile
Re: get from tuple by type
On Sun, 15 Mar 2015 21:59:16 +, Charles Cooper wrote: C++14 has: templateclass T, class... Types constexpr T get(tupleTypes... t); Which allows you to get a member of the tuple struct by type. Is there an idiomatic / library way to do this in D? Preferably by indexing. why indexing? functional programming is fun! import std.typecons : tuple; template GetByType(Type, Tuple...) { import std.typecons : isTuple; static if (Tuple.length == 0) static assert(false, Type.stringof~ not found); else static if (Tuple.length == 1 isTuple!(typeof(Tuple[0]))) enum GetByType = GetByType!(Type, Tuple[0].expand); else static if (is(typeof(Tuple[0]) == Type)) enum GetByType = Tuple[0]; else enum GetByType = GetByType!(Type, Tuple[1..$]); } static assert(2.5 == GetByType!(double, 1, 2.5)); static assert(2.5 == GetByType!(double, 1, 2.5, 3.1)); //static assert(2.5 == GetByType!(char, 1, 2.5, 3.1)); static assert(2.5 == GetByType!(double, std.typecons.tuple(1, 2.5))); static assert(2.5 == GetByType!(double, std.typecons.tuple(1,2.5,3.1))); signature.asc Description: PGP signature
Re: get from tuple by type
True. If I had to do something involving such an API I would first wrap the API with a type safe one before doing anything else. void external_api_do_something(uint dollars, uint cents); /* I think this could somehow be automated with staticMap and ParameterTypeTuple / ParameterIdentifierTuple */ alias dollars_t = Typedef!(uint, uint.init, dollars); alias cents_t = Typedef!(uint, uint.init, cents); void internal_api_do_something(dollars_t, cents_t); On Sunday, 15 March 2015 at 23:20:22 UTC, anonymous wrote: On Sunday, 15 March 2015 at 23:13:58 UTC, Charles Cooper wrote: How would GetByType help here? Both members are uint, so you can't distinguish them by type. And if you gave them distinct types, the bad example here wouldn't compile anymore either.
Re: get from tuple by type
On Sun, 15 Mar 2015 23:17:34 +, Charles Cooper wrote: Sure. It is also easy to write merge sort. Or std.typetuple.Erase. Or Tuple.opIndex(size_t). But that doesn't mean everybody does it. Some utilities (and I am not saying this is, but it could be) are widely used enough that it makes sense to put them in the standard. sorry if you feel offended, i never meant that. what i meant is that it's hard in c++, but easy in D when one knows how to do that. i've learned D mostly by reading other people code, and there is nothing wrong in asking questions, quite the contrary. but the requested solution is not universal enough to be included in Phobos (what if i want an index instead of a value? or (index, value) tuple? or just check if it is there? or find either `int` or `double`?). it's easier to write specialized template for required cases than to try to make it generic (and complex) enough. but it's much harder to write that in c++, to the extent that it's easier to include that things in standard. just stay with us and you will see that D shines in such things (and in many other areas too ;-). signature.asc Description: PGP signature
Re: Using std.format required std.string?
On Sunday, 15 March 2015 at 17:36:24 UTC, Robert M. Münch wrote: Ok, good to here. Didn't cath/remember this one. Is there a way to use version(...) to have code sections depending on compiler version? Something like: version(dmd = 2.067) or version(dmd 2.067)? static if( __VERSION__ = 2.067 ) { ... } This works with any D compiler using the DMD frontend.
Re: Using std.format required std.string?
On Monday, 16 March 2015 at 04:31:19 UTC, Mike Parker wrote: On Sunday, 15 March 2015 at 17:36:24 UTC, Robert M. Münch wrote: Ok, good to here. Didn't cath/remember this one. Is there a way to use version(...) to have code sections depending on compiler version? Something like: version(dmd = 2.067) or version(dmd 2.067)? static if( __VERSION__ = 2.067 ) { ... } Ugh. 2067, not 2.067.
exclude current directory from search path in dmd ?
Is there a way to exclude current directory from search path in dmd, so that the search path is only given by '-I' arguments (+ones from dmd.conf)? use case: files: /base/foo.d /base/bar/foo.d /base/bar/main.d #contains: import foo.d cd /base/bar dmd -I/base main.d = I want 'import foo.d' to point to /base/foo.d, not /base/bar/foo.d, but this is not the case since -I. is implicit in search path