Re: How far can CTFE go?
H. S. Teoh wrote: If this was code generated by an external utility I wasn't argumenting for using external utilities, but against the argument, that separating code for separatable phases would obfuscate the code. for more than one _needed_ phase compile-time validation of generated code The proof for more than one needed phase is missing and I doubt that there is one, because validation is part of checking contracts, which are not included in the `-release' compilation by definition. -manfred
Re: Pure Contract bug?
On 02/04/2012 08:51 PM, Era Scarecrow wrote: If I'm reading how pure works, my original example was likely broken as it was part of a struct that returned a state value (although the contract constraints meaning was still valid). So is pure fully usable or is it not yet ready? Makes me think that pure should have further constraints/limits, if it's part of a class/struct it should either require or automatically be static (no state access) and if it accesses any global variables, they must be immutable. int x; immutable int y = 10; pure int test(int z) { int t = z + x; //should error t += y; //fine, globally immutable. return t; } struct X { int s_x; static int s_st_x; immutable int s_y; static immutable int s_st_y = 100; pure int test(int z) { int t = x + z; //should error t += s_x; //error, mutable external state t += s_st_x; //error, mutable external state (static) t += s_y; //error, not statically immutable, mathematically impure. t += y; //fine, global immutable t += s_st_y; //fine, statically immutable. return t; } } Errors I get currently are these: test(int): Error: pure function 'test' cannot access mutable static data 'x' X.test(int): Error: pure function 'test' cannot access mutable static data 'x' Error: pure function 'test' cannot access mutable static data 's_st_x' If I understand pure correctly, I should get two more, for s_x and s_y. Pure does not imply const in D. If you want stronger guarantees, just turn 'test' into a const (or immutable) member function. In D, a function can change anything that is mutable and reachable through its parameters, this includes the implicit 'this' pointer. The reason for this design is simple: There is no need to be overly restrictive, because the additional restrictions are already trivially expressed in the type system. Furthermore, any mutation of a parameter can be turned into a less efficient protocol that only requires a const pure function, so there would be no gain if pure implied const, it would only make pure less useful. void foo(int* x)pure{*x+=2;} int bar(const(int)*x)pure{return *x+2;} void main() pure{ int x, y; foo(x); // those two lines have y = bar(y); // equivalent functionality! }
Re: Segment violation (was Re: Why I could not cast string to int?)
On 02/04/12 02:03, Timon Gehr wrote: On 02/03/2012 11:08 AM, Artur Skawina wrote: On 02/03/12 00:20, Jonathan M Davis wrote: in is pointless on value types. All it does is make the function parameter const, which really doesn't do much for you, and in some instances, is really annoying. Personally, I see no point in using in unless the parameter is a reference type, and even then, it's often a bad idea with reference types, because in is really const scope, and the scope is problematic if you want to return anything from that variable. It's particularly problematic with arrays, since it's frequently desirable to return slices of them, and scope (and therefore in) would prevent that. It's useful in some instances (particularly with delegates), but I'd use in _very_ sparingly. It's almost always more trouble than it's worth IMHO. BTW, scope should have been the default for *all* reference type function arguments, with an explicit modifier, say esc, required to let the thing escape. It's an all-or-nothing thing, just like immutable strings - not using it everywhere is painful, but once you switch everything over you get the benefits. I totally agree. Most function arguments are not escaped. However, it is nice that the shortest storage class, 'in', implies scope. There are currently two problems with using in: a) the one mentioned, where using in/scope means you can't (or shouldn't be able to) pass the thing to another function w/o scope marked args, and b) in implies const, which is a problem because you may want to reassign the argument - a perfectly safe thing to do. With const itself you can use parentheses to limit its scope to not include the reference itself; the problematic case is the builtin string alias, ie int f(in string s); would have to allow reassigning 's' inside the function. Semi-related quiz: immutable(char)[] a = a; const(char)[] b = b; auto aa = a ~ a; auto bb = b ~ b; auto ab = a ~ b; writeln(aa: , typeid(aa), bb: , typeid(bb), ab: , typeid(ab)); And the question is: How many people, who have not already been bitten by this, will give the correct answer to: What will this program print?? There should have been another class, in addition to immutable/const, say uniq. For cases where an expression results in new unique objects. This class implicitly converts to any of const/immutable and mutates to the new type. IOW string a = a; char[] b = b; auto c = a ~ b; // typeid(c) == (uniq(char)[]) string d = c; // Fine, c is unique and can be safely treated as a string. // But, from now on, c is (immutable(char)[]) so: char[] e = c; // Fails. // And the other way: auto f = a ~ b; char[] g = f; // OK string h = f // Fails, as f is now a (char[]) No need for unsafe-looking casts, just so that the compiler accepts perfectly safe code, like: string c = ab;, which would currently fail if used in the above quiz, and has to be written as string c = cast(string)ab;. [1] artur [1] Using a helper template is not different from adding a comment, it only serves to document /why/ the programmer had to something, which is only a workaround for a language/compiler limitation. Compiler because at least the simple cases could be silently fixed in a backward compatible way (by not disallowing safe conversions). Language because uniq would also be useful when the programmer knows it applies, but the compiler can't figure it out by itself.
Re: Struct inheritance
On Sat, 04 Feb 2012 15:04:50 +0100, Vidar Wahlberg cani...@exent.net wrote: This code does not compile: Bar.d:6: Error: function expected before (), not module Struct of type void Bar.d:6: Error: constructor Foo.Foo.this (Struct s) is not callable using argument types (_error_) Why is that? I see. There's a hint in the error message: function expected [...], not module. Struct is the name of a module, so the compiler thinks you want to access something inside it. If you want 'Struct' to refer to the type, you must use selective import[1]: import Struct : Struct; This says 'I want only the type Struct from the module Struct, not everything else in there.' The other solution is to simply use different names for the type and the module. It is. The problem is that bool opEquals(ref const Point) expects a Point by reference, and the return value from your property is a temporary, from which we can get no reference. The solution is to remove the ref: bool opEquals(const Point). The only reason to use ref here is to cut down on copying, and might be worthwhile on larger structures. I've tried removing the ref, but I get other errors in return then: Point.d:19: Error: function Point.Point.opEquals type signature should be const bool(ref const(Point)) not const bool(const const(Point) p) Coordinate.d:20: Error: function Coordinate.Coordinate.opEquals type signature should be const bool(ref const(Coordinate)) not const bool(const const(Coordinate) c) I cannot seem to recreate this error message. Which version of the compiler are you using? [1]: http://www.d-programming-language.org/module.html#ImportDeclaration
Re: Contracts vs debug
F i L: Why/where should I use contracts vs debug statements? This is a sting point: http://en.wikipedia.org/wiki/Design_by_contract Contract-based programming is a different way to write programs. But adding few more asserts here and there is useful still. int foo(int bar) { debug assert(bar != 0); Asserts go away with -release. So generally I don't need to write that. Bye, bearophile
Re: Contracts vs debug
Timon Gehr wrote: First of all, you don't really need the debug statements, assertions are stripped from -release'd code anyway. The assertions in the function body are not part of the function interface. (eventually, contracts can be on function declarations lacking a function body) Conceptually, with an assert in the function body, the bug would be inside the function: If it is not assumed in the in-contract it cannot be asserted that bar is != 0. Some code could just go ahead and call foo(0). If the assertion is in the in-contract, foo(0) is invalid. And in the in-contract, this is supposed to be visible for everyone. For a pragmatic reason, because contracts are supposed to be inherited (but due to a bug, in-contracts are not currently inherited without adding an in{assert(false);} contract to the overriding function, this bug does not break LSP though, it is just a little annoying) Contracts can also be used for modular static model checking/static error detection. You may want to have a look at the Eiffel and Spec# systems. All that makes sense. I forgot about Inheritance. Thank you for the explanation.
Re: Contracts vs debug
On Sat, 04 Feb 2012 18:18:22 +0100, F i L witte2...@gmail.com wrote: Why/where should I use contracts vs debug statements? Is it completely arbitrary? If so, I wonder if contracts syntax is even needed: int foo(int bar) in { assert(bar != 0); } body { return bar + 1; } The thing I like more about debug statements, is that I can put them anywhere in my code, testing parameters and locals in the same way. If for documentation is the only argument for contracts, I find that a bit weak. int foo(int bar) { debug assert(bar != 0); return bar + 1; } That is much cleaner syntax and just as easy to understand from a assertion-failure/documentation standpoint IMO. The idea is also that contracts will be inherited. A subclass may relax the 'in' contracts and strengthen the 'out' contracts. I am not sure if this currently works, but that is the idea.
Re: Contracts vs debug
On 02/04/2012 06:18 PM, F i L wrote: Why/where should I use contracts vs debug statements? Is it completely arbitrary? If so, I wonder if contracts syntax is even needed: int foo(int bar) in { assert(bar != 0); } body { return bar + 1; } The thing I like more about debug statements, is that I can put them anywhere in my code, testing parameters and locals in the same way. If for documentation is the only argument for contracts, I find that a bit weak. int foo(int bar) { debug assert(bar != 0); return bar + 1; } That is much cleaner syntax and just as easy to understand from a assertion-failure/documentation standpoint IMO. First of all, you don't really need the debug statements, assertions are stripped from -release'd code anyway. The assertions in the function body are not part of the function interface. (eventually, contracts can be on function declarations lacking a function body) Conceptually, with an assert in the function body, the bug would be inside the function: If it is not assumed in the in-contract it cannot be asserted that bar is != 0. Some code could just go ahead and call foo(0). If the assertion is in the in-contract, foo(0) is invalid. And in the in-contract, this is supposed to be visible for everyone. For a pragmatic reason, because contracts are supposed to be inherited (but due to a bug, in-contracts are not currently inherited without adding an in{assert(false);} contract to the overriding function, this bug does not break LSP though, it is just a little annoying) Contracts can also be used for modular static model checking/static error detection. You may want to have a look at the Eiffel and Spec# systems.
Re: Pure Contract bug?
If I'm reading how pure works, my original example was likely broken as it was part of a struct that returned a state value (although the contract constraints meaning was still valid). So is pure fully usable or is it not yet ready? Makes me think that pure should have further constraints/limits, if it's part of a class/struct it should either require or automatically be static (no state access) and if it accesses any global variables, they must be immutable. int x; immutable int y = 10; pure int test(int z) { int t = z + x; //should error t += y; //fine, globally immutable. return t; } struct X { int s_x; static int s_st_x; immutable int s_y; static immutable int s_st_y = 100; pure int test(int z) { int t = x + z; //should error t += s_x; //error, mutable external state t += s_st_x;//error, mutable external state (static) t += s_y; //error, not statically immutable, mathematically impure. t += y; //fine, global immutable t += s_st_y;//fine, statically immutable. return t; } } Errors I get currently are these: test(int): Error: pure function 'test' cannot access mutable static data 'x' X.test(int): Error: pure function 'test' cannot access mutable static data 'x' Error: pure function 'test' cannot access mutable static data 's_st_x' If I understand pure correctly, I should get two more, for s_x and s_y.
Re: Struct inheritance
So why not just use classes? I've understood it as there may be a performance gain by using structs over classes, and in my program Point and Coordinate are used heavily. The other big difference is value vs. reference type. You can use alias this to achieve something like struct inheritance.
Struct inheritance
Good day. I know inheritance is a misleading word as there's no such thing when it comes to structs, but I couldn't think of a better description for this problem: Let's say I got a struct for a location on a 2-dimensional plane: struct Point { int x; int y; } Further I also need to represent a location in a 3-dimensional space: struct Coordinate { int x; int y; int z; } If these were classes instead I could simply make Coordinate inherit from Point and only add int z;. This would also make the thing I'm trying to achieve much easier; Consider I have a method that does something nifty with x and y, I'd like this method to handle both Point and Coordinate, if they were classes it would be fairly simple: int somethingNifty(Point p) { return p.x + p.y; } So why not just use classes? I've understood it as there may be a performance gain by using structs over classes, and in my program Point and Coordinate are used heavily. Obviously I'm fairly new to both D and structs, I have plenty Java and some C++ experience (I've avoided using structs in C++) and I have The D Programming Language book by Andrei which I'm happy to look up in, although I've failed to find an answer to this question in the book, in this newsgroup and on the net. I would greatly appreciate if someone could give me a nudge the the right direction.
Re: Struct inheritance
On Sat, 04 Feb 2012 12:38:30 +0100, Vidar Wahlberg cani...@exent.net wrote: Good day. I know inheritance is a misleading word as there's no such thing when it comes to structs, but I couldn't think of a better description for this problem: Let's say I got a struct for a location on a 2-dimensional plane: struct Point { int x; int y; } Further I also need to represent a location in a 3-dimensional space: struct Coordinate { int x; int y; int z; } If these were classes instead I could simply make Coordinate inherit from Point and only add int z;. This would also make the thing I'm trying to achieve much easier; Consider I have a method that does something nifty with x and y, I'd like this method to handle both Point and Coordinate, if they were classes it would be fairly simple: int somethingNifty(Point p) { return p.x + p.y; } So why not just use classes? I've understood it as there may be a performance gain by using structs over classes, and in my program Point and Coordinate are used heavily. Obviously I'm fairly new to both D and structs, I have plenty Java and some C++ experience (I've avoided using structs in C++) and I have The D Programming Language book by Andrei which I'm happy to look up in, although I've failed to find an answer to this question in the book, in this newsgroup and on the net. I would greatly appreciate if someone could give me a nudge the the right direction. It seems that what you want is alias this: struct Point { int x; int y; } struct Coordinate { Point pt; int z; alias pt this; } void foo( Point p ) {} void main( ) { Coordinate c; foo( c ); c.x = 3; c.y = 4; c.z = 5; }
Re: Struct inheritance
On 2012-02-04 13:06, Simen Kjærås wrote: It seems that what you want is alias this: Thank you both, that's exactly what I needed. Leeching a bit more on the thread: Going back to the method: int somethingNifty(Point p) { return p.x + p.y; } Let's say I have the following code: for (x; 0 .. 10) { for (y; 0 .. 10) { Point p = {x, y}; somethingNifty(p); } } [How] can you rewrite those two statements inside the loops to a single line? For example (this doesn't work): somethingNifty(Point(x, y)); And finally a question about operator overloading, here's the code for Coordinate (Point is similar in structure): import Point; struct Coordinate { Point _point; int _z; @property auto point() const { return _point; } @property auto point(Point point) { return _point = point; } @property auto z() const { return _z; } @property auto z(int z) { return _z = z; } bool opEquals(ref const Coordinate c) const { return z == c.z point == c.point; } } Compilation fails with the following error: Coordinate.d:18: Error: function Point.Point.opEquals (ref const const(Point) p) const is not callable using argument types (const(Point)) const Coordinate.d:18: Error: c.point() is not an lvalue Noteworthy the code compiles fine if i replace point and c.point with _point and c._point, but then I'm referencing _point directly instead of through the property point (which may do something else than just return _point in the future). I've looked at http://www.d-programming-language.org/operatoroverloading.html#equals and that page is slightly confusing. It claims that: If structs declare an opEquals member function, it should follow the following form: struct S { int opEquals(ref const S s) { ... } } However, I can't even get the code to compile if I do that, the compiler (gdc-4.6) says: Error: function Coordinate.Coordinate.opEquals type signature should be const bool(ref const(Coordinate)) not int(ref const const(Coordinate) c) I hope it's somewhat clear what I'm trying to achieve.
Re: Struct inheritance
Vidar Wahlberg: Leeching a bit more on the thread: Going back to the method: int somethingNifty(Point p) { return p.x + p.y; } Let's say I have the following code: for (x; 0 .. 10) { for (y; 0 .. 10) { Point p = {x, y}; somethingNifty(p); } } [How] can you rewrite those two statements inside the loops to a single line? For example (this doesn't work): somethingNifty(Point(x, y)); This works: struct Point { int x, y; } int somethingNifty(Point p) { return p.x + p.y; } void main( ) { foreach (x; 0 .. 10) foreach (y; 0 .. 10) somethingNifty(Point(x, y)); } Bye, bearophile
Re: Struct inheritance
On Sat, 04 Feb 2012 13:55:55 +0100, Vidar Wahlberg cani...@exent.net wrote: On 2012-02-04 13:06, Simen Kjærås wrote: It seems that what you want is alias this: Thank you both, that's exactly what I needed. Leeching a bit more on the thread: Going back to the method: int somethingNifty(Point p) { return p.x + p.y; } Let's say I have the following code: for (x; 0 .. 10) { for (y; 0 .. 10) { Point p = {x, y}; somethingNifty(p); } } [How] can you rewrite those two statements inside the loops to a single line? For example (this doesn't work): somethingNifty(Point(x, y)); Like bearophile said, Point(x, y) should work - assuming you have defined no other constructors for Point. You can also explicitly define a constructor that does what you want. And finally a question about operator overloading, here's the code for Coordinate (Point is similar in structure): import Point; struct Coordinate { Point _point; int _z; @property auto point() const { return _point; } @property auto point(Point point) { return _point = point; } @property auto z() const { return _z; } @property auto z(int z) { return _z = z; } bool opEquals(ref const Coordinate c) const { return z == c.z point == c.point; } } Compilation fails with the following error: Coordinate.d:18: Error: function Point.Point.opEquals (ref const const(Point) p) const is not callable using argument types (const(Point)) const Coordinate.d:18: Error: c.point() is not an lvalue Noteworthy the code compiles fine if i replace point and c.point with _point and c._point, but then I'm referencing _point directly instead of through the property point (which may do something else than just return _point in the future). I've looked at http://www.d-programming-language.org/operatoroverloading.html#equals and that page is slightly confusing. It claims that: If structs declare an opEquals member function, it should follow the following form: struct S { int opEquals(ref const S s) { ... } } However, I can't even get the code to compile if I do that, the compiler (gdc-4.6) says: Error: function Coordinate.Coordinate.opEquals type signature should be const bool(ref const(Coordinate)) not int(ref const const(Coordinate) c) I hope it's somewhat clear what I'm trying to achieve. It is. The problem is that bool opEquals(ref const Point) expects a Point by reference, and the return value from your property is a temporary, from which we can get no reference. The solution is to remove the ref: bool opEquals(const Point). The only reason to use ref here is to cut down on copying, and might be worthwhile on larger structures.
Re: Struct inheritance
On 2012-02-04 14:45, Simen Kjærås wrote: Like bearophile said, Point(x, y) should work - assuming you have defined no other constructors for Point. You are correct, my apologies for not testing more thoroughly. Let me try again, explaining the real issue: I have 3 files: -- Bar.d -- import Foo; import Struct; class Bar { Foo _foo; this() { _foo = new Foo(Struct(1)); } } void main() { new Bar(); } -- Foo.d -- import Struct; class Foo { Struct _s; this(Struct s) { _s = s; } } -- Struct.d -- struct Struct { int baz; } This code does not compile: Bar.d:6: Error: function expected before (), not module Struct of type void Bar.d:6: Error: constructor Foo.Foo.this (Struct s) is not callable using argument types (_error_) Why is that? It is. The problem is that bool opEquals(ref const Point) expects a Point by reference, and the return value from your property is a temporary, from which we can get no reference. The solution is to remove the ref: bool opEquals(const Point). The only reason to use ref here is to cut down on copying, and might be worthwhile on larger structures. I've tried removing the ref, but I get other errors in return then: Point.d:19: Error: function Point.Point.opEquals type signature should be const bool(ref const(Point)) not const bool(const const(Point) p) Coordinate.d:20: Error: function Coordinate.Coordinate.opEquals type signature should be const bool(ref const(Coordinate)) not const bool(const const(Coordinate) c)
Re: i18n
On Thursday, 2 February 2012 at 19:40:14 UTC, Stewart Gordon wrote: Under Windows, you can use a stringtable resource. It's possible to make resources language-specific, but I don't know how. With LANGUAGE statement? http://msdn.microsoft.com/en-us/library/windows/desktop/aa381019%28v=vs.85%29.aspx
Re: i18n
Also http://msdn.microsoft.com/en-us/library/windows/desktop/aa381050%28v=vs.85%29.aspx
Less typed ranges
You can't write this: import std.algorithm; void main() { int[] a1 = [1, 2, 3]; auto r1 = map!(x = 2 * x)(a1); auto r2 = map!(x = x ^^ 2)(a1); auto a2 = [r1, r2]; } because the types of r1 and r2 aren't compatibile: test.d(6): Error: incompatible types for ((r1) ? (r2)): 'Result' and 'Result' So is it good to have something like this in Phobos that uses some type erasure? import std.algorithm, std.range; void main() { int[] a1 = [1, 2, 3]; ForwardRange!int r1 = forwardRange(map!(x = 2 * x)(a1)); ForwardRange!int r2 = forwardRange(map!(x = x ^^ 2)(a1)); ForwardRange!int[] a2 = [r1, r2]; } Bye, bearophile
Re: Struct inheritance
On 02/04/2012 03:38 AM, Vidar Wahlberg wrote: Let's say I got a struct for a location on a 2-dimensional plane: struct Point { int x; int y; } Further I also need to represent a location in a 3-dimensional space: struct Coordinate { int x; int y; int z; } If these were classes instead I could simply make Coordinate inherit from Point and only add int z;. There is also template mixins to inject complete features into the code (similar to C macros but without their gotchas). The following templatizes the coordinate types, but you could use put write everywhere: import std.stdio; template Point2D(T) { T x; T y; void foo2D() { writefln(Using (%s,%s), x, y); } } struct Coordinate(T) { mixin Point2D!T; // -- Inject x, y, and foo2D() here T z; this(T x, T y, T z) { this.x = x; this.y = y; this.z = z; } } void main() { auto c = Coordinate!double(1.1, 2.2, 3.3); c.foo2D(); } You could insert the following line in any other scope and you would have x, y, foo2D() inserted right there as well: if (someCondition) { mixin Point2D!T; // -- Inject x, y, and foo2D() here // ... use the local x, y, and foo2D() here } Of course 'static if' may be even more suitable in other cases. Ali
Re: Struct inheritance
On 02/04/2012 08:25 AM, Ali Çehreli wrote: The following templatizes the coordinate types, but you could use put write everywhere: That should be ... you could write *ints* everywhere. Ali
Re: Less typed ranges
Ali: It already exists: inputRangeObject() supports the accessing ranges and outputRangeObject takes care of output ranges. Thank you, I did miss them :-) Bye, bearophile
Contracts vs debug
Why/where should I use contracts vs debug statements? Is it completely arbitrary? If so, I wonder if contracts syntax is even needed: int foo(int bar) in { assert(bar != 0); } body { return bar + 1; } The thing I like more about debug statements, is that I can put them anywhere in my code, testing parameters and locals in the same way. If for documentation is the only argument for contracts, I find that a bit weak. int foo(int bar) { debug assert(bar != 0); return bar + 1; } That is much cleaner syntax and just as easy to understand from a assertion-failure/documentation standpoint IMO.
What should do a D lint?
hi, What should do a D lint? - check if in code the are no mixin between space / tab for indent - check indent (4 spaces as default) complete the list
Re: Segment violation (was Re: Why I could not cast string to int?)
On 02/04/2012 06:55 PM, Artur Skawina wrote: On 02/04/12 02:03, Timon Gehr wrote: On 02/03/2012 11:08 AM, Artur Skawina wrote: On 02/03/12 00:20, Jonathan M Davis wrote: in is pointless on value types. All it does is make the function parameter const, which really doesn't do much for you, and in some instances, is really annoying. Personally, I see no point in using in unless the parameter is a reference type, and even then, it's often a bad idea with reference types, because in is really const scope, and the scope is problematic if you want to return anything from that variable. It's particularly problematic with arrays, since it's frequently desirable to return slices of them, and scope (and therefore in) would prevent that. It's useful in some instances (particularly with delegates), but I'd use in _very_ sparingly. It's almost always more trouble than it's worth IMHO. BTW, scope should have been the default for *all* reference type function arguments, with an explicit modifier, say esc, required to let the thing escape. It's an all-or-nothing thing, just like immutable strings - not using it everywhere is painful, but once you switch everything over you get the benefits. I totally agree. Most function arguments are not escaped. However, it is nice that the shortest storage class, 'in', implies scope. There are currently two problems with using in: a) the one mentioned, where using in/scope means you can't (or shouldn't be able to) pass the thing to another function w/o scope marked args, and b) in implies const, which is a problem because you may want to reassign the argument - a perfectly safe thing to do. With const itself you can use parentheses to limit its scope to not include the reference itself; the problematic case is the builtin string alias, ie int f(in string s); would have to allow reassigning 's' inside the function. Semi-related quiz: immutable(char)[] a = a; const(char)[] b = b; auto aa = a ~ a; auto bb = b ~ b; auto ab = a ~ b; writeln(aa: , typeid(aa), bb: , typeid(bb), ab: , typeid(ab)); And the question is: How many people, who have not already been bitten by this, will give the correct answer to: What will this program print?? I think this is covered in this issue: http://d.puremagic.com/issues/show_bug.cgi?id=7311 But feel free to open a more specific enhancement/bug report. There should have been another class, in addition to immutable/const, say uniq. For cases where an expression results in new unique objects. This class implicitly converts to any of const/immutable and mutates to the new type. IOW string a = a; char[] b = b; auto c = a ~ b; // typeid(c) == (uniq(char)[]) string d = c; // Fine, c is unique and can be safely treated as a string. // But, from now on, c is (immutable(char)[]) so: char[] e = c; // Fails. // And the other way: auto f = a ~ b; char[] g = f; // OK string h = f // Fails, as f is now a (char[]) No need for unsafe-looking casts, just so that the compiler accepts perfectly safe code, like: string c = ab;, which would currently fail if used in the above quiz, and has to be written as string c = cast(string)ab;. [1] artur [1] Using a helper template is not different from adding a comment, it only serves to document /why/ the programmer had to something, which is only a workaround for a language/compiler limitation. Compiler because at least the simple cases could be silently fixed in a backward compatible way (by not disallowing safe conversions). Language because uniq would also be useful when the programmer knows it applies, but the compiler can't figure it out by itself. I am certain we'll get something like this eventually, once the compiler bug count has shrunk sufficiently. It is a natural thing to add.
Re: Pure Contract bug?
Pure does not imply const in D. If you want stronger guarantees, just turn 'test' into a const (or immutable) member function. In D, a function can change anything that is mutable and reachable through its parameters, this includes the implicit 'this' pointer. The reason for this design is simple: There is no need to be overly restrictive, because the additional restrictions are already trivially expressed in the type system. Furthermore, any mutation of a parameter can be turned into a less efficient protocol that only requires a const pure function, so there would be no gain if pure implied const, it would only make pure less useful. void foo(int* x)pure{*x+=2;} int bar(const(int)*x)pure{return *x+2;} void main() pure{ int x, y; foo(x); // those two lines have y = bar(y); // equivalent functionality! } Only external data I was implying, that was not based off the input arguments. Examples in the book refer that calculating Pi, or the square root of 2 is a constant and will always result in the same output, regardless the situation. Quote TDPL pg 165: In D, a function is considered pure if returning a result is it's only effect and the result depends only on the function's arguments. Also, pure functions can run literally in parallel because they don't interact with the rest of the program except through their result. So... If we take a struct. struct X { int i; pure int squaredPlus(int x) { return x*x + i } alias squaredPlus sqp; } X st(15); writeln(st.sqp(0)); //15 int i1 = st.sqp(10); st.i++; int i2 = st.sqp(10); st.i++; int i3 = st.sqp(10); st.i++; int i4 = st.sqp(10); st.i++; assert(i1 == 100); //pass/fail? assert(i2 == 101); //pass/fail? assert(i3 == 102); //pass/fail? assert(i4 == 103); //pass/fail? assert(s1.i == 104); //probably pass. If the compiler can reorder or run these in parallel (for optimization) or caches the result the first time (since it's suppose to always return the same value), what's correct in this case? This afterall isn't synchronized, even if it was, what's correct behavior? Am I wrong in understanding this?
Re: Segment violation (was Re: Why I could not cast string to int?)
On 02/04/12 22:20, Timon Gehr wrote: On 02/04/2012 06:55 PM, Artur Skawina wrote: On 02/04/12 02:03, Timon Gehr wrote: On 02/03/2012 11:08 AM, Artur Skawina wrote: On 02/03/12 00:20, Jonathan M Davis wrote: in is pointless on value types. All it does is make the function parameter const, which really doesn't do much for you, and in some instances, is really annoying. Personally, I see no point in using in unless the parameter is a reference type, and even then, it's often a bad idea with reference types, because in is really const scope, and the scope is problematic if you want to return anything from that variable. It's particularly problematic with arrays, since it's frequently desirable to return slices of them, and scope (and therefore in) would prevent that. It's useful in some instances (particularly with delegates), but I'd use in _very_ sparingly. It's almost always more trouble than it's worth IMHO. BTW, scope should have been the default for *all* reference type function arguments, with an explicit modifier, say esc, required to let the thing escape. It's an all-or-nothing thing, just like immutable strings - not using it everywhere is painful, but once you switch everything over you get the benefits. I totally agree. Most function arguments are not escaped. However, it is nice that the shortest storage class, 'in', implies scope. There are currently two problems with using in: a) the one mentioned, where using in/scope means you can't (or shouldn't be able to) pass the thing to another function w/o scope marked args, and b) in implies const, which is a problem because you may want to reassign the argument - a perfectly safe thing to do. With const itself you can use parentheses to limit its scope to not include the reference itself; the problematic case is the builtin string alias, ie int f(in string s); would have to allow reassigning 's' inside the function. Semi-related quiz: immutable(char)[] a = a; const(char)[] b = b; auto aa = a ~ a; auto bb = b ~ b; auto ab = a ~ b; writeln(aa: , typeid(aa), bb: , typeid(bb), ab: , typeid(ab)); And the question is: How many people, who have not already been bitten by this, will give the correct answer to: What will this program print?? I think this is covered in this issue: http://d.puremagic.com/issues/show_bug.cgi?id=7311 But feel free to open a more specific enhancement/bug report. Apparently, there's already a bug open for everything. I'm not sure if it's a good or bad thing. :) I don't think there's one correct answer here - you're right that unique const does not really make sense. But is mutable (non-const) really better than immutable? It depends, sometimes you will want one, sometimes the other. I first ran into this while doing a custom string class - there it was the cause of the one and only cast - (string ~ const(char)[]) can obviously still be a string, but the compiler won't accept it without a cast. I'm not sure how often you'll want the result of concatenation to be mutable, compared to immutable. Anyway, the result really is unique, not mutable, const or immutable, at least until it is converted to one of those, hence the solution described below. There should have been another class, in addition to immutable/const, say uniq. For cases where an expression results in new unique objects. This class implicitly converts to any of const/immutable and mutates to the new type. IOW string a = a; char[] b = b; auto c = a ~ b; // typeid(c) == (uniq(char)[]) string d = c; // Fine, c is unique and can be safely treated as a string. // But, from now on, c is (immutable(char)[]) so: char[] e = c; // Fails. // And the other way: auto f = a ~ b; char[] g = f; // OK string h = f // Fails, as f is now a (char[]) No need for unsafe-looking casts, just so that the compiler accepts perfectly safe code, like: string c = ab;, which would currently fail if used in the above quiz, and has to be written as string c = cast(string)ab;. [1] artur [1] Using a helper template is not different from adding a comment, it only serves to document /why/ the programmer had to something, which is only a workaround for a language/compiler limitation. Compiler because at least the simple cases could be silently fixed in a backward compatible way (by not disallowing safe conversions). Language because uniq would also be useful when the programmer knows it applies, but the compiler can't figure it out by itself. I am certain we'll get something like this eventually, once the compiler bug count has shrunk sufficiently. It is a natural thing to add. It would be great if as many of the /language/ issues were fixed and documented as soon as possible. They don't even have to be implemented. What i'm afraid of is what will happen once dmd no longer is the
Re: Pure Contract bug?
On 02/04/2012 11:04 PM, Era Scarecrow wrote: Pure does not imply const in D. If you want stronger guarantees, just turn 'test' into a const (or immutable) member function. In D, a function can change anything that is mutable and reachable through its parameters, this includes the implicit 'this' pointer. The reason for this design is simple: There is no need to be overly restrictive, because the additional restrictions are already trivially expressed in the type system. Furthermore, any mutation of a parameter can be turned into a less efficient protocol that only requires a const pure function, so there would be no gain if pure implied const, it would only make pure less useful. void foo(int* x)pure{*x+=2;} int bar(const(int)*x)pure{return *x+2;} void main() pure{ int x, y; foo(x); // those two lines have y = bar(y); // equivalent functionality! } Only external data I was implying, that was not based off the input arguments. Examples in the book refer that calculating Pi, or the square root of 2 is a constant and will always result in the same output, regardless the situation. Quote TDPL pg 165: In D, a function is considered pure if returning a result is it's only effect and the result depends only on the function's arguments. Also, pure functions can run literally in parallel because they don't interact with the rest of the program except through their result. Probably the restriction was lifted after TDPL was out. So... If we take a struct. struct X { int i; pure int squaredPlus(int x) { return x*x + i } alias squaredPlus sqp; } X st(15); writeln(st.sqp(0)); //15 int i1 = st.sqp(10); st.i++; int i2 = st.sqp(10); st.i++; int i3 = st.sqp(10); st.i++; int i4 = st.sqp(10); st.i++; assert(i1 == 100); //pass/fail? assert(i2 == 101); //pass/fail? assert(i3 == 102); //pass/fail? assert(i4 == 103); //pass/fail? assert(s1.i == 104); //probably pass. If the compiler can reorder or run these in parallel (for optimization) or caches the result the first time (since it's suppose to always return the same value), what's correct in this case? This afterall isn't synchronized, even if it was, what's correct behavior? Am I wrong in understanding this? Yes. The compiler will only reorder/run in parallel/optimize if it is safe (not changing execution semantics). Pure can be used to prove that certain optimizations are safe. If a pure function only takes const or immutable arguments, the compiler has more guarantees and can do more things. If a pure function takes mutable arguments, it can be used as a component of other pure functions (important!), but the kind of optimizations that can be performed directly on them are a lot more limited. 'Pure' means that the behavior of the function does not change between invocations with the same/equivalent arguments. This can include mutating actions on the arguments, if those are typed mutable.
Raw socket TCP/IP
Hi, I'm trying to use a raw socket, but when I create a socket(AddressFamily.INET, SocketType.RAW, ProtocolType.TCP) and then I use socket.sendTo(datagram, addr) I've got a 10002 code error Invalid argument... Can anyone help me please, and sorry for my bad english :s
Re: Segment violation (was Re: Why I could not cast string to int?)
On 02/04/2012 11:23 PM, Artur Skawina wrote: On 02/04/12 22:20, Timon Gehr wrote: On 02/04/2012 06:55 PM, Artur Skawina wrote: On 02/04/12 02:03, Timon Gehr wrote: On 02/03/2012 11:08 AM, Artur Skawina wrote: On 02/03/12 00:20, Jonathan M Davis wrote: in is pointless on value types. All it does is make the function parameter const, which really doesn't do much for you, and in some instances, is really annoying. Personally, I see no point in using in unless the parameter is a reference type, and even then, it's often a bad idea with reference types, because in is really const scope, and the scope is problematic if you want to return anything from that variable. It's particularly problematic with arrays, since it's frequently desirable to return slices of them, and scope (and therefore in) would prevent that. It's useful in some instances (particularly with delegates), but I'd use in _very_ sparingly. It's almost always more trouble than it's worth IMHO. BTW, scope should have been the default for *all* reference type function arguments, with an explicit modifier, say esc, required to let the thing escape. It's an all-or-nothing thing, just like immutable strings - not using it everywhere is painful, but once you switch everything over you get the benefits. I totally agree. Most function arguments are not escaped. However, it is nice that the shortest storage class, 'in', implies scope. There are currently two problems with using in: a) the one mentioned, where using in/scope means you can't (or shouldn't be able to) pass the thing to another function w/o scope marked args, and b) in implies const, which is a problem because you may want to reassign the argument - a perfectly safe thing to do. With const itself you can use parentheses to limit its scope to not include the reference itself; the problematic case is the builtin string alias, ie int f(in string s); would have to allow reassigning 's' inside the function. Semi-related quiz: immutable(char)[] a = a; const(char)[] b = b; auto aa = a ~ a; auto bb = b ~ b; auto ab = a ~ b; writeln(aa: , typeid(aa), bb: , typeid(bb), ab: , typeid(ab)); And the question is: How many people, who have not already been bitten by this, will give the correct answer to: What will this program print?? I think this is covered in this issue: http://d.puremagic.com/issues/show_bug.cgi?id=7311 But feel free to open a more specific enhancement/bug report. Apparently, there's already a bug open for everything. I'm not sure if it's a good or bad thing. :) I don't think there's one correct answer here - you're right that unique const does not really make sense. But is mutable (non-const) really better than immutable? It depends, sometimes you will want one, sometimes the other. I first ran into this while doing a custom string class - there it was the cause of the one and only cast - (string ~ const(char)[]) can obviously still be a string, but the compiler won't accept it without a cast. I'm not sure how often you'll want the result of concatenation to be mutable, compared to immutable. Anyway, the result really is unique, not mutable, const or immutable, at least until it is converted to one of those, hence the solution described below. Well, string = string ~ const(char)[] and char[] = string ~ const(char)[] should work, regardless of the type of immutable[] ~ const[]. The compiler can track the uniqueness of the data at the expression level without actually introducing a type modifier. There is precedent: Array literals are covariant, because it is safe. Do you want to open the enhancement or should I do it? (I really thought I already had an issue open for this...) There should have been another class, in addition to immutable/const, say uniq. For cases where an expression results in new unique objects. This class implicitly converts to any of const/immutable and mutates to the new type. IOW string a = a; char[] b = b; auto c = a ~ b; // typeid(c) == (uniq(char)[]) string d = c; // Fine, c is unique and can be safely treated as a string. // But, from now on, c is (immutable(char)[]) so: char[] e = c; // Fails. // And the other way: auto f = a ~ b; char[] g = f; // OK string h = f // Fails, as f is now a (char[]) No need for unsafe-looking casts, just so that the compiler accepts perfectly safe code, like: string c = ab;, which would currently fail if used in the above quiz, and has to be written as string c = cast(string)ab;. [1] artur [1] Using a helper template is not different from adding a comment, it only serves to document /why/ the programmer had to something, which is only a workaround for a language/compiler limitation. Compiler because at least the simple cases could be silently fixed in a backward compatible way (by not disallowing safe conversions). Language because uniq would also be useful when the
Re: Pure Contract bug?
Probably the restriction was lifted after TDPL was out. Yes. The compiler will only reorder/run in parallel/optimize if it is safe (not changing execution semantics). Pure can be used to prove that certain optimizations are safe. If a pure function only takes const or immutable arguments, the compiler has more guarantees and can do more things. If a pure function takes mutable arguments, it can be used as a component of other pure functions (important!), but the kind of optimizations that can be performed directly on them are a lot more limited. 'Pure' means that the behavior of the function does not change between invocations with the same/equivalent arguments. This can include mutating actions on the arguments, if those are typed mutable. Even if you changed the signature of the pure function to 'pure int squaredPlus(immutable int);' you'd have the same problem; Because the int argument it receives is a copy so it won't matter if it was mutable or not. (If it were an object, then it would be more enforced). I'll refer to the language specs to see if I can find an answer on this, but it feels wrong allowing access to 'this' on mutable data; I thought it could only mutate it's own data in regards to local variables and arguments it owned.
Re: Segment violation (was Re: Why I could not cast string to int?)
On 02/04/12 23:44, Timon Gehr wrote: On 02/04/2012 11:23 PM, Artur Skawina wrote: On 02/04/12 22:20, Timon Gehr wrote: On 02/04/2012 06:55 PM, Artur Skawina wrote: Semi-related quiz: immutable(char)[] a = a; const(char)[] b = b; auto aa = a ~ a; auto bb = b ~ b; auto ab = a ~ b; writeln(aa: , typeid(aa), bb: , typeid(bb), ab: , typeid(ab)); And the question is: How many people, who have not already been bitten by this, will give the correct answer to: What will this program print?? I think this is covered in this issue: http://d.puremagic.com/issues/show_bug.cgi?id=7311 But feel free to open a more specific enhancement/bug report. Apparently, there's already a bug open for everything. I'm not sure if it's a good or bad thing. :) I don't think there's one correct answer here - you're right that unique const does not really make sense. But is mutable (non-const) really better than immutable? It depends, sometimes you will want one, sometimes the other. I first ran into this while doing a custom string class - there it was the cause of the one and only cast - (string ~ const(char)[]) can obviously still be a string, but the compiler won't accept it without a cast. I'm not sure how often you'll want the result of concatenation to be mutable, compared to immutable. Anyway, the result really is unique, not mutable, const or immutable, at least until it is converted to one of those, hence the solution described below. Well, string = string ~ const(char)[] and char[] = string ~ const(char)[] should work, regardless of the type of immutable[] ~ const[]. The compiler can track the uniqueness of the data at the expression level without actually introducing a type modifier. There is precedent: Array literals are covariant, because it is safe. Do you want to open the enhancement or should I do it? (I really thought I already had an issue open for this...) Please do; i've been avoiding filing dmd bugs, because i'm only using gdc, not dmd. (so i can't even easily check if the issue still exists in the current tree) artur
Re: Pure Contract bug?
On 02/05/2012 12:15 AM, Era Scarecrow wrote: Probably the restriction was lifted after TDPL was out. Yes. The compiler will only reorder/run in parallel/optimize if it is safe (not changing execution semantics). Pure can be used to prove that certain optimizations are safe. If a pure function only takes const or immutable arguments, the compiler has more guarantees and can do more things. If a pure function takes mutable arguments, it can be used as a component of other pure functions (important!), but the kind of optimizations that can be performed directly on them are a lot more limited. 'Pure' means that the behavior of the function does not change between invocations with the same/equivalent arguments. This can include mutating actions on the arguments, if those are typed mutable. Even if you changed the signature of the pure function to 'pure int squaredPlus(immutable int);' you'd have the same problem; Because the int argument it receives is a copy so it won't matter if it was mutable or not. (If it were an object, then it would be more enforced). I'll refer to the language specs to see if I can find an answer on this, but it feels wrong allowing access to 'this' on mutable data; I thought it could only mutate it's own data in regards to local variables and arguments it owned. the signature I meant looks like pure int squaredPlus(int)immutable;
Re: Associative array literal is non-constant?
On 02/04/12 07:46, H. S. Teoh wrote: On Fri, Feb 03, 2012 at 10:18:18PM -0800, H. S. Teoh wrote: Why does the following code give a compiler error? static int[string] table = [abc:1, def:2, ghi:3]; Error message is: prog.d:3: Error: non-constant expression [abc:1,def:2,ghi:3] How is a literal non-constant? [...] Ugh. Just found this: http://d.puremagic.com/issues/show_bug.cgi?id=6238 Further testing shows that assoc array literals can't be used outside of function scope at all, for example: // (in package scope) auto hash = [ abc:1, def:2, ghi:3 ]; // Error: non-constant expression [abc:1,def:2,ghi:3] Seems like a pretty nasty bug to me. Consider the implementation, ie what you have to do to make const AAs work... I think I'd prefer them to be distinct types, that do not implicitly convert to the non-const variant. Then the compiler is free to implement them differently, eg by picking a perfect hash, ensuring there are no collisions etc. This would let you use them for fast local lookups, which is probably what most use cases of const AAs are. And if you assign it to another AA, the new one is initialized at runtime from the values in the const AA. Which (runtime init) is the only way possible currently. It shouldn't happen implicitly because for larger arrays the conversion could be expensive. Defining a non-const AA initialized from a literal (like in the quoted examples above) is the non-obvious case. If nothing modifies the array and it does not leave the scope everything's fine. But if one of these things happens, doing the init/conversion at runtime might not be what the user expects. So keeping mutable AAs initialized from literals illegal would probably be the best thing. Note: AA literals are documented to be non-const [1], so all of the above would be backwards compatible - it only allows for things which currently are illegal. artur [1] Somewhere on dlang.org. Can't find that page right now.
Re: Raw socket TCP/IP
On 2/4/12 11:42 PM, Eyyub wrote: I'm trying to use a raw socket, […] Use SocketType.STREAM if you want TCP. SOCK_RAW is for cases where you want a raw IP socket (for the exact details, look it up in your OS docs). David
Re: Pure Contract bug?
the signature I meant looks like pure int squaredPlus(int)immutable; Which then the only way you could call it, was if the object itself was immutable, which is definitely safe (I think). Hmmm...
Re: Pure Contract bug?
On 02/05/2012 01:20 AM, Era Scarecrow wrote: the signature I meant looks like pure int squaredPlus(int)immutable; Which then the only way you could call it, was if the object itself was immutable, which is definitely safe (I think). Hmmm... Alternatively you can use pure int squaredPlus(int)const;, of course.
Re: i18n
On Thu, Feb 2, 2012 at 4:48 PM, xancorreu xancor...@gmail.com wrote: Hi, Is there any way for localizate and internationalizate messages? I were shocked if D has something like Fantom [http://fantom.org/doc/docLang/Localization.html]. Gettext is pretty ugly ;-) I just glanced at Fantom because I am very much interesting in localization framework design. You really think that Fantom's localization design is better than gettext? What human language is $fwt::cancel.name? If not, any plannings? Thanks, Xan.