Re: an extremely naive question regarding synchronized...
On Monday, 14 November 2016 at 17:43:37 UTC, WhatMeWorry wrote: I was reading this fasciniating article: https://davesdprogramming.wordpress.com/2013/05/06/low-lock-singletons/ And to quote a section of it: - static MySingleton get() { synchronized { if (instance_ is null) { instance_ = new MySingleton; } } return instance_; } Now, if Thread 1 calls get(), it has a chance to finish instantiating instance_ and storing a reference to it before Thread 2 checks whether instance_ is null. There’s only one problem with this: It comes at a huge performance cost (benchmarks forthcoming). Entering a synchronized block is expensive. - Why is the synchronized block so expensive? Isn't it just doing one conditional and a new command? Again, to my naive way of thinking, this seems like a very small blocking window. And the graph shows 1B get() calls. I assume B stands for billion. What use case would require so many gets? Thanks. Keep in mind, this is only slow for such a large amount of calls. If you're calling this only a hundred times a second, then who cares if it's slower. After all, with GDC we were looking at 1 billion calls in 21 seconds. That's 47,000 calls per *millisecond*.
Re: newbie problem with nothrow
On Monday, 31 October 2016 at 17:04:28 UTC, Temtaime wrote: On Monday, 31 October 2016 at 16:55:51 UTC, WhatMeWorry wrote: Is there a way to turn off nothrow or work around it? Because to me it looks like nothrow prevents me from doing anything useful. extern(C) void onKeyEvent(GLFWwindow* window, int key, int scancode, int action, int modifier) nothrow { if(queue.roomInQueue()) { auto event = new Event; event.type = EventType.keyboard; event.keyboard.key = cast(Key) key; // etc. } Error: function 'event_handler.CircularQueue.roomInQueue' is not nothrow Error: function 'event_handler.onKeyEvent' is nothrow yet may throw The compiler wouldn't let me just remove "nothrow" from the function. I tried a kludge where I had this function just pass all its parameters to another throwable function, but this caused errors as well. So I'm stuck. Anyone know how to proceed. Thanks. Wrap a body of the function to try {} catch {} and it'll work. Assuming you're sure it'll never throw. To enforce this, use try { } catch { throw new Error("blah"); }. You can still throw errors, just not exceptions (as errors are not meant to be caught).
Re: How to debug (potential) GC bugs?
On Sunday, 25 September 2016 at 16:23:11 UTC, Matthias Klumpp wrote: Hello! I am working together with others on the D-based appstream-generator[1] project, which is generating software metadata for "software centers" and other package-manager functionality on Linux distributions, and is used by default on Debian, Ubuntu and Arch Linux. For Ubuntu, some modifications on the code were needed, and apparently for them the code is currently crashing in the GC collection thread: http://paste.debian.net/840490/ The project is running a lot of stuff in parallel and is using the GC (if the extraction is a few seconds slower due to the GC being active, it doesn't matter much). We also link against a lot of 3rd-party libraries and use a big amount of existing C code in the project. So, I would like to know the following things: 1) Is there any caveat when linking to C libraries and using the GC in a project? So far, it seems to be working well, but there have been a few cases where I was suspicious about the GC actually doing something to malloc'ed stuff or C structs present in the bindings. 2) How can one debug issues like the one mentioned above properly? Since it seems to happen in the GC and doesn't give me information on where to start searching for the issue, I am a bit lost. 3) The tool seems to leak memory somewhere and OOMs pretty quickly on some machines. All the stuff using C code frees resources properly though, and using Valgrind on the project is a pain due to large amounts of data being mmapped. I worked around this a while back, but then the GC interfered with Valgrind, making information less useful. Is there any information on how to find memory leaks, or e.g. large structs the GC cannot free because something is still having a needless reference on it? Unfortunately I can't reproduce the crash from 2) myself, it only seems to happen at Ubuntu (but Ubuntu is using some different codepaths too). Any insights would be highly appreciated! Cheers, Matthias [1[: https://github.com/ximion/appstream-generator First, make sure any C threads calling D code use Thread.attachThis (thread_attachThis maybe?). Otherwise the GC will not suspend those threads during a collection which will cause crashes. I'd guess this is your issue. Second, tell the GC of non-GC memory that has pointers to GC memory by using GC.addRange / GC.addRoot as needed. Make sure to remove them once the non-GC memory is deallocated as well, otherwise you'll get memory leaks. The GC collector is also conservative, not precise, so false positives are possible. If you're using 64 bit programs, this shouldn't be much of an issue though. Finally, make sure you're not doing any GC allocations in dtors.
Re: Proper way to work around `Invalid memory operation`?
On Sunday, 25 September 2016 at 16:07:12 UTC, Matthias Klumpp wrote: Hello! I have a class similar to this one: ``` class Dummy { private: string tmpDir; public: this (string fname) { tmpDir = buildPath ("/tmp", fname.baseName); std.file.mkdirRecurse (tmpDir); } ~this () { close (); } void close () { if (std.file.exists (tmpDir)) std.file.rmdirRecurse (tmpDir); } } ``` When the GC calls the classes destructor, I get a `core.exception.InvalidMemoryOperationError@/<...>/ldc/runtime/druntime/src/core/exception.d(693): Invalid memory operation` Looks like rmdirRecurse tries to allocate with the GC, and the GC doesn't like that. Is there any good way to get the temporary directory deletet automatically when the object is freed? At time, I work around this bug by calling close() manually at the appropriate time, but this feel like a rather poor solution. Cheers, Matthias As seen, you can't make GC allocations in dtors. And you should never rely on the GC calling your dtor to close things like file handles anyways. Consider making Dummy a struct and maybe using std.typecons(?).RefCounted with it.
Re: Simple performance question from a newcomer
On Monday, 22 February 2016 at 07:10:23 UTC, Kapps wrote: If you do want to test the differences between the range approach and the loop approach, something like: auto sumtest4(Range)(Range range) @safe pure { return range.reduce!((a, b) => a + b); } is a more fair comparison. I get results within 15% of sumtest2 with this using dmd. I think with ldc this would be identical, but the version in homebrew is too old to compile this. Using LDC with the mir version of ndslice so it compiles, and the following code: sw.reset(); sw.start(); foreach (unused; 0..times) { for (int i=0; i<N; ++i) { res4[i] = sumtest4(f[i]); } } t3 = sw.peek().msecs; and auto sumtest4(Range)(Range range) { return range.reduce!((a, b) => a + b); } I get: 145 ms 19 ms 19 ms 19 ms So, with LDC, there is no performance hit doing this. The only performance hit is when .sum uses a different algorithm for a more accurate result. Also, the LDC version appears to be roughly 5x faster than the DMD version.
Re: Simple performance question from a newcomer
If you do want to test the differences between the range approach and the loop approach, something like: auto sumtest4(Range)(Range range) @safe pure { return range.reduce!((a, b) => a + b); } is a more fair comparison. I get results within 15% of sumtest2 with this using dmd. I think with ldc this would be identical, but the version in homebrew is too old to compile this.
Re: Is this nogc? dmd and gdc disagree
On Saturday, 13 February 2016 at 00:41:35 UTC, tsbockman wrote: On Friday, 12 February 2016 at 23:46:09 UTC, Kapps wrote: You'll encounter this pretty often in Phobos I think. I really don't think @nogc is ready, and tend to avoid it in my code. Exceptions are a big reason for it, and lots of functions in Phobos throw exceptions which prevents them from being used in @nogc (barring ugly hacks). I don't want to discourage you before you try it, but I feel like @nogc is not yet worth using until something is done about issues such as exceptions, allowing Phobos to properly be able to handle @nogc. On the other hand... Realistically, the only way that Phobos will reach usability with @nogc, is if people keep trying and complaining when something doesn't work that should. I guess the problem is that a lot of this stuff requires RC exceptions to be realistically fixable. (Not this case though.) Yeah. I originally intended to go through and make what I needed @nogc, but then I realized that it was pointless thanks to exceptions. Hopefully one day...
Re: Is this nogc? dmd and gdc disagree
On Thursday, 11 February 2016 at 12:41:16 UTC, rcorre wrote: On Thursday, 11 February 2016 at 04:20:13 UTC, tsbockman wrote: On Thursday, 11 February 2016 at 03:09:51 UTC, rcorre wrote: I recently tried compiling enumap with GDC, and found that it disagrees with DMD on whether a function is @nogc. Here's a semi-reduced test-case: Here's an @nogc version of `byKeyValue()`: @nogc auto byKeyValue() const { static immutable keys = [EnumMembers!K]; return zip(keys[], _store[]); } Using zip and slices guarantees that the structure returned will be only 5*size_t.sizeof bytes, regardless of the types of K and V. I'm on the DMD 2.070 release, so maybe its fixed in master. Either way, thanks for the suggestion! Somehow I didn't realize what I was doing was an over-complicated zip :) You'll encounter this pretty often in Phobos I think. I really don't think @nogc is ready, and tend to avoid it in my code. Exceptions are a big reason for it, and lots of functions in Phobos throw exceptions which prevents them from being used in @nogc (barring ugly hacks). I don't want to discourage you before you try it, but I feel like @nogc is not yet worth using until something is done about issues such as exceptions, allowing Phobos to properly be able to handle @nogc.
Re: nogc Array
On Tuesday, 26 January 2016 at 04:31:07 UTC, Igor wrote: On Tuesday, 26 January 2016 at 03:06:40 UTC, maik klein wrote: On Tuesday, 26 January 2016 at 03:03:40 UTC, Igor wrote: Is there a GC-less array that we can use out of the box or do I have to create my own? https://dlang.org/phobos/std_container_array.html How do we use std.algorithm with it? I could like to use find but I have no luck. I have std.container.array!MyClass classes; then std.algorithm.find!("a.myInt == b")(classes, 3) I was hoping this would find the first object in classes who has myInt == 3 but I just get many errors about not being able to find the right definition. I guess std.container.array isn't a range? Or am I using it wrong? First, should be std.container.array.Array!MyClass. However I don't think(?) that the Array struct is a range itself, you might have to use classes[] instead to get a slice of the array.
Re: Voldemort Type Construction Error
On Friday, 15 January 2016 at 20:04:47 UTC, Nordlöw wrote: On Friday, 15 January 2016 at 16:51:24 UTC, Anon wrote: On Friday, 15 January 2016 at 14:04:50 UTC, Nordlöw wrote: What have I missed? In line 126, `static struct Result()` is a template. Either drop the parens there, or change the call on line 187 to `Result!()(haystack, needles)`. Ahh, annoying mistake. Why is this allowed? /Per At least for functions, making them templates provides some benefits like inferring attributes. Not sure if it behaves the same way on structs by making all functions within it templates.
Re: question about the implementation of Variant
On Monday, 4 January 2016 at 09:13:25 UTC, Jonathan M Davis wrote: On Monday, January 04, 2016 07:30:50 aki via Digitalmars-d-learn wrote: But wait, how does GC detect there still be a live reference to the object Foo? Because store is just a fix sized array of bytes. ubyte[size] store; GC cannot be aware of the reference, right? As I understand it, the GC doesn't actually care about whether something is a pointer when it tries to figure out whether something refers to something - or at least, it'll treat integers as if they were pointers so that if you tried to do something like size_t i; { auto p = new int(5); i = cast(size_t)p; } // GC will not collect p even if it runs now then the fact that i matches the value of the address that p points to is enough for the GC to not collect the memory pointed to by p, even if there are no longer any pointers referring to it. This prevents problems when you do stuff like cast pointers to integers to store their values (which normally is crazy but on rare occasions makes sense). The downside is that the GC then has to treat all integers as if they were pointers, so if you have an integer whose value happens to match that of a memory address in GC-allocated memory (a so called false pointer), then that memory won't be freed, even if nothing is really pointing to it anymore. Fortunately, however, false pointers are primarily limited to 32-bit programs, and 64-bit programs don't have that problem because of how large their address space is (but 32-bit programs which allocate most of their address space can definitely run into problems where memory that should be freed isn't thanks to false pointers). - Jonathan M Davis That's only because we don't have a precise garbage collector and can't be relied upon. It's more of a bug / limitation rather than something to actually use. In the case of std.variant, it's not just byte[size] store, it's actually a union: union { ubyte[size] store; // conservatively mark the region as pointers static if (size >= (void*).sizeof) void*[size / (void*).sizeof] p; } Which tells the garbage collector that it may be pointers there, making it valid even for precise garbage collectors (which would have to conservatively handle such a union).
Re: Speeding up text file parser (BLAST tabular format)
On Monday, 14 September 2015 at 18:31:38 UTC, H. S. Teoh wrote: I decided to give the code a spin with `gdc -O3 -pg`. Turns out that the hotspot is in std.array.split, contrary to expectations. :-) Here are the first few lines of the gprof output: [...] Perhaps using the new rangified splitter instead of split would help.
Re: (De)Serializing interfaces
On Saturday, 22 August 2015 at 19:14:16 UTC, nims wrote: I think interfaces are very powerful and I heavily use them. The only problem I have with them is that serializing/deserializing them to XML or JSON doesn't seem to work. So far I got to try Orange and painlessjson. Using Orange all I got was a lot of compiler errors. Painlessjson did compile normally but just ignores all interface class members. I've never used Orange, but one thing you could try is casting your object from MyInterface to Object, and registering the type Foobar like in http://dsource.org/projects/orange/wiki/Tutorials/SerializeBase, then serializing/deserializing it as Object rather than MyInterface. I'm not sure if this will work, but it's worth a try if it doesn't handle interfaces. Interfaces are a bit odd in some ways, as they are not necessarily classes (and thus not implicitly convertible to Object) in situations like with COM / extern(C++).
Re: How disruptive is the GC?
On Wednesday, 29 July 2015 at 17:09:52 UTC, Namespace wrote: On Wednesday, 29 July 2015 at 09:25:50 UTC, Snape wrote: I'm in the early stages of building a little game with OpenGL (in D) and I just want to know the facts about the GC before I decide to either use it or work around it. Lots of people have said lots of things about it, but some of that information is old, so as of today, what effect does the GC have on the smooth operation of a real-time application? Is it pretty noticeable with any use of the GC or only if you're deallocating large chunks at a time? http://3d.benjamin-thaut.de/?p=20 Note that this was 3 years ago, so there have been GC improvements since then. I'm not sure what the results would be like today (or what the code is like in terms of needless allocations). That being said, you probably want to avoid the GC as much as possible for games. Luckily we have tools like -vgc to help with that now (and @nogc, but I still consider this mostly unusable thanks largely to exceptions).
Re: how to avoid cycle detected?
On Wednesday, 1 July 2015 at 09:09:53 UTC, aki wrote: Following code causes run-time error. How can I use static this() without causing error? It's difficult to avoid this situation because actual code is more complex. file main.d: void main() { } file a.d: import b; class A { static this() {} }; file b.d: import a; class B { static this() {} }; object.Exception@src\rt\minfo.d(162): Aborting: Cycle detected between modules w ith ctors/dtors: a - b - a An ugly solution, but the approach used in Phobos is to create something like a_init.d which a.d imports, provided that the static ctors don't actually rely on things from the static ctor of b.
Re: Shouldn't std.conv.emplace be @nogc?
On Monday, 2 March 2015 at 12:37:33 UTC, drug wrote: I guess the reason why std.conv.emplace is not @nogc-ed is that nobody added it yet? I didn't see using of gc in the emplace sources. Soon: https://github.com/D-Programming-Language/phobos/pull/2999
Re: stdio.lines doesn't have popFront, but works with foreach
On Thursday, 11 December 2014 at 20:11:21 UTC, Andrew Klaassen wrote: The docs for stdio.lines say that it's a struct. stdio.lines works with foreach. The docs for foreach say: Iteration over struct and class objects can be done with ranges. For foreach, this means the following properties and methods must be defined: .empty ... .front ... .popFront() But when I try to access any of those properties or methods for stdio.lines, I get compilation errors: 1 import io = std.stdio; 2 3 void main(string[] args) { 4 5 auto infile = io.File(args[1], r); 6 7 auto filelines = io.lines(infile); 8 9 io.writeln(filelines.front); 10 io.writeln(filelines.empty); 11 io.writeln(filelines.popFront()); 12 } test_filechunking.d(9): Error: no property 'front' for type 'lines' test_filechunking.d(10): Error: no property 'empty' for type 'lines' test_filechunking.d(11): Error: no property 'popFront' for type 'lines' Why is this? I'm using ldc2 for compilation, FWIW. Andrew Ranges are one way of allowing foreach. The other is through the use of opApply, which is what std.stdio.lines does. http://dlang.org/statement.html#ForeachStatement
Re: Check type is a struct at compile time?
On Friday, 5 December 2014 at 20:38:31 UTC, Gary Willoughby wrote: How can i check that a type is a struct at compile time? I know i can test for a class like this: static if(is(T == class)) { ... } But how to do the same thing for a struct? Same thing but with struct: is(T == struct) Note that this returns false for things like 'int'. Ex: struct Foo { } void foo(T)(T inst) { static if(is(T == struct)) writeln(T.stringof, is a struct); else writeln(T.stringof, is NOT a struct); } void main() { Foo a; foo(a); foo(3); } -- Foo is a struct int is NOT a struct
Re: [dub] Size of executable
On Thursday, 27 November 2014 at 09:33:49 UTC, Chris wrote: [Maybe this has been asked before.] I usually use dub to create and build projects. I built one of the projects with dub and then by hand with dmd[1] passing all the files etc. Turned out that the executable built with dub was 1.4 MB whereas the one built by hand was only 807 kB. Why is that? Another thing, I've spotted a typo in dub's[2] command line help: clean [package] Removes intermetiate build files and cached build results It should read intermediate (with d), else it sounds like the Goths in Asterix :-) [1] dmd 2.066.0 [2] DUB version 0.9.22, built on Sep 16 2014 Dub builds with debug symbols by default. Using dub build -v will tell you how it invokes DMD.
Re: undefined reference to class template
On Friday, 14 November 2014 at 23:29:34 UTC, Satoshi wrote: Hi, Im using GDC 4.9.0 compiler. I have template classes like public class LinkedList(T) {...} and when I try compile it together, everything works fine. But when I compile every source file to separate object file and link it together with ld Ill get errors like: /os/KernelLand/Kernel/TaskManager/Thread.d:99: undefined reference to `_D7Library10LinkedList45__T10LinkedListTC11TaskManager6Thread6ThreadZ10LinkedList6__ctorMFNaNbNfZC7Library10LinkedList45__T10LinkedListTC11TaskManager6Thread6ThreadZ10LinkedList' Im compiling it with command like: gdc -mcmodel=kernel -nostdlib -mno-red-zone -Wall -masm=intel -frelease -finline-functions -O3 -o obj-x86_64/abc.d.o -c abc.d Here is full error log http://pastebin.com/SjnYjqKh makefile https://github.com/Bloodmanovski/Trinix/blob/dc80f3197f59fe96e9f4e29cea670ff2c7eaa342/KernelLand/Kernel/Makefile#L104 LinkedList class https://github.com/Bloodmanovski/Trinix/blob/dc80f3197f59fe96e9f4e29cea670ff2c7eaa342/KernelLand/Kernel/Library/LinkedList.d Can anyone help me how to solve this problem? Thanks (Sorry for bad english) Sounds like you're not passing in LinkedList.d while compiling a file that uses it. You need to include all used files, including imports, on the command line when compiling. The undefined reference indicates it can't find the source code or di file containing LinkedList. Tools like rdmd do this for you by looking at the imports used automatically. If not that, I'm not sure if this will help, but try using -femit-templates (similar to -allinst in DMD I believe?). Besides that, all I can really suggest is double checking that you're actually including the object file containing LinkedList when you're linking and the source file when compiling.
Re: new(malloc) locks everything in multithreading
On Friday, 24 October 2014 at 10:49:42 UTC, tcak wrote: On Friday, 24 October 2014 at 10:46:57 UTC, tcak wrote: On Friday, 24 October 2014 at 10:29:10 UTC, Kagamin wrote: Looks like your IDE filters too much. Can you configure it to filter less and show address locations? This is what I have found: Main Thread http://i.imgur.com/6ElZ3Fm.png Second Thread (TestThread) http://i.imgur.com/w4y5gYB.png BTW, instead of using Monodevelop with Mono-D, I used same code on a text file, and compiled with dmd test.d, then run with ./test, then everything works fine. When I run it with gdb ./test, then I can see those errors again. Not sure if this is the same issue, but by default gdb breaks on signals that the GC uses, which would explain why it's breaking in gdb but not normally. What happens if you try: handle SIGUSR1 noprint nostop handle SIGUSR2 noprint nostop In GDB before starting execution of the program?
Re: new(malloc) locks everything in multithreading
On Friday, 24 October 2014 at 18:38:39 UTC, tcak wrote: On Friday, 24 October 2014 at 16:51:02 UTC, Kapps wrote: On Friday, 24 October 2014 at 10:49:42 UTC, tcak wrote: Not sure if this is the same issue, but by default gdb breaks on signals that the GC uses, which would explain why it's breaking in gdb but not normally. What happens if you try: handle SIGUSR1 noprint nostop handle SIGUSR2 noprint nostop In GDB before starting execution of the program? This is what I did on shell: (I put some spaces for readability) tolga@tolga:~/dev/d/bug$ dmd -gc -debug test.d tolga@tolga:~/dev/d/bug$ gdb ./test Yes, GDB is stopping on SIGUSR1 / SIGUSR2 since that's the default settings. D's GC uses these signals for suspending / resuming threads during a collection. You need to type what I said above, prior to typing 'run'.
Re: Beginner ?. Why does D suggest to learn java
On Thursday, 16 October 2014 at 22:26:51 UTC, RBfromME wrote: I'm a newbie to programming and have been looking into the D lang as a general purposing language to learn, yet the D overview indicates that java would be a better language to learn for your first programming language. Why? Looks like D is easier than Java... Honestly, I'd recommend starting with VB.net or C# (preferably C#) over D, as: 1) They're simpler, no template magic, not as low level, etc. 2) Having an excellent IDE is very nice for starting out, seeing errors right as you type them, seeing all the methods and how to call them, having the documentation right there in your IDE, and not having to worry about whether what you just wrote is something that the IDE's parser can't handle or is actually invalid code. 3) Being significantly more popular is in general a boon, more tutorials are available (though D has some nice resources like Ali's book), and you're more likely to find a solution to a problem through Google as more people have come across it. 4) Having to deal with any compiler bugs would be very frustrating when starting to learn programming. D still has plenty, even if they're much less noticeable now. Trying to figure out why something doesn't work only to realize it's a compiler bug is frustrating. 5) Having a drag-and-drop GUI designer is very nice. D is still difficult to use for GUIs, and when starting it's really nice to see something significant on the screen right away. 6) You probably won't use most of D's features when you're just learning, so much of D's advantages are gone. D is an awesome language, but I would not recommend it for someone completely new to programming. Once you get the hang of programming, D is an excellent language, until then something simpler, more popular, and more supported, would be better.
Re: Beginner ?. Why does D suggest to learn java
On Tuesday, 21 October 2014 at 09:14:08 UTC, ketmar via Digitalmars-d-learn wrote: On Tue, 21 Oct 2014 09:01:32 + Kapps via Digitalmars-d-learn digitalmars-d-learn@puremagic.com wrote: no template magic that's very bad. it's time to stop making people think that templates are inevitably arcane. I like D's templates, it's one of the things that makes me like D more than C#. But they can definitely get quite complex. C# limits templates to generic types, like Listint, and for a beginner I think that's an easier way to handle things.
Re: Can someone explain how glfw3.dll gets created?
Derelict provides bindings to C libraries, and loads them at runtime. So glfw3.dll is actually an existing C library (you can get it at http://www.glfw.org/download.html), which Derelict provides bindings for. Derelict / your code does not generate the actual dll.
Re: Threadpools, difference between DMD and LDC
On Monday, 4 August 2014 at 05:14:22 UTC, Philippe Sigaud via Digitalmars-d-learn wrote: I have another question: it seems I can spawn hundreds of threads (Heck, even 10_000 is accepted), even when I have 4-8 cores. Is there: is there a limit to the number of threads? I tried a threadpool because in my application I feared having to spawn ~100-200 threads but if that's not the case, I can drastically simplify my code. Is spawning a thread a slow operation in general? Without going into much detail: Threads are heavy, and creating a thread is an expensive operation (which is partially why virtually every standard library includes a ThreadPool). Along with the overhead of creating the thread, you also get the overhead of additional context switches for each thread you have actively running. Context switches are expensive and a significant waste of time where your CPU gets to sit there doing effectively nothing while the OS manages scheduling which thread will go and restoring its context to run again. If you have 10,000 threads even if you won't run into limits of how many threads you can have, this will provide very significant overhead. I haven't looked into detail your code, but consider using the TaskPool if you just want to schedule some tasks to run amongst a few threads, or potentially using Fibers (which are fairly light-weight) instead of Threads.
Re: Programming a Game in D? :D
On Sunday, 3 August 2014 at 03:39:25 UTC, Rikki Cattermole wrote: Lastly the game dev industry is very hesitant to change languages for a lot of reasons. And one of those is platform support. They won't be seeing D on e.g. Xbox One anytime soon if you get my drift. Apparently D already works on the Xbox One using Windows with -m64 (and thus COFF) and Visual Studio's toolchain, at least in conjunction with some C++ (I'm not sure about standalone, though I don't see why not).
Re: Small part of a program : d and c versions performances diff.
Measure a larger number of loops. I understand you're concerned about microseconds, but your benchmark shows nothing because your timer is simply not accurate enough for this. The benchmark that bearophile showed where C took ~2 nanoseconds vs the ~7000 D took heavily implies to me that the C implementation is simply being optimized out and nothing is actually running. All inputs are known at compile-time, the output is known at compile-time, the compiler is perfectly free to simply remove all your code and replace it with the result. I'm somewhat surprised that the D version doesn't do this actually, perhaps because of the dynamic memory allocation. I realize that you can't post your actual code, but this benchmark honestly just has too many flaws to determine anything from. As for startup cost, D will indeed have a higher startup cost than C because of static constructors. Once it's running, it should be very close. If you're looking to start a process that will run for only a few milliseconds, you'd probably want to not use D (or avoid most static constructors, including those in the runtime / standard library).
Re: Small part of a program : d and c versions performances diff.
On Wednesday, 9 July 2014 at 13:18:00 UTC, Larry wrote: You are definitely right, I did mess up while translating ! I run the corrected codes (the ones I was meant to provide :S) and on a slow macbook I end up with : C : 2 D : 15994 Of course when run on very high end machines, this diff is almost non existent but we want to run on very low powered hardware. Ok, even with a longer code, there will always be a launch penalty for d. So I cannot use it for very high performance loops. Shame for us.. :) Thanks and bye This to me pretty much confirms that almost the entirety of your C code is being optimized out and thus not actually executing.
Re: Problem Linking Phobos git master
Possibly something related to: https://github.com/D-Programming-Language/dmd/pull/3715 Have you tried updating to git master today?
Re: import except one?
A bit late, but you should also be able to do: import scriptlike; alias Config = std.process.Config;
Re: httpS post fail at tango
On Thursday, 26 June 2014 at 17:07:30 UTC, JJDuck wrote: On Thursday, 26 June 2014 at 16:33:57 UTC, JJDuck wrote: I tried to use phobos , but there is no such function exists for posting to https too With Phobos, you can use http://dlang.org/phobos/std_net_curl.html#post. Depending on the SSL certificate (i.e., if it's self-signed), you may need to use the C API to cURL and disable SSL verification (http://dlang.org/phobos/etc_c_curl.html). With curl, if it works for http it works for https, provided no certificate issues are found. Tango isn't really used much anymore and Phobos is the official standard library now (though you can use Tango alongside it), so you'd probably have a hard time finding help for Tango on these forums.
Re: Concurrency on Windows (spawn)
On Wednesday, 18 June 2014 at 15:03:55 UTC, Ali Çehreli wrote: On 06/18/2014 06:28 AM, Chris wrote: On Wednesday, 18 June 2014 at 11:57:06 UTC, Chris wrote: Windows: in a D-DLL I'm trying to spawn a thread. However, nothing happens auto myThread = spawn(myFunction, thisTid); send(myThread, arg); The thread is never called. Any ideas? Thanks! PS In an old DLL it used to work, there I called it with only one argument, i.e. spawn(myFunction). Is thisTid messing it up, do I need to pass something else? Mystery solved. There was an audio delay so that the program had already finished, before the thread was properly executed. I _lve_ Windows! Not! That can happen on Linux as well. So, the owner may have to call thread_joinAll() to wait for the worker: import core.thread; auto myThread = spawn(myFunction, thisTid); send(myThread, arg); // ... sometime before the program ends: thread_joinAll(); Ali Alternatively, one should use non-daemon threads for this purpose. http://dlang.org/phobos/core_thread.html#.Thread.isDaemon
Re: what is going on with cgcs.c:351?
Possibly https://issues.dlang.org/show_bug.cgi?id=11763 or https://issues.dlang.org/show_bug.cgi?id=11903
Re: Does __gshared have shared semantics?
On Saturday, 14 June 2014 at 01:24:05 UTC, Mike Franklin wrote: In other words, is 'shared __gshared' redundant? All __gshared does is makes the variable not go into thread-local storage, nothing more. Shared does this, as well as modify the type to be shared(T) instead of just T. So yes, it's redundant.
Re: Source File and Position of User Defined Type
On Tuesday, 10 June 2014 at 20:58:41 UTC, Nordlöw wrote: Is there a way to, programatically (trait), lookup the source file and position of a user defined type either dynamically or, even better, statically? I don't believe this is possible. Perhaps you would be able to generate the .json file and use that at runtime, but I don't know if even that will handle situations like using mixins.
Re: Cannot understand deprecation message recently added to Phobos
On Wednesday, 11 June 2014 at 20:59:25 UTC, Nordlöw wrote: Can somebody explain the meaning of split in the error message Deprecation: function core.time.Duration.weeks is deprecated - Please use split instead. weeks was too frequently confused for total!weeks. given by function shortDurationString() at https://github.com/nordlow/justd/blob/master/pprint.d https://github.com/D-Programming-Language/druntime/pull/825
Re: Class Data Members Name Reflection
On Tuesday, 10 June 2014 at 16:13:31 UTC, Adam D. Ruppe wrote: Two options: do allMembers and filter it out to only be data members, or do some slicing of tupleof.stringof: S s; foreach(idx, member; s.tupleof) { writeln(Name: , s.tupleof[idx].stringof[2..$]); } The tupleof[idx] inside the loop is important instead of just using member because then you get the name, then the slicing is because you get: s.foo for example, and you want to slice off the s. to leave just the name. You may not want to use stringof for this, because stringof is explicitly defined as being able to change across versions, and no actual format is defined. Instead use __traits(identifier, s.tupleof[idx]). Also note that .tupleof will not return static fields.
Re: Class Data Members Name Reflection
On Tuesday, 10 June 2014 at 20:01:37 UTC, Nordlöw wrote: Notice that A.init.tupleof segfaults for classes so that is _not_ an adviced solution in a generic solution! There's no need to use .init: import std.stdio; struct Foo { int a, b; } void main() { writeln(__traits(identifier, Foo.tupleof[0])); }
Re: Basic dynamic array question. Use of new versus no new.
On Wednesday, 11 June 2014 at 02:30:01 UTC, WhatMeWorry wrote: In Mr. Cehreli's book it says Additionally, the length of dynamic arrays can be changed by assigning a value to this property: int[] array; // initially empty array.length = 5; // now has 5 elements while in Mr. Alexandrescu's book, it says To create a dynamic array, use a new expression (§ 2.3.6.1 on page 51) as follows: int[] array = new int[20]; // Create an array of 20 integers Could someone please compare and contrast the two syntaxes. I presume the new command places the 2nd array in heap memory. They both do the same, create an array of n integers on the heap and set the length to n. You can also use .capacity instead of .length to allocate n but not adjust length.
Re: XamarinStudio dependency issues(Mono-D)
On Friday, 16 May 2014 at 00:23:00 UTC, Jack wrote: I recently downloaded Xamarin Studio from the Mono-Develop site(as this was the only available installer on that site) and was looking to try out Mono-D. Then this showed up: http://puu.sh/8NV4V.png Was wondering where I can get those dependencies, or how to solve this particular problem... Thank you The problem occurs because MonoDevelop 5 is coming out, and the 4.2.2 version I believe isn't supported anymore. I think that if you go into Help - Check for Updates and set yourself to the Alpha channel it might work on Windows.
Re: XamarinStudio dependency issues(Mono-D)
On Friday, 16 May 2014 at 01:07:28 UTC, Kapps wrote: On Friday, 16 May 2014 at 00:23:00 UTC, Jack wrote: I recently downloaded Xamarin Studio from the Mono-Develop site(as this was the only available installer on that site) and was looking to try out Mono-D. Then this showed up: http://puu.sh/8NV4V.png Was wondering where I can get those dependencies, or how to solve this particular problem... Thank you The problem occurs because MonoDevelop 5 is coming out, and the 4.2.2 version I believe isn't supported anymore. I think that if you go into Help - Check for Updates and set yourself to the Alpha channel it might work on Windows. I should clarify, I think that the 4.2.2 version isn't supported by Mono-D anymore (might be wrong). The installation instructions say to make sure you're on the alpha channel and thus 4.3. But if this doesn't work, you might get more useful help on http://mono-d.alexanderbothe.com, Alex is quite active and helpful with questions.
Re: Array!T and find are slow
On Wednesday, 14 May 2014 at 17:20:37 UTC, David Nadlinger wrote: On Wednesday, 14 May 2014 at 15:42:13 UTC, Damian Day wrote: On Wednesday, 14 May 2014 at 14:54:57 UTC, David Nadlinger wrote: Could you post a short benchmark snippet explicitly showing the problem? Benchmark found here: http://dpaste.dzfl.pl/0058fc8341830 Unfortunately, I don't have the time to look at the details right now, but https://github.com/D-Programming-Language/phobos/pull/1713 might have improved the situation somewhat. David That pull shows that the previous behaviour was to use enforce? Isn't this very expensive, particularly considering that enforce uses lazy non-scope arguments?
Re: Array!T and find are slow
On Wednesday, 14 May 2014 at 23:50:34 UTC, Meta wrote: On the topic of lazy, why *is* it so slow, exactly? I thought it was just shorthand for taking a function that evaluates the expression, and wrapping said expression in that function at the call site. That is, I thought that: int doSomething(lazy int n) { return n(); } Was more or less equivalent to: int doSomething(int function(int) n) { return n(); } It's more equivalent to: int doSomething(int delegate(int) n) { return n(); } And (I could be very likely wrong here), I believe that it's expensive because it's not scope and possibly requires a closure. Again, very likely may be wrong.
Re: Configuring Phobos from the 1-click installer
On Monday, 12 May 2014 at 15:02:54 UTC, Moses wrote: PATH environment variable is not related at all with phobos2 sources paths. All Linux packages (Ubuntu too) includes -I/usr/include/dmd/phobos on /etc/dmd.conf configuration file. If you need to explicit pass this argument to dmd compiler, may be due to several reasons. - You've edited your /etc/dmd.conf file. - You've created a new dmd.conf on your current directory, on you home directory or on dmd command directory (/usr/bin/). Any dmd.conf file on these places, overrides /etc/dmd.conf Take a look at: $ cat /etc/dmd.conf Regard, I didn't find any extra dmd.conf files, but I found that adding #!/usr/include/dmd/phobos to the top of my D program solved the problem to my satisfaction. Thanks so much for your help. It really does seem like you have an extra dmd.conf that's being loaded. Type dmd -v abc.d - The first few lines should include what config it's using.
Re: Create many objects using threads
On Monday, 5 May 2014 at 22:11:39 UTC, Ali Çehreli wrote: On 05/05/2014 02:38 PM, Kapps wrote: I think that the GC actually blocks when creating objects, and thus multiple threads creating instances would not provide a significant speedup, possibly even a slowdown. Wow! That is the case. :) You'd want to benchmark this to be certain it helps. I did: import std.range; import std.parallelism; class C {} void foo() { auto c = new C; } void main(string[] args) { enum totalElements = 10_000_000; if (args.length 1) { foreach (i; iota(totalElements).parallel) { foo(); } } else { foreach (i; iota(totalElements)) { foo(); } } } Typical run on my system for -O -noboundscheck -inline: $ time ./deneme parallel real0m4.236s user0m4.325s sys 0m9.795s $ time ./deneme real0m0.753s user0m0.748s sys 0m0.003s Ali Huh, that's a much, much, higher impact than I'd expected. I tried with GDC as well (the one in Debian stable, which is unfortunately still 2.055...) and got similar results. I also tried creating only totalCPUs threads and having each of them create NUM_ELEMENTS / totalCPUs objects rather than risking that each creation was a task, and it still seems to be the same. Using malloc and emplace instead of new D, results are about 50% faster for single-threadeded and ~3-4 times faster for multi-threaded (4 cpu 8 thread machine, Linux 64-bit). The multi-threaded version is still twice as slow though. On my Windows laptop (with the program compiled for 32-bit), it did not make a significant difference and the multi-threaded version is still 4 times slower. That being said, I think most malloc implementations while being thread-safe, usually use locks or do not scale well. Code: import std.range; import std.parallelism; import std.datetime; import std.stdio; import core.stdc.stdlib; import std.conv; class C {} void foo() { //auto c = new C; enum size = __traits(classInstanceSize, C); void[] mem = malloc(size)[0..size]; emplace!C(mem); } void createFoos(size_t count) { foreach(i; 0 .. count) { foo(); } } void main(string[] args) { StopWatch sw = StopWatch(AutoStart.yes); enum totalElements = 10_000_000; if (args.length = 1) { foreach (i; iota(totalElements)) { foo(); } } else if(args[1] == tasks) { foreach (i; parallel(iota(totalElements))) { foo(); } } else if(args[1] == parallel) { for(int i = 0; i totalCPUs; i++) { taskPool.put(task(createFoos, totalElements / totalCPUs)); } taskPool.finish(true); } else writeln(Unknown argument ', args[1], '.); sw.stop(); writeln(cast(Duration)sw.peek); } Results (Linux 64-bit): shardsoft:~$ dmd -O -inline -release test.d shardsoft:~$ ./test 552 ms, 729 μs, and 7 hnsecs shardsoft:~$ ./test 532 ms, 139 μs, and 5 hnsecs shardsoft:~$ ./test tasks 1 sec, 171 ms, 126 μs, and 4 hnsecs shardsoft:~$ ./test tasks 1 sec, 38 ms, 468 μs, and 6 hnsecs shardsoft:~$ ./test parallel 1 sec, 146 ms, 738 μs, and 2 hnsecs shardsoft:~$ ./test parallel 1 sec, 268 ms, 195 μs, and 3 hnsecs
Re: Create many objects using threads
On Tuesday, 6 May 2014 at 15:56:11 UTC, Kapps wrote: On Monday, 5 May 2014 at 22:11:39 UTC, Ali Çehreli wrote: On 05/05/2014 02:38 PM, Kapps wrote: I think that the GC actually blocks when creating objects, and thus multiple threads creating instances would not provide a significant speedup, possibly even a slowdown. Wow! That is the case. :) You'd want to benchmark this to be certain it helps. I did: import std.range; import std.parallelism; class C {} void foo() { auto c = new C; } void main(string[] args) { enum totalElements = 10_000_000; if (args.length 1) { foreach (i; iota(totalElements).parallel) { foo(); } } else { foreach (i; iota(totalElements)) { foo(); } } } Typical run on my system for -O -noboundscheck -inline: $ time ./deneme parallel real0m4.236s user0m4.325s sys 0m9.795s $ time ./deneme real0m0.753s user0m0.748s sys 0m0.003s Ali Huh, that's a much, much, higher impact than I'd expected. I tried with GDC as well (the one in Debian stable, which is unfortunately still 2.055...) and got similar results. I also tried creating only totalCPUs threads and having each of them create NUM_ELEMENTS / totalCPUs objects rather than risking that each creation was a task, and it still seems to be the same. snip I tried with using an allocator that never releases memory, rounds up to a power of 2, and is lock-free. The results are quite a bit better. shardsoft:~$ ./test 1 sec, 47 ms, 474 μs, and 4 hnsecs shardsoft:~$ ./test 1 sec, 43 ms, 588 μs, and 2 hnsecs shardsoft:~$ ./test tasks 692 ms, 769 μs, and 8 hnsecs shardsoft:~$ ./test tasks 692 ms, 686 μs, and 8 hnsecs shardsoft:~$ ./test parallel 691 ms, 856 μs, and 9 hnsecs shardsoft:~$ ./test parallel 690 ms, 22 μs, and 3 hnsecs I get similar results on my laptop (which is much faster than the results I got on it using DMD's malloc): test 1 sec, 125 ms, and 847 ╬╝s test 1 sec, 125 ms, 741 ╬╝s, and 6 hnsecs test tasks 556 ms, 613 ╬╝s, and 8 hnsecs test tasks 552 ms and 287 ╬╝s test parallel 554 ms, 542 ╬╝s, and 6 hnsecs test parallel 551 ms, 514 ╬╝s, and 9 hnsecs Code: http://pastie.org/9146326 Unfortunately it doesn't compile with the ancient version of gdc available in Debian, so I couldn't test with that. The results should be quite a bit better since core.atomic would be faster. And frankly, I'm not sure if the allocator actually works properly, but it's just for testing purposes anyways.
Re: Create many objects using threads
On Monday, 5 May 2014 at 17:14:54 UTC, Caslav Sabani wrote: Hi, I have just started to learn D. Its a great language. I am trying to achieve the following but I am not sure is it possible or should be done at all: I want to have one array where I will store like 10 objects. But I want to use 4 threads where each thread will create 25000 objects and store them in array above mentioned. And all 4 threads should be working in parallel because I have 4 core processor for example. I do not care in which order objects are created nor objects should be aware of one another. I just need them stored in array. Can threading help in creating many objects at once? Note that I am beginner at working with threads so any help is welcome :) Thanks I could be wrong here, but I think that the GC actually blocks when creating objects, and thus multiple threads creating instances would not provide a significant speedup, possibly even a slowdown. You'd want to benchmark this to be certain it helps.
Re: Optimize my code =)
On Tuesday, 18 February 2014 at 09:05:33 UTC, Stanislav Blinov wrote: allocationTest ... Time required: 2 hnsecs (o_O) identityMatrixTest ... Time required: 4 hnsecs (o_O) LDC is probably detecting that you're never actually using the results of the operation and that none of the steps have side-effects, so it's optimizing the call out. One way of avoiding this is to do something like writeln the result of an operation.
Re: 64 bit size_t
On Monday, 17 February 2014 at 07:46:02 UTC, Steve Teale wrote: On Monday, 17 February 2014 at 07:17:06 UTC, Steve Teale wrote: What is size_t for 64 bit? Steve Sorry parent.children is just a straightforward array Sorry again - forget about it. I'd forgotten that D actually says int is 32 bits, and ulong is 64, and size_t for a 64 bit machine is obviously 64. I'll just go through the code and either change int to ulong or use a cast. ;=( Rather than change it to int/ulong, just change it to 'size_t len = parent.children.length+1' (or auto instead of size_t). This way it's proper for both 32-bit and 64-bit and you don't need to worry about architecture. If you do need a signed version, you can use ptrdiff_t.
Re: Optimize my code =)
On Monday, 17 February 2014 at 11:34:43 UTC, bearophile wrote: foreach (ref T element; this.data) { element *= scalar; } Try to use: data[] *= scalar; for (auto i = 0; i this.dim.size; ++i) { this.data[i] += other.data[i]; } Try to use: data[] += other.data[]; for (auto i = 0; i this.dim.size; ++i) { this.data[i] -= other.data[i]; } Try to use: data[] -= other.data[]; While it is cleaner, I remember array operations (such as data[] -= other.data[]) being significantly slower than doing it yourself. I don't know if this has been fixed. Perhaps using -m64 helps this. Also, I stress again that if you aren't compiling for 64-bit (-m64), it's very likely to give a significant improvement (because the optimizer will probably convert some of your operations into SIMD operations). Using LDC / GDC would also give a significant improvement.
Re: Optimize my code =)
On Friday, 14 February 2014 at 16:00:09 UTC, Robin wrote: As I am very new to D I instantly ran into certain optimizing issues. E.g. the simple matrix multiplication based in my java implementation requires about 1.5 secs for multiplying two 1000x1000 matrices, however my D implementation requires 39 seconds without compiler optimizations and about 14 seconds with -inline, -O, -noboundscheck and -release. So I am sure that I just missed some possible optimization routines for D and that I could miss entire patters used in D to write more optimized code - especially when looking at the const and immutability concepts. Try with and without -noboundscheck. Sometimes using it seems to make things slower, which is odd. Also, compiling for 64-bit may help significantly. When you compile for 32-bit, you won't get benefits of SIMD instructions as it's not guaranteed to be supported by the CPU. Since Java runs a JIT, it would use these SIMD instructions. Also, you'll get significantly faster code if you use LDC or GDC. class Matrix(T = double) { private T[] data; private Dimension dim; } This should be final class or struct, you don't need virtual methods. This is my class with its templated data as a one dimensional array (as I don't like jagged-arrays) and a dimension (which is a struct). The dimension object has some util functionality such as getting the total size or mapping (row, col) to a one-dimensional index besides the getter for rows and columns. this(size_t rows, size_t cols) { this.dim = Dimension(rows, cols); this.data = new T[this.dim.size]; enum nil = to!T(0); foreach(ref T element; this.data) element = nil; } You don't need to!T for setting to 0, just use plain 0. Using this to will probably result in overhead. Note that this may evaluated every time you use 'nil', so using a constant will help. T opIndex(size_t row, size_t col) const { immutable size_t i = this.dim.offset(row, col); if (i = this.dim.size) { // TODO - have to learn exception handling in D first. :P } return this.data[i]; } You're using -noboundscheck then manually implementing bounds checks, and probably less efficiently than the compiler does. Either change this to an assert, or remove it. In either case, the compiler will do it's own built in bounds checking. This call is especially expensive since you're doing entirely virtual methods because you specified class instead of final class or using a struct. None of your Matrix calls will be inlined. Which calls: size_t size() @property const { return this.rows * this.cols; } I think and hope that this is getting optimized via inlining. =) This works similar for opIndexAssign. Not unless you final class / struct. The function I am mainly benchmarking is the simple matrix multiplication where one of the multiplied matrices is tranposed first in order to improve cache hit ratio. Matrix opMul(ref const(Matrix) other) { if (this.dim.rows != other.dim.cols || this.dim.cols != ther.dim.rows) { // TODO - still have to learn exception handling first ... } auto m = new Matrix(this.dim.rows, other.dim.cols); auto s = new Matrix(other).transposeAssign(); size_t r1, r2, c; T sum; for (r1 = 0; r1 this.dim.rows; ++r1) { for (r2 = 0; r2 other.dim.rows; ++r2) { sum = to!T(0); for (c = 0; c this.dim.cols; ++c) { sum += this[r1, c] * other[r2, c]; } m[r1, r2] = sum; } } return m; } These allocations may potentially hurt. Also, again, the virtual calls here are a huge hit. Using to!T(0) is also a waste of performance, as youc an just do straight 0. I am aware that there are faster algorithms for matrix multiplication but I am mainly learning how to write efficient D code in general and not based on any algorithm. Using SIMD instructions manually would of course be much, much, faster, but I understand that it defeats the point somewhat and is much more ugly. This is more or less the same algorithm I am using with java and c++. Both require about 1.5 secs (after java warm-up) to perform this task for two 1000x1000 matrices. D compiled with DMD takes about 14 seconds with all (known-to-me) optimize flag activated. (listed above) If you used LDC or GDC 64-bit with the changes above, I'd guess it would be similar. I wouldn't expect D to out-perform Java much for this particular scenario, there's very little going on and the JIT should be able to optimize it quite well with SIMD stuff. I wanted to make s an immutable matrix in order to hopefully improve performance via this change, however I wasn't technically able to do this to be honest. I don't think this would improve performance.
Re: std.algorithm for changing array values
On Wednesday, 15 January 2014 at 20:34:32 UTC, Andre wrote: foreach(entry;entries){ if (entry.key == 3){ entry.value = 42; found = true; } } One thing to keep in mind is that structs are passed by value, so this foreach would be operating on a copy of the entry. So your setting the value to 42 would have no effect. Instead you would need foreach(ref entry; entries) in order to have the change take effect (regardless of whether or not you use std.algorithm).
Re: Server is not active?
This is just a guess, but it is because you're setting the socket to be blocking after the call to accept? If it defaults to non-blocking, this would cause accept to return immediately, so the client connecting would fail as the server isn't currently accepting connections. Also to verify it's not a firewall issue, for connecting try using 127.0.0.1.
Re: Support implicit conversion between types
On Wednesday, 4 September 2013 at 21:14:26 UTC, Ali Çehreli wrote: On 09/04/2013 01:46 PM, Adam D. Ruppe wrote: D does not support implicit struct construction. That's what I knew. Interestingly though, it *does* support it for functions taking classes: class Foo { this(int i) {} } void foo(Foo f...) {} void main() { foo(10); } WHAT? :) It even new's one? But it works only for the ellipsis. I wonder why the discrepancy... Ali http://dlang.org/function.html Under Typesafe Variadic Functions - For class objects.
Re: Tools for building a dynamic derived type? I need a push in the right direction.
On Tuesday, 20 August 2013 at 18:55:44 UTC, Gary Willoughby wrote: I've been researching ways to accomplish creating a template that creates a special kind of derived type and i think i need a push in the right direction. Take this simple class: class Person { private string _name; private int _age; this(string name, int age) { this._name = name; this._age = age; } public string getName() { return this._name; } public int getAge() { return this._age; } } I want to create a mock of this class which would mean achieving the following: 1). Extend the class 2). Override all public methods to do nothing (or look for enabled methods) 3). Provide a way of dynamically enabling methods with new return values Extending the class is pretty easy and adding methods dynamically looks to be solved (TDPL 12.11.1) but it's the override all public methods to do something different which is beating me. I know it will probably involve mixins and dealing with tuples somewhere along the line but documentation is lacking everywhere i look. std.traits gives me information about a type but using that information is where i need the documentation. e.g. i know the traits methods return tuples but how do you work with these tuples? how to Iterate through them? I seem to always get stuck when trying to iterate through tuples and generate compiler errors. I've taken a look at the std.typecons source especially BlackHole and WhiteHole templates but i get lost. They are almost doing what i want but for abstract methods. The general usage is probably going to be something like this: class Mock(T) : T { // Implementation } auto cat = Mock!Cat(Ginger); // constructors supported. auto person = Mock!Person(); person.addMethod(getName, delegate(){ return Foo; }); person.addMethod(getAge, delegate(){ return 10; }); Any help will be greatly appreciated. AutoImplement (http://dlang.org/phobos/std_typecons.html#.AutoImplement) from std.typecons should do what you want. Instead of implementing only abstract methods, you could make it implement all non-final methods by changing the 'what' template parameter to simply return true (final methods are skipped regardless). Then you could change the 'how' template parameter to return ReturnType!parent.init unless an argument is set in an AA. I can't say I've ever tried this though, so I'm not sure how well it would work in reality. https://github.com/QAston/DMocks-revived may interest you as well.
Getting vtable for inherited Interface instance
I'm trying to implement a runtime reflection module, and am having some issues with figuring out the function pointer to invoke an interface on a class that derives from the one that implements the interface. For example, given the following code, we can call an interface function using a delegate with http://pastie.org/8255612 - but even with the derived instance passed in it will invoke Bar's implementation as we're using the function pointer for Bar's implementation. I figured typeid(DerivedBar).interfaces would return it's own Interface instance for DerivedBar, but it doesn't and instead Bar's has to be used. The ABI page doesn't seem to mention much about inheriting from a class that implements an interface and overrides it's functions. Is there a way for me to get the function pointer to the overridden version of foo?
Re: Getting vtable for inherited Interface instance
I should mention that there's no knowledge of Bar nor DerivedBar at compile-time, but there is of Foo. The vtable index of bar within Foo is known as well, but without knowledge of Bar or DerivedBar I can't just do the same with their implementation.
Re: how to get enclosing function as symbol ? (eg: __function__.stringof ==__FUNCTION__)
On Sunday, 18 August 2013 at 01:52:50 UTC, Timothee Cour wrote: Is there any way to get the enclosing function as symbol ? I'd like something like that: alternative names would be: __function__ __context__ auto fun(alias caller=__function__)(){ //caller represents fun1!double return ReturnType!caller.init; } T fun1(T)(T x){ assert(__function__.stringof==__FUNCTION__); alias fun=__function__; assert( is(ReturnType! __function__) == T); return fun(); } void main(){fun1!double();} I don't think you can pass it in to the function, but you can use __traits(parent) on a variable within the function to get the function.
Re: Struct's alignment
On Saturday, 10 August 2013 at 20:36:24 UTC, Temtaime wrote: Hello, guys! I have Matrix class(that contains an array of 16 floats) and SSE code to mult it. It's neccessary to have an array alignment 16. I'm figured out simple test-code: align(16) struct S { align(16) int a; } void main() { align(16) S s; writeln(cast(void *)s.a); } And it prints 18FCC8, but must ends with 0. What i'm doing wrong? Thanks. Perhaps core.simd (http://dlang.org/phobos/core_simd.html) could be of help. I believe that those types should be aligned.
Re: Win32 + OpenGL bindings
On Saturday, 20 April 2013 at 03:26:29 UTC, Diggory wrote: I've been trying to write a win32 app using opengl in D, but none of the bindings I've found have been sufficient: - core.sys.windows.windows: Missing large parts of wingdi.h, including PFD_* constants, ChoosePixelFormat(), SwapBuffers(), wgl*() functions. - win32.windows: Apparantly out of date and gives linker errors, although it does declare all the functions needed. - derelict.util.wintypes: Declares a small number of useful windows functions, many of which conflict with those declared in core.sys.windows.windows (such as PIXELFORMATDESCRIPTOR). However, SetPixelFormat is not declared. - derelict.opengl.gl: Has all of opengl plus wgl* functions needed for windows, but has more dependencies than an ideal opengl binding would have. Why isn't there a simple relationship between C/C++ header files and D modules, instead of this weird mix where some things are duplicated and others not declared at all? All of the windows specific functions including wgl* are supposed to be in windows.h, and opengl functions in gl/gl.h It's a shame because I really like the ideas behind D - in fact the reason I found it is that I'd come up with a whole bunch of ideas I wanted in an ideal language and it turned out D already implemented them all... Deimos has some OpenGL bindings for up to 3.1 core here https://github.com/D-Programming-Deimos/OpenGL/tree/master/deimos/gl I also have my own that are up to 4.2 core here https://bitbucket.org/Kapps/shardgraphics/src (gl.d, glfuncs.d, gltypes.d, and possibly glfw.d if you need that), which include loading the function pointers, but there may be some licensing issues because they're parsed from the OpenGL man pages. Also there may be some incorrect functions in mine because of parsing errors.
Re: foreach for ranges?
On Wednesday, 18 July 2012 at 04:54:51 UTC, Jonathan M Davis wrote: On Wednesday, July 18, 2012 06:27:28 Mike L. wrote: Thanks for the reply. Not sure how I missed it there. Interesting that the compiler has to be made aware of a concept that I had thought was only supposed to be part of phobos. Would it be possible to implement it in std.range using the new UFCs? You can do for(; !range.empty; range.popFront()) { auto e = range.front; } without the compiler doing anything at all. But if you want for(e; range) {} you need a way in the language for the compiler to translate that into the above. UFCS has nothing to do with it. All UFCS does is take a.b(c, d) and make it b(a, c, d). - Jonathan M Davi If UFCS worked on operators, you would be able to make ranges without any compiler support. int opApply(T)(T Range) if(isInputRange!T) { // Stuff. }
Re: align(16) struct member throws an exception with movdqa
On Monday, 11 June 2012 at 03:19:08 UTC, ixid wrote: struct a { align(16) int[4] test = [1,2,3,4]; } a test; asm { movdqa XMM0, test ; addps XMM0, XMM0; movdpa test, XMM0 ; } This works fine with unaligned movdqu but throws an access violation exception with movdqa. Why isn't align letting me do an aligned read? How should I do an aligned read? IIRC, you're supposed to be able to do something like align(16) struct a, but it doesn't work when a is created on the stack. That was the conclusion I found when trying to implement my own vector type a year ago anyways.
Re: shared status
On Saturday, 14 April 2012 at 10:48:16 UTC, Luis Panadero Guardeño wrote: What is the status of shared types ? I try it with gdmd v4.6.3 And I not get any warring/error when I do anything over a shared variable without using atomicOp. It's normal ? shared ushort ram[ram_size]; ram[i] = cast(ushort) (bytes[0] | bytes[1] 8); Shared is at the moment (in my opinion anyways) not useable. Very little in Phobos is shared friendly. Most benefits of shared aren't implemented yet. I personally avoid it.
Re: D slower ~1s from C ?!
On Thursday, 5 April 2012 at 17:22:38 UTC, Minas wrote: Many of you should know the website projecteuler.net, where there are mathematical problems to solve with computers. I am doing those in D, and after I finished one today, I decided to compile it in C as well to compare the results. The problem was: The number 3797 has an interesting property. Being prime itself, it is possible to continuously remove digits from left to right, and remain prime at each stage: 3797, 797, 97, and 7. Similarly we can work from right to left: 3797, 379, 37, and 3. Find the sum of the only eleven primes that are both truncatable from left to right and right to left. NOTE: 2, 3, 5, and 7 are not considered to be truncatable primes. My solution in D: First, you should compile with -O -release -inline and, in this case, -noboundscheck. The main issue here seems to be the for loop. Changing: for(ulong i = 2; i = cast (ulong)sqrt(cast(double)n+1); ++i) if( n % i == 0 ) return false; To: ulong End = cast (ulong)sqrt(cast(double)n+1); for(ulong i = 2; i = End; ++i) if( n % i == 0 ) return false; Results in a 26 times performance increase for me, based off of using a StopWatch at start of main and stopping it at end of main. It's possible that the C compiler can recognize that this is a constant expression (sqrt might be an intrinsic). D should be able to do this even better; sqrt is strongly pure and takes in arguments that do not change, thus it should be able to automatically make the change I did above. It (at least DMD) does not seem to however. I did not try the C version, and the D version was compiled with DMD on Windows.
Re: HelloWordl in Webserver
On Saturday, 17 March 2012 at 20:52:33 UTC, Xan wrote: So, there is not built-in functions? Thanks, Xan. There's no built in webserver class, and it's not something that should be in the standard library in the first place.
Re: Method invocation -- why it's not working?
On Thursday, 8 March 2012 at 07:53:02 UTC, Jonathan M Davis wrote: It would be nice, but I honestly don't understand the people who think that the lack of it is crippling. It's just one of those nice-to-have features. Most languages don't have anything of the sort. - Jonathan M Davis Speaking of UFCS... https://github.com/D-Programming-Language/dmd/commit/b7742f7a733ff73d364c6ed54af70d875d7e911b :D
Re: MySQL connection strange behavior (again...)
On Wednesday, 22 February 2012 at 21:18:32 UTC, miazo wrote: Problem solved. :-) I found that it was @4 suffix that was missing. With a libmysql.def file as below: LIBRARY libmysql EXETYPE NT SUBSYSTEM WINDOWS EXPORTS _mysql_init@4 = mysql_init I was able to generate working libmysql.lib file with implib (with /system switch). That, with changing from extern (C) to extern (System), removed the problematic issue. Thank you for all your hints! You shouldn't have to manually create a .def file. Try using coffimplib (I think it's bundled with dmc?) instead of implib and use it on libmysql.lib (coffimplib libmysql.lib _libmysql.lib, back up the original libmysql.lib, replace the original with the generated _libmysql.lib, and then link to it). Then create your headers with extern(System). It seems that adding it manually into the .def file is working for you, but it's a lot more effort than needed.
Re: MySQL
The way I did it is 1) Download C connector from mysql's website, 6.0.2 is version headers were made for. Remember you'll need the 32-bit one if you're using DMD on Windows. 2) Create the binding functions using extern(System). 3) For Windows, use 'coffimplib libmysql.dll libmysql.lib', and build with PathToFile/libmysql.lib. Example: 'dmd test.d libmysql.lib' 3b) For Linux, just link to libmysqlclient. a with -Llibmysqlclient.a or by just passing path. 4) Make sure that libmysql.dll (for Windows) is in the application folder otherwise you'll get errors when trying to run. On 21/01/2012 3:38 PM, Mars wrote: Hello everyone. I've been trying to use MySQL in an application on Windows, but I always get Symbol Undefined _mysql_init I've put the lib in the correct folder, so I don't know what the problem might be. I've tried several libs, and tried to compile it myself (always converted using coffimplib), but it fails, no matter what. I've also tried to make a def file out of the lib, and the functions are definitly listed as exports there. Any idea what I might doing wrong? Mars
Re: Reading web pages
The host is www.google.com - http is only a web protocol. The DNS lookup is independent of HTTP, and thus should not include it. Note that you're also missing a space after the GET. Also, in terms of the example given, some servers won't like you not using the Host header, some won't like the GET being an absolute path instead of relative (but the two combined should make most accept it). There's a CURL wrapper added, and a higher level version should be available within the next release or two, you make want to look into that. On 19/01/2012 9:30 AM, Xan xan wrote: Hi, I want to simply code a script to get the url as string in D 2.0. I have this code: //D 2.0 //gdmd-4.6 import std.stdio, std.string, std.conv, std.stream; import std.socket, std.socketstream; int main(string [] args) { if (args.length 2) { writeln(Usage:); writeln( ./aranya {url1,url2, ...}); return 0; } else { foreach (a; args[1..$]) { Socket sock = new TcpSocket(new InternetAddress(a, 80)); scope(exit) sock.close(); Stream ss = new SocketStream(sock); ss.writeString(GET ~ a ~ HTTP/1.1\r\n); writeln(ss); } return 0; } } but when I use it, I receive: $ ./aranya http://www.google.com std.socket.AddressException@../../../src/libphobos/std/socket.d(697): Unable to resolve host 'http://www.google.com' What fails? Thanks in advance, Xan.
Re: associative arrays
Looks like this is fixed for 2.058. https://github.com/D-Programming-Language/dmd/commit/3e23b0f5834acb32eaee20d88c30ead7e03bb2f4 On 08/01/2012 3:43 AM, Jonathan M Davis wrote: On Sunday, January 08, 2012 03:24:22 Kapps wrote: Ah, found the bug / pull request. https://github.com/D-Programming-Language/dmd/pull/597 http://d.puremagic.com/issues/show_bug.cgi?id=4523 Ah, TDPL says that it returns bool. Well, then it definitely needs to be changed, and it's good to see that that there's a pull request for it. So, it should be fixed in the next release. In fact, the number of TDPL-related bugs fixed for the next release should be quite high, which is great. - Jonathan M Davis
Re: associative arrays
Ah, found the bug / pull request. https://github.com/D-Programming-Language/dmd/pull/597 http://d.puremagic.com/issues/show_bug.cgi?id=4523 On 08/01/2012 1:39 AM, Kapps wrote: For most languages (such as C# and maybe Java), the Remove method on collections returns a boolean indicating whether it was removed. So you could write: enforce(MyAA.remove(lenght)) or bool Result = MyAA.remove(lenght); assert(Result); I'm not sure why it doesn't in D, but I thought I remembered seeing a pull request or change that added it. Maybe I'm imagining things since I can't find it now. On 07/01/2012 4:11 PM, RenatoL wrote: Very quick question import std.stdio; void main() { auto arr1 = [uno:1, due:2, tre:3]; arr1.remove(xxx); } also in this case the compiler does not say anything and the program goes out silently ... why? Would not it be better if an exception was raised? After all if i write: writeln(arr1[xxx]); runtime expresses its disappointment...
Re: associative arrays
For most languages (such as C# and maybe Java), the Remove method on collections returns a boolean indicating whether it was removed. So you could write: enforce(MyAA.remove(lenght)) or bool Result = MyAA.remove(lenght); assert(Result); I'm not sure why it doesn't in D, but I thought I remembered seeing a pull request or change that added it. Maybe I'm imagining things since I can't find it now. On 07/01/2012 4:11 PM, RenatoL wrote: Very quick question import std.stdio; void main() { auto arr1 = [uno:1, due:2, tre:3]; arr1.remove(xxx); } also in this case the compiler does not say anything and the program goes out silently ... why? Would not it be better if an exception was raised? After all if i write: writeln(arr1[xxx]); runtime expresses its disappointment...
Re: Make a variable single-assignment?
For one reason, public fields that lack a set without having to create a backing field, followed by a bulky property. It does sound lazy, but when it's something you have to repeat many times, it gets annoying. On 21/11/2011 9:43 AM, Ary Manzana wrote: On 11/21/11 11:04 AM, Alex Rønne Petersen wrote: Hi, Is there any way to make a variable single-assignment, regardless of its type? I.e.: void foo() { some magical keyword? int i = 0; i = 2; // Error: i cannot be reassigned } I realize const and immutable will do this, but they are transitive and infect the type, which I do *not* want. I simply want the variable to be single-assignment. Is it possible? - Alex Why do you want that?