Re: Template constraints: opCmp and opUnary!"++"
On Friday, 20 December 2013 at 20:42:13 UTC, monarch_dodra wrote: AFAIK, there is no real difference, but "is(typeof())" is more "idiomatic" in phobos. Most uses of `is(typeof())` were written before the `compiles` trait was introduced. Add the cargo cult to that, and it's no wonder that Phobos uses `is(typeof())` so liberally, but I think the `compiles` trait shows intent better and benefits from fewer parentheses. However, there is the problem that uses of `__traits` are supposed to be internal, not user-facing. We haven't made much headway on that one.
Re: Removing multiple elements from array
On Fri, Dec 20, 2013 at 07:13:59PM -0800, H. S. Teoh wrote: > On Fri, Dec 20, 2013 at 07:01:17PM -0800, Ali Çehreli wrote: > > On 12/20/2013 06:17 PM, aldanor wrote: > > >On Saturday, 21 December 2013 at 01:42:04 UTC, Ali Çehreli wrote: > > > > > >>That's probably a bug, right? The indexes would probably become off as > > >>the array gets shorter. > > > > > >Note the .reverse there? > > > > Yes, I missed that part. :) > > > > >Which makes sure indices don't get off. Still, > > >that's probably an inefficient way of doing this... > > > > Yeah, every removal would move the right-hand elements one position > > to the left. But you would be removing only M times (the number of > > indexes). So the complexity is I think O(M logM) + O(NM) for sorting > > the indexing plus removing M elements by shifting at the order of N > > elements. > > > > The range solution that I've come up with is I think O(M log M) + > > O(M) + O(N), for sorting the indexes, removing the duplicates with > > uniq and iterating the elements. Since O(M log M) dominates O(M), it > > should be O(M log M) + O(N). > [...] > > If you know the which elements you're going to remove, you can remove > them all at once in O(N) time: > > int[] arr = [ ... ]; > for (i=0, j=0; i < arr.length; i++) > { > if (deleteThisElement(arr[i])) > continue; > if (j < i) > arr[j] = arr[i]; > j++; > } > arr.length = j; There's also a Phobos solution: the above code is equivalent to: import std.algorithm : remove; int[] arr = [ ... ]; arr = arr.remove!deleteThisElement(); > Of course, if you know which *indices* you're going to remove, then > you can do even better (by starting your loop at the first index to be > deleted). [...] Unfortunately, while std.algorithm.remove does provide a way to do this if the number of indices to remove are known beforehand, it doesn't seem to be able to remove a dynamic list of indices. Probably an enhancement request should be filed: http://d.puremagic.com/issues If the number of indices to remove are fixed, though, you can do this: import std.algorithm : remove; int[] arr = [ ... ]; int i1, i2, i3; // indices to remove arr = arr.remove(i1, i2, i3); T -- It's bad luck to be superstitious. -- YHL
Re: Removing multiple elements from array
On Fri, Dec 20, 2013 at 07:01:17PM -0800, Ali Çehreli wrote: > On 12/20/2013 06:17 PM, aldanor wrote: > >On Saturday, 21 December 2013 at 01:42:04 UTC, Ali Çehreli wrote: > > > >>That's probably a bug, right? The indexes would probably become off as > >>the array gets shorter. > > > >Note the .reverse there? > > Yes, I missed that part. :) > > >Which makes sure indices don't get off. Still, > >that's probably an inefficient way of doing this... > > Yeah, every removal would move the right-hand elements one position > to the left. But you would be removing only M times (the number of > indexes). So the complexity is I think O(M logM) + O(NM) for sorting > the indexing plus removing M elements by shifting at the order of N > elements. > > The range solution that I've come up with is I think O(M log M) + > O(M) + O(N), for sorting the indexes, removing the duplicates with > uniq and iterating the elements. Since O(M log M) dominates O(M), it > should be O(M log M) + O(N). [...] If you know the which elements you're going to remove, you can remove them all at once in O(N) time: int[] arr = [ ... ]; for (i=0, j=0; i < arr.length; i++) { if (deleteThisElement(arr[i])) continue; if (j < i) arr[j] = arr[i]; j++; } arr.length = j; Of course, if you know which *indices* you're going to remove, then you can do even better (by starting your loop at the first index to be deleted). T -- BREAKFAST.COM halted...Cereal Port Not Responding. -- YHL
Re: Removing multiple elements from array
On 12/20/2013 06:17 PM, aldanor wrote: On Saturday, 21 December 2013 at 01:42:04 UTC, Ali Çehreli wrote: That's probably a bug, right? The indexes would probably become off as the array gets shorter. Note the .reverse there? Yes, I missed that part. :) Which makes sure indices don't get off. Still, that's probably an inefficient way of doing this... Yeah, every removal would move the right-hand elements one position to the left. But you would be removing only M times (the number of indexes). So the complexity is I think O(M logM) + O(NM) for sorting the indexing plus removing M elements by shifting at the order of N elements. The range solution that I've come up with is I think O(M log M) + O(M) + O(N), for sorting the indexes, removing the duplicates with uniq and iterating the elements. Since O(M log M) dominates O(M), it should be O(M log M) + O(N). Ali P.S. Hm. I think I've reading an algorithms book lately. :p
Re: "a[++i] = i" vs "a[i] = ++i"
On Saturday, 21 December 2013 at 02:52:26 UTC, aldanor wrote: So.. isn't it exactly the case where a warning is most suitable? :) C/C++ compilers sure get it right in this regard. No. There is no such thing as "suitable compiler warning". It should have been an error.
Re: "a[++i] = i" vs "a[i] = ++i"
On Saturday, 21 December 2013 at 01:00:48 UTC, bearophile wrote: aldanor: it would be nice if the compiler (at least) fired a warning about this kind of things, For reasons D doesn't like warnings, they are kept at a minimum. D prefers errors :-) Bye, bearophile So.. isn't it exactly the case where a warning is most suitable? :) C/C++ compilers sure get it right in this regard.
Re: Removing multiple elements from array
aldanor: Is there an efficient method to remove elements with multiple (compile-time-unknown) indices from an array? I currently do something like if (!index.empty) foreach (i; index.sort.reverse) a = a.remove(i); ... which looks a bit awkward. Do not forget to add the () after the sort, otherwise you call the deprecated, buggy and slow built-in sort. reverse is another deprecated built-in, so use "retro". The first "if" is not much useful, trying to sort an empty array will not wast much time. foreach (i; index.sort().retro) a = a.remove(i); In alternative you can also invert the sorting cmp (untested): foreach (i; index.sort!q{a > b}) a = a.remove(i); If you have to remove just few items in-place, that's the way to do it. In future I hope we'll have a better remove function in Phobos (but it's not hard to write). Another solution is to filter the array a. If you have the indexes, you can zip a with the indexes, and then filter, map to extract just the items and use copy() to work in place, but it's not nice-looking code. Bye, bearophile
Re: Removing multiple elements from array
On Saturday, 21 December 2013 at 01:42:04 UTC, Ali Çehreli wrote: That's probably a bug, right? The indexes would probably become off as the array gets shorter. Note the .reverse there? Which makes sure indices don't get off. Still, that's probably an inefficient way of doing this...
Re: Language subset for printing
On Saturday, 21 December 2013 at 01:57:50 UTC, Casper Færgemand wrote: Having skimmed core.stdc.stdio.d now, it's seems pretty manageable to parse, so we'll go with that. Thankies. :3 cool. Also make note of the "extern(C):" on line 30 of that file: the colon applies that thing to everything after it, so the whole file is extern(C) (and nothrow and @system, unless overridden later0 Also, the druntime import names follow a simple pattern: core.stdc.* -> #include<*.h> in C. so stdio.h is core.stdc.stdio, stdlib.h is core.stdc.stdlib, and so on. This only covers standard C functions, some C includes won't be there since they are non-standard extensions. There's also includes for other operating systems in core.sys.OS_NAME.FILE so import core.sys.posix.unistd; is #include in C on Posix systems (linux, etc.) core.sys.linux.* is Linus specific extensions. core.sys.posix.sys.socket == #include And there's also core.sys.windows.windows for Windows stuff, though this is really incomplete. So if you do much work with the Win32 API you'll want to download the more complete bindings http://www.dsource.org/projects/bindings/browser/trunk/win32 There's a bunch of other C libs done in here too: https://github.com/D-Programming-Deimos Or, you can avoid doing the modules by just copy/pasting the extern(C) definitions you need to call yourself. That can get a bit tricky translating macros and structs from C, you'll have to be sure to get the types right (A "long" in C isn't the same as a "long" in D for instance), but this isn't too hard either. So if something isn't already done in the deimos collection, you can still use the C libraries (or other C files you write) just by getting those function prototypes done like i did in my last message.
Re: Language subset for printing
On Saturday, 21 December 2013 at 01:47:07 UTC, Adam D. Ruppe wrote: snip Well that answered more than my question. That's pretty useful actually. Having skimmed core.stdc.stdio.d now, it's seems pretty manageable to parse, so we'll go with that. Thankies. :3
Re: Language subset for printing
On Saturday, 21 December 2013 at 01:39:29 UTC, Casper Færgemand wrote: I take it that means it's intrinsic? Not intrinsic, just an extern library function. D can call any C function by copy/pasting the declaration and adding extern(C). for example, on Linux, you can do: extern(C) void write(int, char*, size_t); void main() { write(1, "hello\n", 6); } and that will work too. Similarly, on Windows, you can do: extern(Windows) int MessageBoxA(void*, const char*, const char*, int); void main() { MessageBoxA(null, "hello", "message", 0); } and call operating system functions that way.
Re: Removing multiple elements from array
On 12/20/2013 04:47 PM, aldanor wrote: > Is there an efficient method to remove elements with multiple > (compile-time-unknown) indices from an array? I currently do something like > > if (!index.empty) > foreach (i; index.sort.reverse) > a = a.remove(i); That's probably a bug, right? The indexes would probably become off as the array gets shorter. > ... which looks a bit awkward. I am sure others can come up with solutions but I can't think of a way of doing this Phobos right now. :) Here is a range that does what you want (not very well tested ;) ): import std.stdio; import std.array; import std.range; import std.algorithm; struct SkipIndexes(R, I) { alias SortedIndexRange = typeof((I.init).sort.uniq); R range; SortedIndexRange indexes; size_t currentIndex; this(R range, I indexes, size_t currentIndex = 0) { this.range = range; this.indexes = indexes.sort.uniq; this.currentIndex = currentIndex; prime(); } bool empty() const @property { return range.empty; } ElementType!R front() const @property { return range.front; } void prime() { while (!empty && !indexes.empty && (indexes.front == currentIndex)) { range.popFront(); indexes.popFront(); ++currentIndex; } } void popFront() { range.popFront(); ++currentIndex; prime(); } auto save() @property { return this; } void report() const { writeln(indexes); writeln(currentIndex); } } auto skipIndexes(R, I)(R range, I skipIndexes, size_t currentIndex = 0) { return SkipIndexes!(R, I)(range, skipIndexes, currentIndex); } void main() { auto arr = [ 0, 1, 2, 3, 4, 5 ]; size_t[] badIndexes = [ 0, 1, 5 ]; auto skipped = arr.skipIndexes(badIndexes); // skipped is a lazy range: assert(skipped.equal([ 2, 3, 4 ])); // arr is untouched at this point: assert(arr == [ 0, 1, 2, 3, 4, 5 ]); // To affect it, assign from .array of the lazy range: arr = skipped.array; assert(arr == [ 2, 3, 4 ]); } Ali
Re: Language subset for printing
On Saturday, 21 December 2013 at 01:18:55 UTC, Adam D. Ruppe wrote: Just call printf in D! import core.stdc.stdio; void main() { printf("hello world!\n"); } int printf(in char* format, ...); I take it that means it's intrinsic?
Re: Language subset for printing
On Saturday, 21 December 2013 at 01:09:31 UTC, Casper Færgemand wrote: How big of a subset of D would a compiler need to use writeln? writeln is pretty complex and using it pulls in a lot of Phobos too. Is there possibly an easier way to write to stdout? Calling printf in some C code perhaps? Just call printf in D! import core.stdc.stdio; void main() { printf("hello world!\n"); }
Language subset for printing
How big of a subset of D would a compiler need to use writeln? I managed to track stdout to file. At the very least it seems to require templates and type tuples. Or will everything in stdio and file be needed, and perhaps thing in other files as well? Is there possibly an easier way to write to stdout? Calling printf in some C code perhaps? We'd like to start out with as small a subset as possible, but looking at return codes only is not particularly appealing. :3
Re: "a[++i] = i" vs "a[i] = ++i"
aldanor: it would be nice if the compiler (at least) fired a warning about this kind of things, For reasons D doesn't like warnings, they are kept at a minimum. D prefers errors :-) Bye, bearophile
Removing multiple elements from array
Is there an efficient method to remove elements with multiple (compile-time-unknown) indices from an array? I currently do something like if (!index.empty) foreach (i; index.sort.reverse) a = a.remove(i); ... which looks a bit awkward.
Re: "a[++i] = i" vs "a[i] = ++i"
On Friday, 20 December 2013 at 23:17:31 UTC, bearophile wrote: Right, currently the outcome of that kind of code is not specified in D. So writing it is a error, and the D compiler doesn't warn you. Do not write that kind of code in D. Walter wants to eventually (but when? Five years from now?) make that code specified, this means all the D compilers will know what that kind of code produce and will all give the same result reliably. But in my opinion making the code unambiguous and specified for the compiler is not enough. You have also to take in account people that write and read the code, it needs to be unambiguous for them too. For them that kind of code can become tricky, even when you know the rules used by the compiler. So I'd like that kind of D code just to be disallowed, to be an error (and this doesn't break compatibility with C, because equivalent C code is not defined). I completely agree. I guess my point is, it would be nice if the compiler (at least) fired a warning about this kind of things, kinda of like clang does for both statements (and rightly so). It is nigh impossible for a D newcomer figure out if this kind of code is valid or not, and as you can see from the random example above one might think that it is indeed the way to go.
Re: assert vs enforce.
TheFlyingFiddle: When should i use enforce instead of assert? Others have already told you most of the answer. Let me add that enforce() is heavier for the compiler, so don't put an enforce in a performance-critical path in your code. Bye, bearophile
Re: TypeInfo of interfaces bugg or feature?
On Friday, 20 December 2013 at 21:21:16 UTC, TheFlyingFiddle wrote: Is this intended or is it a bug? Intended, because an interface is not necessarily an Object. It might also be a COM object or a C++ object, and the typeinfo may not be available for them. (I think, maybe it would be from the .di file at least, but it is a different root anyway). If you cast to Object then do typeid, you'll get the typeinfo you expect. (or null if it isn't a D Object)
Re: std.net.curl - get() is too slow
On Friday, 20 December 2013 at 18:23:30 UTC, Benji wrote: When I call get() function from std.net.curl, I notice it's extremely slow! Maybe 50 times slower than in Python.. Is there any better/faster alternative? How do you benchmark the functions? David
Re: "a[++i] = i" vs "a[i] = ++i"
Ali Çehreli: Although D is less vocal on these topics it is the same as C and C++: The evaluation order is unspecified. I've read before that Walter wants to eventually define such evaluation orders but it is not specified yet. Right, currently the outcome of that kind of code is not specified in D. So writing it is a error, and the D compiler doesn't warn you. Do not write that kind of code in D. Walter wants to eventually (but when? Five years from now?) make that code specified, this means all the D compilers will know what that kind of code produce and will all give the same result reliably. But in my opinion making the code unambiguous and specified for the compiler is not enough. You have also to take in account people that write and read the code, it needs to be unambiguous for them too. For them that kind of code can become tricky, even when you know the rules used by the compiler. So I'd like that kind of D code just to be disallowed, to be an error (and this doesn't break compatibility with C, because equivalent C code is not defined). Bye, bearophile
Re: assert vs enforce.
Asserts are removed in release builds, enforces remain. Asserts are used to verify internal sanity of application and never happen if it does not contain programming errors. Enforces provide syntax sugar for routine error handling under normal workflow.
Re: assert vs enforce.
On Friday, 20 December 2013 at 23:08:32 UTC, TheFlyingFiddle wrote: When should i use enforce instead of assert? Assert is for things that is completely controlled by your program. If an assert fails, it is something you, the programmer, can fix by changing the code. enforce is for things that interact with the outside world at runtime. It might be fixable by the user, creating a file or something like that.
assert vs enforce.
When should i use enforce instead of assert?
Re: "a[++i] = i" vs "a[i] = ++i"
On Fri, Dec 20, 2013 at 11:29:54PM +0100, Ivan Smirnov wrote: > I was wondering if this behavior is actually documented anywhere? > Let's say we want to increment i and store the new value at the > index equal to the new (incremented) value. > > int[int] a; > int i = 1; > a[++i] = i; > writeln(a); > a[i] = ++i; > writeln(a); [...] In C/C++, the evaluation order in this case is unspecified, so you're in the territory of undefined behaviour. Whatever you observe will be specific to the compiler (and version) you're using, and you cannot depend on getting the same result across different compilers (or even different versions of the same compiler, or even different compiler flags -- using -O may change the behaviour in some cases). Now, in D, I believe this is currently also undefined behaviour, although Walter did mention at some point that he wanted to fix evaluation order in these cases. But I don't know if that has happened yet. Either way, you're treading on dangerous ground, since the spec currently doesn't say one way or another, so different compilers could have different interpretations of what the above code means. So the runtime behaviour could change from compiler to compiler, or from version to version, or from specifying -O or not. Mixing side-effects in an expression that references the changed value multiple times should be avoided in general because of these kinds of ambiguity. For example, what should the following code do? int a = 1; int b = ++a * --a + --a * ++a; (N.B. * must be evaluated before +. So does ++/-- get evaluated before or after *, or something else?) T -- Государство делает вид, что платит нам зарплату, а мы делаем вид, что работаем.
Re: "a[++i] = i" vs "a[i] = ++i"
On 12/20/2013 02:29 PM, Ivan Smirnov wrote:> I was wondering if this behavior is actually documented anywhere? Let's > say we want to increment i and store the new value at the index equal to > the new (incremented) value. > > int[int] a; > int i = 1; > a[++i] = i; > writeln(a); > a[i] = ++i; > writeln(a); > >>> [2:2] >>> [2:2, 3:3] > > If any, I would expect it to work for either one of lines but not both? > > What is interesting, if you compile the same in C (I used clang), you > get a "warning: unsequenced modification That is a roundabout way of saying "the assignment operator does not define a sequence point". :p > and access to 'i'" on both > lines and the answer is (as I would initially except) > >>> [2:1] >>> [2:1, 3:3] Well, regardless of one's expectations, that is one outcome of unspecified behavior. :) Although D is less vocal on these topics it is the same as C and C++: The evaluation order is unspecified. I've read before that Walter wants to eventually define such evaluation orders but it is not specified yet. Ali
"a[++i] = i" vs "a[i] = ++i"
I was wondering if this behavior is actually documented anywhere? Let's say we want to increment i and store the new value at the index equal to the new (incremented) value. int[int] a; int i = 1; a[++i] = i; writeln(a); a[i] = ++i; writeln(a); [2:2] [2:2, 3:3] If any, I would expect it to work for either one of lines but not both? What is interesting, if you compile the same in C (I used clang), you get a "warning: unsequenced modification and access to 'i'" on both lines and the answer is (as I would initially except) [2:1] [2:1, 3:3]
Re: unittests and Windows App
On 19.12.2013 14:55, ref2401 wrote: I'm using D 2064.2 and VisualD 0.3.37 VisualD "Redirect stdout to output window" checkbox is checked. In simple ConsoleApp unittests work properly. I can debug them and assertion fail results are printed to the Output window. But it seems that unittests don't work at all with any WindowsApp. It's impossible to debug and no assertion fail messages are printed to the Output windows. I think there was a recent change that Runtime.initialize would no longer run the unit tests, so you have to call runModuleUnitTests() yourself from within WinMain.
Re: Template constraints: opCmp and opUnary!"++"
On 12/20/2013 10:57 PM, Timon Gehr wrote: Most non-trivial templates that use is(typeof(...)) in the constraint can be broken. (In the sense that it is possible to instantiate them even though their body does not compile.) Actually, it seems that the behaviour of DMD has changed in this respect. It does not seem to be an issue any longer.
Re: Template constraints: opCmp and opUnary!"++"
On 12/20/2013 09:42 PM, monarch_dodra wrote: On Friday, 20 December 2013 at 17:48:03 UTC, Philippe Sigaud wrote: On Fri, Dec 20, 2013 at 6:33 PM, Francesco Cattoglio wrote: Is there any difference between "is(typeof())" and __traits(compiles, )? I find the latter cleaner: its intent is more apparent. I use is(typeof()) only for really testing for type existence. AFAIK, there is no real difference, but "is(typeof())" is more "idiomatic" in phobos. I used is(typeof(...)) as that was used in the original post, but I think it is actually better to use __traits(compiles,...). The difference is that typeof will not check if all referenced symbols are indeed accessible in the given scope. (Currently __traits(compiles, ...) won't either, but I assume this is a bug.) Most non-trivial templates that use is(typeof(...)) in the constraint can be broken. (In the sense that it is possible to instantiate them even though their body does not compile.)
TypeInfo of interfaces bugg or feature?
When using the typeid expression on a instance of an interface it gives the type of the interface not the type of the underlying object. Is this intended or is it a bug? interface I { } class A : I { } class B : A { } unittest { A a = new A(); B b = new B(); writeln(typeid(a)); //Prints A writeln(typeid(b)); //Prints B a = b; writeln(typeid(b)); //Prints B I i = b; writeln(typeid(i)); //Prints I }
Re: Compilation depends on class methods order
On 2013-12-20 15:28, Andrej Mitrovic wrote: Yeah, it caused many headaches. Fixed thanks to Kenji, of course (who else?). Yeah, he's doing a lot of good work :) -- /Jacob Carlborg
Re: Template constraints: opCmp and opUnary!"++"
On Friday, 20 December 2013 at 17:18:01 UTC, Timon Gehr wrote: On 12/20/2013 05:40 PM, monarch_dodra wrote: That's normal, because "T.init" is not an lvalue. If you need an lvalue, we have `std.traits.lvalueOf!T` which you can use. is(typeof((T v){ /+ use v +/ })) I think this is a lot cleaner. I dunno. Being forced to declare a scope and a list of variables just to have access to an lvalue instance seems a bit verbose to me. I *think* doing this can lead to issues if done inside an inout context (not certain about this. It's a buggy behavior anywyas, Kenji told me, so not a real argument). For example: enum isAssignable(Lhs, Rhs = Lhs) = __traits(compiles, lvalueOf!Lhs = lvalueOf!Rhs); vs enum isAssignable(Lhs, Rhs = Lhs) = __traits(compiles, (Lhs lhs, Rhs rhs){lhs = rhs}); Hum... Actually, I'm not sure which is cleanest. You do bring up a good point. Plus, it solves the whole "initialization issue" we've been having. Why haven't e been using this up to now...? For example, std.range has a lot of: template isInputRange(R) { enum bool isInputRange = is(typeof( (inout int = 0) { R r = void; // can define a range object if (r.empty) {} // can test for empty r.popFront(); // can invoke popFront() auto h = r.front; // can get the front of the range })); } The line "R r = void;" has led to problems before. Why haven't we just used: template isInputRange(R) { enum bool isInputRange = is(typeof( (R r, inout int = 0) { if (r.empty) {} // can test for empty r.popFront(); // can invoke popFront() auto h = r.front; // can get the front of the range })); }
Re: Template constraints: opCmp and opUnary!"++"
On Friday, 20 December 2013 at 17:48:03 UTC, Philippe Sigaud wrote: On Fri, Dec 20, 2013 at 6:33 PM, Francesco Cattoglio wrote: Is there any difference between "is(typeof())" and __traits(compiles, )? I find the latter cleaner: its intent is more apparent. I use is(typeof()) only for really testing for type existence. AFAIK, there is no real difference, but "is(typeof())" is more "idiomatic" in phobos.
Re: std.net.curl - get() is too slow
On Friday, 20 December 2013 at 18:23:30 UTC, Benji wrote: When I call get() function from std.net.curl, I notice it's extremely slow! Maybe 50 times slower than in Python.. Is there any better/faster alternative? Without doing any profiling I'd say this character concatenation while decoding is probably a large source of any slowness. https://github.com/D-Programming-Language/phobos/blob/master/std/net/curl.d#L1908 Switching it to Appender or doing some sort of batch processing would probably help a lot. Even just a .reserve() would probably do wonders.
Re: D references
On Friday, 20 December 2013 at 15:42:29 UTC, Frustrated wrote: (I do believe you can build the docs from the source but I'm not interested in that since it is already done) Try http://ddili.org/ders/d.en/ (by Ali)
Re: D references
On Friday, 20 December 2013 at 18:26:08 UTC, Benji wrote: On Friday, 20 December 2013 at 15:42:29 UTC, Frustrated wrote: (I do believe you can build the docs from the source but I'm not interested in that since it is already done) Try http://ddili.org/ders/d.en/ (by Ali) Sorry, I have got some "sweety birds" in my head now, I haven't understand your question properly :)
std.net.curl - get() is too slow
When I call get() function from std.net.curl, I notice it's extremely slow! Maybe 50 times slower than in Python.. Is there any better/faster alternative?
Re: (emulating) weak typing and some other things
On Fri, Dec 20, 2013 at 09:40:47AM -0800, H. S. Teoh wrote: > On Fri, Dec 20, 2013 at 06:30:53PM +0100, seany wrote: > > I am sorry, perhaps the question could be answered with already > > available information, but I did not manage to figure it completely > > > > I realize that D is a strongly typed language. But in certain > > scenarios i may want to use a weak typing, especially when handling > > structs which are very close to each other in content, but not equal, > > it would be nice to use to redefine the type while preserving the > > name. > [...] > > See std.typecons.Variant. [...] Another way is to use alias this: struct B { int x, y, z; // common fields } struct C { B _common; alias _common this; float p, q, r; } struct D { B _common; alias _common this; string a, b, c; } C c; c.x = 1; // same as c._common.x = 1 c.p = 1.0; D d; d.x = 1; // same as d._common.x = 1 d.a = "abc"; void fun(B b) { ... } fun(c); // OK, same as fun(c._common) fun(d); // OK, same as fun(d._common) Basically, this is the struct equivalent of class inheritance, except without the dynamic polymorphism. If this is not good enough, you can use casts to force structs into each other: struct S { int x; string y; } struct T { int a; float b; } T t; S* ptr = cast(S*) &t; ptr.x = 1; // effectively does t.a = 1. But this is dangerous, since it relies on programming by convention: if the definitions of S and T don't match, the above code will corrupt data instead. Using alias this or std.typecons.Variant is a much better, type-safe solution. T -- Claiming that your operating system is the best in the world because more people use it is like saying McDonalds makes the best food in the world. -- Carl B. Constantine
Re: (emulating) weak typing and some other things
seany: thank you for your patience Beside using Variant or Alebraic, some of your cases can be handled with a "alias this" plus some manual code. struct Foo1 { int x; } struct Foo2 { Foo1 f; int y; alias f this; } Bye, bearophile
Re: Template constraints: opCmp and opUnary!"++"
On Fri, Dec 20, 2013 at 6:31 PM, Francesco Cattoglio wrote: > On Friday, 20 December 2013 at 16:40:23 UTC, monarch_dodra wrote: >>> >>> Everything works as it should, but according to "D Templates: A Tutorial" >>> book, you should not use arguments in constraints. >> >> >> That's news to me. > > It seems strange to me too, but: page 69 on the PDF: > "Do not use argument in your constraint. If you need a value of type T, use > T.init." > Since I don't know D really well, I thought something was wrong with it. Well I wrote this, so I should explain :-) I'm pretty sure at one time, using direct symbols led to strange behavior. And I'm still not sure symbol have values when used in template constraints. What happens when you try ++a on such a symbol? But then, if people tell me using these values directly is perfectly OK, I'll update the text, of course.
Re: Template constraints: opCmp and opUnary!"++"
On Fri, Dec 20, 2013 at 6:33 PM, Francesco Cattoglio wrote: > Is there any difference between "is(typeof())" and > __traits(compiles, )? I find the latter cleaner: its intent is more apparent. I use is(typeof()) only for really testing for type existence.
Re: (emulating) weak typing and some other things
On Fri, Dec 20, 2013 at 06:30:53PM +0100, seany wrote: > I am sorry, perhaps the question could be answered with already > available information, but I did not manage to figure it completely > > I realize that D is a strongly typed language. But in certain > scenarios i may want to use a weak typing, especially when handling > structs which are very close to each other in content, but not equal, > it would be nice to use to redefine the type while preserving the > name. [...] See std.typecons.Variant. T -- The volume of a pizza of thickness a and radius z can be described by the following formula: pi zz a. -- Wouter Verhelst
Re: Template constraints: opCmp and opUnary!"++"
On Friday, 20 December 2013 at 17:18:01 UTC, Timon Gehr wrote: On 12/20/2013 05:40 PM, monarch_dodra wrote: That's normal, because "T.init" is not an lvalue. If you need an lvalue, we have `std.traits.lvalueOf!T` which you can use. is(typeof((T v){ /+ use v +/ })) I think this is a lot cleaner. Is there any difference between "is(typeof())" and __traits(compiles, )?
(emulating) weak typing and some other things
I am sorry, perhaps the question could be answered with already available information, but I did not manage to figure it completely I realize that D is a strongly typed language. But in certain scenarios i may want to use a weak typing, especially when handling structs which are very close to each other in content, but not equal, it would be nice to use to redefine the type while preserving the name. So for example consider struct S_A { //many contents}; and struct S_B { //all contents of S_A + int SomeExtra}; //do something S_A o1; S_B o2; //do some morething if(someCondition) { S_A temp; S_B o1; o1 = o2; //set other stuff of temp in o1 //do the extra processing on the SomeExtra integer } //continue processing o1 For this very particular simple example it is possible to do the same thing without bothering about type conversion. However, in general - although i can not strictly prove it - weak typing could be used to avoid too much branching, while I could, for EACH variation fo the struct possibly (or not) write a if-else braching, I would prefer some easier approach. One approach would be to somehow make the comipler to ignore the shadowing definition, where o1 is redefined as S_B, and another approach can be to dynamically allocate elements to a stack so if(someCondition) { //dynamically allocate the element int SomeExtra //to S_A o1, And then the next question is how to resolve the conflict that o1 WAS a S_A, now has an extra element .. Perhaps tuples would be an approach, but what are the differences between such a dynamic struct and a tuple? thank you for your patience
Re: Template constraints: opCmp and opUnary!"++"
On Friday, 20 December 2013 at 16:40:23 UTC, monarch_dodra wrote: Everything works as it should, but according to "D Templates: A Tutorial" book, you should not use arguments in constraints. That's news to me. It seems strange to me too, but: page 69 on the PDF: "Do not use argument in your constraint. If you need a value of type T, use T.init." Since I don't know D really well, I thought something was wrong with it. That's normal, because "T.init" is not an lvalue. Right! I was suspecting something like this. That said: Seems perfectly legit to me. Then I'll probably stick to it. It's simple, easy to understand, and works. Or maybe the __traits(compiles) actually looks even better. "B" is a type, so "++B" will always resolve to "__error", unless you've implemented a static operator (not sure if even legal?). Best part is: ++B actually works, it's the B < E that fails. But they both smelled bad. Perhaps ++B is some kind of accept-invalid bug then?
Re: Template constraints: opCmp and opUnary!"++"
On 12/20/2013 05:40 PM, monarch_dodra wrote: That's normal, because "T.init" is not an lvalue. If you need an lvalue, we have `std.traits.lvalueOf!T` which you can use. is(typeof((T v){ /+ use v +/ })) I think this is a lot cleaner.
Re: Template constraints: opCmp and opUnary!"++"
On Friday, 20 December 2013 at 15:38:56 UTC, Francesco Cattoglio wrote: I'm trying to experiment a bit around the iota function. If I try to impose the following constraits: Everything works as it should, but according to "D Templates: A Tutorial" book, you should not use arguments in constraints. That's news to me. If I try doing something like: auto my_iota(B, E)(B begin, E end) if (is (typeof(++B.init)) && is (typeof(B.init < E.init))) {} the code stops compiling for integers. That's normal, because "T.init" is not an lvalue. If you need an lvalue, we have `std.traits.lvalueOf!T` which you can use. That said: auto my_iota(B, E)(B begin, E end) if (is (typeof(++begin)) && is (typeof(begin < end))) {} Seems perfectly legit to me. On the other hand the code auto my_iota(B, E)(B begin, E end) if (is (typeof(++B)) && is (typeof(B < E))) {} fails to compile for both integers and my defined types. "B" is a type, so "++B" will always resolve to "__error", unless you've implemented a static operator (not sure if even legal?).
Re: Template constraints: opCmp and opUnary!"++"
> fails to compile for both integers and my defined types. > I read the "D Templates: A Tutorial" book and as far as I can tell > "++B.init" and "B.init < E.init" doesn't look too much wrong, but I've not > seen any constraint of this kind in phobos (using variables instead of > types) so I was wondering if doing something like this is actually bad or > even really bad. (And I also wonder how to properly setting those > constraints directly on types) You could put the target code inside a anonymous block and use __traits(compiles, ...), like this: if (__traits(compiles, { B begin; E end; ++begin; bool stop = begin < end; })) I never hade any problem by using Type.init, that's strange.
Re: Circular Buffer
Use std.range.cycle with std.container.Array (slice the array to get a range). http://dlang.org/phobos/std_range.html#.cycle
Re: Circular Buffer
On 12/20/2013 04:45 PM, Frustrated wrote: I'm in need of a circular buffer/array. I am using std.container.array to avoid the GC. I suppose I could copy and modify the code but is there any easier way? ... What prevents you from implementing your buffer using an std.container.Array as the backing store?
Re: Circular Buffer
On 12/20/13, Frustrated wrote: > But does it rely on the GC? > Nope, the template you wanted is vibe.utils.array:FixedRingBuffer.
Re: Circular Buffer
Frustrated: I'm in need of a circular buffer/array. I am using std.container.array to avoid the GC. Why do you need to avoid the GC? Bye, bearophile
Circular Buffer
I'm in need of a circular buffer/array. I am using std.container.array to avoid the GC. I suppose I could copy and modify the code but is there any easier way? It looks like it is defined as templates so could I somehow hijack the code and modify only what is needed rather than duplicate a lot of stuff? (or maybe someone could just add it to the library... circular arrays are useful ya know ;)
Re: Circular Buffer
But does it rely on the GC?
Re: Circular Buffer
There's actually already a circular buffer implemented in vibe.d, and if I remember right it's not dependent on anything from vibe. On 12/20/13, Frustrated wrote: > I'm in need of a circular buffer/array. I am using > std.container.array to avoid the GC. I suppose I could copy and > modify the code but is there any easier way? It looks like it is > defined as templates so could I somehow hijack the code and > modify only what is needed rather than duplicate a lot of stuff? > (or maybe someone could just add it to the library... circular > arrays are useful ya know ;) > >
Re: D references
(I do believe you can build the docs from the source but I'm not interested in that since it is already done)
D references
Is there a site/page with links to really useful reference material for D? It would be nice to have on the dlang site too. I'm specifically looking for the complete phobo's docs in pdf. I came across them some time ago but can't find them now. (good for offline viewing)
Template constraints: opCmp and opUnary!"++"
I'm trying to experiment a bit around the iota function. If I try to impose the following constraits: auto my_iota(B, E)(B begin, E end) if (is (typeof(++begin)) && is (typeof(begin < end))) {} Everything works as it should, but according to "D Templates: A Tutorial" book, you should not use arguments in constraints. If I try doing something like: auto my_iota(B, E)(B begin, E end) if (is (typeof(++B.init)) && is (typeof(B.init < E.init))) {} the code stops compiling for integers. On the other hand the code auto my_iota(B, E)(B begin, E end) if (is (typeof(++B)) && is (typeof(B < E))) {} fails to compile for both integers and my defined types. I read the "D Templates: A Tutorial" book and as far as I can tell "++B.init" and "B.init < E.init" doesn't look too much wrong, but I've not seen any constraint of this kind in phobos (using variables instead of types) so I was wondering if doing something like this is actually bad or even really bad. (And I also wonder how to properly setting those constraints directly on types)
Re: local variable naming convention
On 2013-12-20 10:15, Boyd wrote: I'm in the process of adapting my library to the D standard naming convention. The problem is that I used to separate member variables and local variables through capitalization. X would be a member variable. x would be a local variable. this allowed me, among other things, to create constructors such as: this(int x, int y) { X = x; Y = y; } So now my question is, how do you distinguish between member and local vars in such cases? This is how I would do it: class Point { private int x_; private int y_; this (int x, int y) { x_ = x; y_ = y; } int x () { return x_; } int y () { return y_; } int x (int x) { return x_ = x; } int y (int y) { return y_ = y; } } If I don't have a conflict with methods I just drop the underscore and use "this." in the constructor: struct Point { int x; int y; this (int x, int y) { this.x = x; this.y = y; } } -- /Jacob Carlborg
Re: local variable naming convention
On 2013-12-20 12:16, Boyd wrote: What does m_ stand for anyway? "member" I would guess. -- /Jacob Carlborg
Re: Compilation depends on class methods order
On 12/20/13, Jacob Carlborg wrote: > On 2013-12-20 09:42, Andrej Mitrovic wrote: > >> That was fixed in 2.064+ > > Cool, finally :) Yeah, it caused many headaches. Fixed thanks to Kenji, of course (who else?).
Re: Compilation depends on class methods order
On 2013-12-20 09:42, Andrej Mitrovic wrote: That was fixed in 2.064+ Cool, finally :) -- /Jacob Carlborg
Re: [Windows] Building in 64bits
Le 20/12/2013 02:54, Rikki Cattermole a écrit : On Thursday, 19 December 2013 at 20:37:32 UTC, Xavier Bigand wrote: I try to build in 64bits with dmd to be able to use VS tools. Please notice on linux our project build fine in 64bits. Here is my error : E:\Dev\Personal\DQuick\src\samples\Minesweeper>dub --arch=x86_64 Checking dependencies in 'E:\Dev\Personal\DQuick\src\samples\Minesweeper' Building configuration "application", build type debug Compiling... Linking... Mine Sweeper.obj : fatal error LNK1179: fichier non valide ou endommagé : '_D6dquick6script5utils162__T31fullyQualifiedNameImplForTypes2TDFC6dquick6script11itemBinding65__T11ItemBindingTC6dquick4item15declarativeItem15DeclarativeItemZ11ItemBindingZvVb0Vb0Vb0Vb0Z29__T20storageClassesStringVk0Z20storageClassesStringFNaNdNfZAya' COMDAT dupliqué --- errorlevel 1179 Error executing command run: Link command failed with exit code 1179 Something hasn't been recompiled. The binary you're trying to link against is an OMF (aka 32bit) library. Microsofts linker use PE-COFF. By my guess recompile DQuick as 64bit. Since you're compiling an example. Ok It's certainly the gdi32.lib that I forgot. Thx
Re: local variable naming convention
On Friday, 20 December 2013 at 09:30:08 UTC, bearophile wrote: kdmult: this(int x, int y) { this.x = x; this.y = y; } In D I prefer: this(int x_, int y_) { this.x = x_; this.y = y_; } Bye, bearophile I tend to use the opposite for private/protected member variables as per the d style guidelines located here: http://dlang.org/dstyle.html. "Unless listed otherwise below, names should be camelCased (this includes all variables). So, names formed by joining multiple words have each word other than the first word capitalized. Also, names do not begin with an underscore ‘_’ unless they are private." Example: this(int x, int y) { this._x = x; this._y = y; }
Re: local variable naming convention
On Friday, 20 December 2013 at 10:29:26 UTC, Jeremy DeHaan wrote: On Friday, 20 December 2013 at 10:06:36 UTC, Jonathan M Davis wrote: Whereas I put the underscore before (e.g. _x), and some folks like to do m_x (though I haven't seen many people do that in D - more in C++). I tend to use the m_x naming convention, though I limit it to private member variables. Otherwise I stick to camelCase. If it is a parameter that is just going to be assigned to a member variable and they would otherwise have the same name, I usually add a prefix to parameter name to differentiate the two. In constructors it is usually "the" and in setters it is usually "new." Something like: this(string theTitle) { title = theTitle; } void setTitle(string newTitle) { title = newTitle; } I've never seen the use of "the" before. I must say I like the sound of it better than using 'title_'. I'm not a big fan of arbitrary signs, even though I use '_title' if there is already setter called 'title' For setter parameters I tend to use 'value', though now that might compromise certain cases where 'value' is already a member. I do occasionally use 'new' as well, so I'll probably start using that. What does m_ stand for anyway?
Re: how to detect OS architecture?
On Wed, 18 Dec 2013 13:43:44 -, Hugo Florentino wrote: On Wed, 18 Dec 2013 13:20:45 -, Regan Heath wrote: On Wed, 18 Dec 2013 04:22:23 -, Hugo Florentino wrote: On Tue, 17 Dec 2013 15:13:18 +0100, Gary Willoughby wrote: Make sure you handle if users have a 32bit OS installed on a 64bit PC. As a matter of fact that was the actual configuration in the system I wrote the app. I am now with a friend with the same configuration, and it also seems to be working. At work I use Windows 7 x86_64 and it also works. It works because the SYSTEM_INFO member "wProcessorArchitecture" is defined to be "The processor architecture of the installed operating system" .. note, *installed operating system*, not processor architecture. Well, isn't that what I needed to begin with? Yes, I was just explaining 'why' it works :) That's why I said OS architecture instead of CPU architecture. Unless you are refering to something else. I was just explaining for posterity/future readers. R -- Using Opera's revolutionary email client: http://www.opera.com/mail/
Re: how to detect OS architecture?
On Thu, 19 Dec 2013 09:41:26 -, Marco Leise wrote: Am Wed, 18 Dec 2013 13:19:09 - schrieb "Regan Heath" : On Tue, 17 Dec 2013 15:13:20 -, Marco Leise wrote: > Am Tue, 17 Dec 2013 13:30:25 - > schrieb "Regan Heath" : > >> On Mon, 16 Dec 2013 21:27:13 -, Hugo Florentino >> wrote: >> >> > On Mon, 16 Dec 2013 20:23:00 +0100, Jacob Carlborg wrote: >> >> On 2013-12-16 17:46, Marco Leise wrote: >> >> >> >>> Hehe, I guess the whole purpose of the launcher is to run in >> >>> 32-bit and detect at runtime if the 64-bit main executable can >> >>> be run or the 32-bit version must be used. >> >> >> >> The only advantage of that is that only a 32bit launcher needs to be >> >> distributed. Perhaps that's the whole idea. >> > >> > It is. :) >> >> "Process Explorer" by sysinternals, now distributed by M$ does something >> similar. >> http://technet.microsoft.com/en-gb/sysinternals/bb896653.aspx >> >> It is a 32 bit exe, which detects the OS bit width and if it's 64 bit >> extracts a 64 exe from within itself to run. When you quit that 64 bit >> exe, it deletes the file it extracted from disk. It's quite a neat >> solution. >> >> R >> > > Only if your executable is self-contained. If you already have > external DLLs or assets you can as well have a launcher and 2 > actual binaries. I don't see why that changes things? Sure, you cannot extract your *static* dependent dlls (those linked at compile time with libs), those have to exist before you can execute your 32 bit launcher. But, if you really wanted to, you could extract and runtime load dlls no problem. R That's my point. If you really wanted, you could do that but you can as well have a launcher and 2 application binaries and avoid this repeated file extraction/deletion and save yourself some troubles at the end of the day. Sure, but having a self contained exe is useful and *cool* :) R -- Using Opera's revolutionary email client: http://www.opera.com/mail/
Re: local variable naming convention
On Friday, 20 December 2013 at 10:06:36 UTC, Jonathan M Davis wrote: Whereas I put the underscore before (e.g. _x), and some folks like to do m_x (though I haven't seen many people do that in D - more in C++). I tend to use the m_x naming convention, though I limit it to private member variables. Otherwise I stick to camelCase. If it is a parameter that is just going to be assigned to a member variable and they would otherwise have the same name, I usually add a prefix to parameter name to differentiate the two. In constructors it is usually "the" and in setters it is usually "new." Something like: this(string theTitle) { title = theTitle; } void setTitle(string newTitle) { title = newTitle; }
Re: How to link to libdl under linux
-L-ldl do not work but pragma(lib, "dl"); works! Wtf?
Re: local variable naming convention
On Friday, December 20, 2013 10:30:06 bearophile wrote: > kdmult: > > this(int x, int y) > > { > > > >this.x = x; > >this.y = y; > > > > } > > In D I prefer: > > this(int x_, int y_) { > this.x = x_; > this.y = y_; > } Whereas I put the underscore before (e.g. _x), and some folks like to do m_x (though I haven't seen many people do that in D - more in C++). It doesn't really matter. But the typical naming conventions have types being PascalCased, and everything else being camelCased, so naming any variables with PascalCasing (or simply making them all uppercase) is definitely not the typical thing to do in D. http://dlang.org/dstyle.html - Jonathan M Davis
Re: local variable naming convention
On Friday, 20 December 2013 at 09:30:08 UTC, bearophile wrote: kdmult: this(int x, int y) { this.x = x; this.y = y; } In D I prefer: this(int x_, int y_) { this.x = x_; this.y = y_; } Bye, bearophile I concur. And I should probably get used to using 'this' a lot as well. Maybe it would be a good idea to add this kind of information to the official coding style guide.
Re: local variable naming convention
kdmult: this(int x, int y) { this.x = x; this.y = y; } In D I prefer: this(int x_, int y_) { this.x = x_; this.y = y_; } Bye, bearophile
Re: local variable naming convention
On Friday, 20 December 2013 at 09:15:26 UTC, Boyd wrote: this(int x, int y) { X = x; Y = y; } So now my question is, how do you distinguish between member and local vars in such cases? this(int x, int y) { this.x = x; this.y = y; }
local variable naming convention
I'm in the process of adapting my library to the D standard naming convention. The problem is that I used to separate member variables and local variables through capitalization. X would be a member variable. x would be a local variable. this allowed me, among other things, to create constructors such as: this(int x, int y) { X = x; Y = y; } So now my question is, how do you distinguish between member and local vars in such cases? Cheers, Boyd
Re: Compilation depends on class methods order
On Friday, 20 December 2013 at 08:42:34 UTC, Andrej Mitrovic wrote: On 12/20/13, kdmult wrote: But why the order of the declarations has an effect on the compilation result. I think you should file this as a bug. Done. https://d.puremagic.com/issues/show_bug.cgi?id=11785
Re: Compilation depends on class methods order
On 12/20/13, kdmult wrote: > But why the order of the > declarations has an effect on the compilation result. I think you should file this as a bug.
Re: Compilation depends on class methods order
On 12/20/13, Jacob Carlborg wrote: > You cannot overload a standard function with a template > function, or has that been fixed? That was fixed in 2.064+
Re: Compilation depends on class methods order
On Friday, 20 December 2013 at 08:03:26 UTC, FreeSlave wrote: Make first read function templated too like this: long read()( ubyte* bytes, long len ) In fact, there are workarouns. But why the order of the declarations has an effect on the compilation result. Namely, if the templated overloaded function goes after the non-templated one then the compilation fails. FAILED: long read( ubyte* bytes, long len ) { return 0; } void read(T)( ref T val ) { read(cast(ubyte*)&val, cast(long)val.sizeof); } Otherwise, if the templated overloaded function goes before the non-templated one then the compilation is successful. SUCCEEDED: void read(T)( ref T val ) { read(cast(ubyte*)&val, cast(long)val.sizeof); } long read( ubyte* bytes, long len ) { return 0; } Why?
Re: Compilation depends on class methods order
Make first read function templated too like this: long read()( ubyte* bytes, long len )