Re: Adapting foreign iterators to D ranges
On Monday, 22 April 2024 at 11:36:43 UTC, Chloé wrote: The first implementation has the advantage is being simpler and empty being const, but has the downside that next is called even if the range ends up not being used. Is either approach used consistently across the D ecosystem? You can also place initialization logic inside front, then empty could become const. I don't think there is a preffered way of initializing such ranges, so imho consider what's best for your use case.
Re: impure
On Monday, 8 April 2024 at 07:53:01 UTC, Dom DiSc wrote: On Sunday, 24 March 2024 at 07:41:41 UTC, Dom DiSc wrote: Try `debug unittest {...}`? Cool. This seems to work. That's a nice workaroud for tests. Yay! Nice, fyi, you can use it with statements inside function bodies as well. Usefull for doing logging in pure functions.
Re: impure
On Sunday, 24 March 2024 at 07:41:41 UTC, Dom DiSc wrote: I'm creating a library that is completely pure, but it doesn't compile with pure: at the top because of one impure unittest (which uses random to test some things only probabilistic)! So do I really need to declare every function pure individually because of a test?!? Can we please have a @impure attribute? And by the way also @throws and @gc? That would make live so much easier... Try `debug unittest {...}`?
Re: Branching of a discussion in forums?
On Monday, 29 January 2024 at 14:59:23 UTC, Richard (Rikki) Andrew Cattermole wrote: If you are using a NewsGroup reader like ThunderBird it should be possible to branch off and post in a different one. What about web interface? Although nobody does that, normally people rename the subject instead. Well some questions are not suitable for announce group.
Branching of a discussion in forums?
Hi everyone, So just wondering is it possible to branch off a thread into new one (viewable as separate item in forum group)? Also, is it possible to branch into a different gruop all toghether? I.e. from "blabla" thread in announce to "some other thing" thread in learn for example? Thanks, Alexandru
Re: opApply + const
On Tuesday, 23 January 2024 at 16:11:25 UTC, ryuukk_ wrote: Hello, I have the following: ```D struct Stuff { int opApply(scope int delegate(Stuff*) dg) { return 0; } }; void main() { Stuff* stuff; foreach(it; *stuff) {} } ``` It works fine.. but when the variable becomes ``const(Stuff)* stuff;`` It gives me: ``` onlineapp.d(13): Error: cannot uniquely infer `foreach` argument types ``` I have no idea what i should be doing, does anyone have a clue? Try making opApply const.
Re: Web APis
On Sunday, 31 December 2023 at 04:40:02 UTC, Axel Casillas wrote: Hi there, I'm trying to implement web api's into a terminal program. With some help at the IRC have gotten pretty far but just hit a roadblock trying to manipulate the web api to accept input from the user. Example: auto content = get("www.webapiurl.com/data/v4/example?name=category&from=2022-01-24&to=2023-01-24&apikey=01010101010101010101"); writefln! %s (content); the above is just an example and for the most part it works but I am unable to make the 'category','from=date' and 'to=date' a user modified variable. It doesn't matter how I attempt to split the API into different sections and define variables before running the program it wont compile. Has anybody ever run into this and if someone has could you point me to some example code that might make it ease for me to understand, would greatly appreciate. Perhaps:? ```d auto content = get(format("www.webapiurl.com/data/v4/example?name=category&from=%s&to=%s&apikey=01010101010101010101", fromDate, toDate)); writefln!"%s"(content); ``` Best regards, Alexandru
Re: How to implement filterMap
On Sunday, 31 December 2023 at 09:47:27 UTC, Siarhei Siamashka wrote: Also take a look at the `c` array. The handling of arithmetic overflows is a safety problem of the D language design. Certain types of input may cause overflows, which result in producing bogus data as a result of running your program and are very difficult to troubleshoot. The use of the GDC's `-ftrapv` option surely helps in troubleshooting such cases, but some software or D libraries may intentionally rely on the D's arithmetic wraparound feature. `CheckedInt` should be another solution for overflows, if you really need it to throw exceptions, on overflow errors.
Re: Operator "+=" overloading for class?
On Sunday, 17 December 2023 at 04:13:20 UTC, Ki Rill wrote: I am trying to overload `opOpAssign` for my class. The code compiles, but it does not seem to be working. ```d // binary operations have already been implemented for Value // i need +=, -=, *=, /= auto opOpAssign(string op)(Value rhs) { mixin("return this" ~ op ~ "rhs;"); } auto opOpAssign(string op)(in ElementType rhs) { mixin("return this" ~ op ~ "rhs;"); } ``` What am I missing here? Full project code can be found [here](https://github.com/rillki/tiny-grad). Perhaps: ```d auto opOpAssign(string op)(Value other) { mixin("this.v " ~ op ~ "= other.v;"); return this; } ```
Re: interface opEquals
On Monday, 27 November 2023 at 09:53:48 UTC, Antonio wrote: ...but why? All classes (and interfaces I think), at root of inheritance have `Object` class, this class defines couple of generic methods, you can find this class in object.d btw. One of those methods is `bool opEquals(const Object rhs) const`, therefore if you try to call opEquals, it could be possible that in some cricumstances instead of your overload, one defined on Object is picked up, which checks only if rhs is same object as the one invoked upon. Btw, dunno how the rules for overload set resolution on opEquals work, so someone else should check whther this is a bug or expected behavior. Best regards, Alexandru.
Re: interface opEquals
On Friday, 24 November 2023 at 17:39:10 UTC, Antonio wrote: ... Dunno if this might help, but I noticed that `==` sometimes calls `opEquals(const Object) const` instead of overload defined on class/interface, you might try and override it as well, and delegate to your overload that deals directly with `IOpt`. Best regards, Alexandru.
Re: How can I get the total memory size of a Jagged Array
On Monday, 13 November 2023 at 14:15:31 UTC, seany wrote: Is there a better way? I want a method that works for every variable type including classes and objects. Thank you Perhaps, use length property of string. It should tell you length of a string and then you multiply it by size of char.
Re: Struct copy constructor with inout
On Tuesday, 14 November 2023 at 08:50:34 UTC, dhs wrote: In other words: why doesn't ss2=s2 fail here? Thanks, dhs Seems like it isn't called at all, your copy constructor with inout. Could be a bug. My assumption is that default copy constructors are generated alongside inout one, and then picked up for your initialization instead of inout one. Best regards, Alexandru.
Re: Pure D frontend as library.
On Monday, 26 December 2022 at 23:08:59 UTC, Richard (Rikki) Andrew Cattermole wrote: ... That on the other hand... Yeah, things aren't great on that front. The thing you want to implement is what we call glue code and isn't really setup right now for this (nobody has tried like this, ignoring ldc/gdc as they modify it). Hi, thx for information. Any idea from which file should I start at least learning about this glue code? Also, since this is not yet done, is there a way to insert this custom glue code without modifying D frontend source code? If not which file should I register custom changes? Thanks, Alexandru.
Pure D frontend as library.
Hi team, I'd like to ask a lazy question: How easy is to use D compiler frontend without backend? How complicated would be to write a transpiler, and from which files should you start modifications? I'm wondering if something like https://typescripttolua.github.io/ could be done, but with d as language. From my limited knowledge, I should have an AST visitor that transpiles to target language, and some entry point for application which configures D frontend to use my AST visitor to generate code. I've no idea from where to start. If you know some documentation or tutorials, that would be appreciated. Thanks, Alexandru.
Re: Is defining get/set methods for every field overkill?
On Monday, 21 November 2022 at 11:34:50 UTC, thebluepandabear wrote: Best regards, Alexandru. Thanks but I haven't reached that yet. Well, I wish you'll reach as soon as possible :)
Re: Is defining get/set methods for every field overkill?
On Monday, 21 November 2022 at 11:20:31 UTC, Alexandru Ermicioi wrote: On Thursday, 17 November 2022 at 04:39:35 UTC, thebluepandabear wrote: [...] Dunno if someone mentioned, but you can minimize use of boilerplate by hiding it into mixin templates. Say you have: ```D mixin template Property(T) { private T subject_; T Property() { return subject_; } void Property(T value) { subject_ = value; } } ``` The you can use it in your class to define properties of class: ```D class MyMegaPropertyClass { mixin Property!(string) myFancyProperty; } auto c = new MyMegaPropertyClass() c.myFancyProperty = "indeed" ``` The only issue is that, by using eponymous naming you also block any access of underlying subject_ or any other miscellaneous info that you may add. Best regards, Alexandru. You can use mixin templates to also define contlstructors, or any other boilerplate that is buildable using meta programming capabilities in D. It would be awesome to have smth like Lombok from java but in D using mixin templates. Best regards, Alexandru
Re: Is defining get/set methods for every field overkill?
On Thursday, 17 November 2022 at 04:39:35 UTC, thebluepandabear wrote: I am creating a TUI library and I have a class with the following constant fields: ``` class Label : Renderable { const string text; const TextAlignment textAlignment; const Color color; this(Dimensions dimensions, string text, TextAlignment textAlignment, Color color) { this.dimensions = dimensions; this(text, textAlignment, color); } this(string text, TextAlignment textAlignment, Color color) { this.text = text; this.textAlignment = textAlignment; this.color = color; } override Cell[] render() const { Cell[] cells; for (int x = 0; x < 0 + text.length; ++x) { cells ~= Cell(Coordinates(x, 0), text[x], color); } return cells; } } ``` I am debating whether or not I should add getter methods to these properties. On one hand, it will inflate the codebase by a lot, on the other hand -- in other languages like Java it is a good practice: ``` class Label : Renderable { private const string text; private const TextAlignment textAlignment; private const Color color; this(Dimensions dimensions, string text, TextAlignment textAlignment, Color color) { this.dimensions = dimensions; this(text, textAlignment, color); } this(string text, TextAlignment textAlignment, Color color) { this.text = text; this.textAlignment = textAlignment; this.color = color; } string getText() const { return text; } TextAlignment getTextAlignment() const { return textAlignment; } Color getColor() const { return color; } override Cell[] render() const { Cell[] cells; for (int x = 0; x < 0 + text.length; ++x) { cells ~= Cell(Coordinates(x, 0), text[x], color); } return cells; } } ``` It's not a lot of code that has been added but if you have a class with say 10 different fields, adding getter methods would definitely increase the code size by a lot, so what are you guys thoughts on this? Dunno if someone mentioned, but you can minimize use of boilerplate by hiding it into mixin templates. Say you have: ```D mixin template Property(T) { private T subject_; T Property() { return subject_; } void Property(T value) { subject_ = value; } } ``` The you can use it in your class to define properties of class: ```D class MyMegaPropertyClass { mixin Property!(string) myFancyProperty; } auto c = new MyMegaPropertyClass() c.myFancyProperty = "indeed" ``` The only issue is that, by using eponymous naming you also block any access of underlying subject_ or any other miscellaneous info that you may add. Best regards, Alexandru.
Re: I like dlang but i don't like dub
On Friday, 18 March 2022 at 21:04:03 UTC, H. S. Teoh wrote: On Fri, Mar 18, 2022 at 11:16:51AM -0700, Ali Çehreli via Digitalmars-d-learn wrote: tldr; I am talking on a soap box with a big question mind hovering over on my head: Why can't I accept pulling in dependencies automatically? Because it's a bad idea for your code to depend on some external resource owned by some anonymous personality somewhere out there on the 'Net that isn't under your control. True, and because of that you can try and have local/company wide dub registry (if not, should be added support for), in which packages are verified by you/your company, eliminating the problem of net not being under control. Best regards, Alexandru.
Re: foreach() behavior on ranges
On Wednesday, 25 August 2021 at 11:04:35 UTC, Steven Schveighoffer wrote: It never has called `save`. It makes a copy, which is almost always the equivalent `save` implementation. -Steve Really? Then what is the use for .save method then? The only reason I can find is that you can't declare constructors in interfaces hence the use of the .save method instead of copy constructor for defining forward ranges. We have now two ways of doing the same thing, which can cause confusion. Best would be then for ranges to hide copy constructor under private modifier (or disable altoghether), and force other range wrappers call .save always, including foreach since by not doing so we introduce difference in behavior between ref and value forward ranges (for foreach use).
Re: foreach() behavior on ranges
On Wednesday, 25 August 2021 at 08:15:18 UTC, frame wrote: I know, but foreach() doesn't call save(). Hmm, this is a regression probably, or I missed the time frame when foreach moved to use of copy constructor for forward ranges. Do we have a well defined description of what input, forward and any other well known range is, and how it does interact with language features? For some reason I didn't manage to find anything on dlang.org.
Re: foreach() behavior on ranges
On Wednesday, 25 August 2021 at 06:51:36 UTC, bauss wrote: Of course it doesn't disallow classes but it's generally advised that you use structs and that's what you want in 99% of the cases. It's usually a red flag when a range starts being a reference type. Well, sometimes you can't avoid ref types. For example when you need to mask the implementation of the range, but yes, in most of the cases best is to use simpler methods to represent ranges.
Re: foreach() behavior on ranges
On Tuesday, 24 August 2021 at 09:15:23 UTC, bauss wrote: A range should be a struct always and thus its state is copied when the foreach loop is created. Actually the range contracts don't mention that it needs to be a by value type. It can also be a reference type, i.e. a class. Which means the state resets every time the loop is initiated. True for any forward range and above, not true for input ranges. The problem with them is that some of them are structs, and even if they are not forward ranges they do have this behavior due to implicit copy on assignment, which can potentially make the code confusing. If your range uses some internal state that isn't able to be copied then or your ranges are not structs then your ranges are inherently incorrect. If we follow the definition of ranges, they must not be copy-able at all. The only way to copy/save, would be to have .save method and call that method. This again is not being properly followed by even phobos implementations. Note, that a better approach would be to replace .save in definition of forward range with a copy constructor, then all non-compliant ranges would become suddenly compliant, while those that have .save method should be refactored to a copy constructor version. This is what a foreach loop on a range actually compiles to: ```d for (auto copy = range; !copy.empty; copy.popFront()) { ... } ``` You should add .save on assignment if range is a forward range, or just remove the assignment if it is not. Best regards, Alexandru.
Re: foreach() behavior on ranges
On Tuesday, 24 August 2021 at 08:36:18 UTC, frame wrote: How do you handle that issue? Are your ranges designed to have this bug or do you implement opApply() always? This is expected behavior imho. I think what you need is a forward range, not input range. By the contract of input range, it is a consumable object, hence once used in a foreach it can't be used anymore. It is similar to an iterator or a stream object in java. Forward range exposes also capability to create save points, which is actually used by foreach to do, what it is done in java by iterable interface for example. Then there is bidirectional and random access ranges that offer even more capabilities. Per knowledge I have opApply is from pre range era, and is kinda left as an option to provide easy foreach integration. In this case you can think of objects having opApply as forward ranges, though just for foreach constructs only. Regards, Alexandru.
Re: Lexicographical object comparison by selected members of a struct
On Saturday, 21 August 2021 at 04:34:46 UTC, Ali Çehreli wrote: ... Consider __traits(identifier, member) instead. This one should return member name as string, removing the need of memberName function. Also you could have an annotation @Equality.Include for example, and make mixin scan fields for it and include only those fields and methods that have it into compariosn and hashing. Another problem that may arise is storage in local variable of fields before comparison, it might introduce unnecessary copy. Regards, Alexandru.
Re: Lexicographical object comparison by selected members of a struct
On Saturday, 21 August 2021 at 05:34:59 UTC, Alexandru Ermicioi wrote: ... Also there is no need for mixing string code here. You can get the field using __traits(getMember, this, member).
Re: simple (I think) eponymous template question ... what is proper idimatic way ?
On Tuesday, 17 August 2021 at 19:53:52 UTC, james.p.leblanc wrote: Wow! That is absolutely beautiful ... I had never seen (or even imagined) a recursive template! This expands my mind in a good way ... and is going into my toolbox immediately. Best Regards, James Just don't over rely on it. It can cause compilation slowdowns, so avoid it if you can.
Re: simple (I think) eponymous template question ... what is proper idimatic way ?
On Tuesday, 17 August 2021 at 18:11:56 UTC, james.p.leblanc wrote: Is there a more elegant way, to do this? Regards, James PS Any violations should be caught at compile time. That is template specialization: ``` auto moo(T : YourSpecialClassOrDType)(T myMoo) {•••} ``` You can also declare other overloads of the method, just make sure they don't overlap in the constraints, otherwise you'd get ambiguous call exception. Regards, Alexandru.
Re: Getting a working example of opIndexAssign using opSlice ... have troubles ...
On Monday, 16 August 2021 at 06:36:02 UTC, james.p.leblanc wrote: To be honest, I am not exactly sure what is happening here. I am unfamiliar with the "(T : T[])" syntax ... need to read That is template argument secialization. You're saying that T can be accept only types that are arrays of T, where : reads as 'extends'. Now T : T[] might introduce cyclic reference, so more correct would be: foo(T : Z[], Z)(...) Here you say that T might accept only types that are arrays of Z elements. Regards, Alexandru.
Re: Drawbacks of exceptions being globally allocated
On Monday, 16 August 2021 at 06:12:14 UTC, Tejas wrote: ... Fyi, check out std.exeprimental.allocator package. You can use allocators from there to do allocation of exceptions, on the heap or any other region.
Re: Drawbacks of exceptions being globally allocated
On Sunday, 15 August 2021 at 16:23:25 UTC, Ali Çehreli wrote: That output contains two automatically chained exceptions: Failed: Main failed This failed too: The destructor failed Ali Hmm, wasn't aware of such use case (results of too much java :)). Considering this case I'd say it is better to keep it, because having more info than less is better for debugging. Even in your example, you already catch an use case that wasn't accounted for, that may or may not require fixing, i.e. it is better to know it then be in blissfull unawareness. Though it is annoying to view those chained stacks, since they have repetitions. It would be nice if stack traces of nested exceptions would just show lines up to next exception thrown similar to how java does. Regards, Alexandru
Re: Drawbacks of exceptions being globally allocated
On Sunday, 15 August 2021 at 00:15:32 UTC, Ali Çehreli wrote: Even though this feature is probably never used, in D, multiple exception objects are chained. For example, you can throw e.g. in a destructor when there is an active exception in flight and that second object gets attached to the first one in linked list fashion. This may be useful in some cases but in general, these colatteral exceptions don't carry much information and I don't think anybody looks at them. Usually, the first one is the one that explains the error case. That is just an assumption. There could be designs where original exception gets wrapped in another one to comply with some interface, and in such cases, having entire chain visible, is useful. Also exceptions carry the stack trace which is useful, in debugging, allowing you to know possible location of the bug. Regarding exception chaining, do you mean that it will automatically get chained, even without explicitly passing it as constructor of wrapping exception? If so, it indeed might be best to remove such functionality, and just force user to do this by himself. He will then be able to decide whether chained exception does or does not carry any useful meaning. Regards, Alexandru
Re: Drawbacks of exceptions being globally allocated
On Saturday, 14 August 2021 at 13:24:22 UTC, Tejas wrote: ... I don't think there are any gotchas here. The problem with this technique, is when your exceptions aren't just simple labels but also carry some additional data, say for example specific error type, and subject that, caused this. In such cases you can't have a gloablly shared instance. Let's say it's doable but has lot's of drawbacks. Regards, Alexandru.
Re: __traits() to get parameter details only ? ... hasMember looks up everything within
On Wednesday, 4 August 2021 at 22:28:53 UTC, someone wrote: Is that what you mean ? Not really. I was assuming you were talking about @property methods, and if so you could declare such cases: ``` interface HasMutableLstrSymbolId { @property lstrSymbolId(); @property lstrSymbolId(string id); } interface HasMutableLstrCurrencyId { @property lstrCurrencyId(); @property lstrCurrencyId(string id); } class NyseTicker : HasMutableLstrSymbolId { //... } class NasdaqTicker : HasMutableLstrSymbolId, HasMutableLstrSymbolId { // ... } ``` Having this structure you would just need to check whether it implements right interface and then once you know it, just set the value. Note, that this approach won't work nicely if you have lots of fields to set. In this case I'd try a builder pattern, where you have a common builder interface which has Nasdaq and Nyse implementation that builds respective classes out of information available. Now from the other replies it seems you want to get constructor arguments. Constructor itself is named __ctor internally (you'll see it listed as such when fetching allMembers), therefore fetch the constructor overload set (you need this because D allows method overloading, and therefore all methods in overload set should be checked), and then iterate over it and check what you're interested in. You can then use std.traits.Parameters to fetch a tuple of param types, or std.traits.ParameterIdentifierTuple for fetching parameter names. As other people recommended you can check std.traits implementation to get insight on the compiler magic they rely to do this. Regarding @property methods, even if they are half baked, they are still useful in denoting properties that can be fetched or assigned to a class. It is similar to setters & getters convention in Java, or [set,get] functionality from C# as far as I'm aware. Having properties marked with @property also allows template code to be aware which methods are actually representing a property on the object. Also, it is not really necessary to prefix the name of each class or interface with 'class' or 'interface', since this information is already baked into the type itself, and in most of the time may be just unnecessary noise for reading the code.
Re: __traits() to get parameter details only ? ... hasMember looks up everything within
On Wednesday, 4 August 2021 at 15:08:24 UTC, someone wrote: However, __traits(hasMember, ...) checks for the existence of anything labeled lstrCurrencyID within the class (eg: unrelated variables with same name; not gonna happen, but, I like to code it the right way); so, question is: is there any way to search the parameter declarations only ? Something akin to https://dlang.org/spec/traits.html#getParameterStorageClasses but for the parameter types/labels What do you mean by parameter type? Are you referring to @property functions or just whether there is a field in there? In both cases you need to get that symbol with __traits(getMember ...). If it is about @property then check whether the symbol is a function and if so fetch the function attributes with functionAttributes template and check if it is marked as a property. If this is about field of the class then you can test with FieldNameTuple. Since you're using classes consider just declaring an interface that denotes that implementor has this field, it would be much easier to check for it, and easier for compiler since it avoids compile time magic. Best regards, Alexandru.
Re: how much "real-life" code can be marked @safe ?
On Saturday, 3 July 2021 at 20:09:56 UTC, tsbockman wrote: On Saturday, 3 July 2021 at 16:06:33 UTC, Alexandru Ermicioi wrote: 3. An edge case. Ex: You need to mutate some data and then assume it is immutable in a constructor. Can you give a valid example where that is necessary? The main examples that I can think of either can be `@safe` with the right API, or are motivated by a desire to avoid the GC and/or druntime, thus falling under (1). Can't remember any specific code now, but suppose you have a mutable object as input to a function or constructor. You need to return or assign an immutable copy of that struct and you can do that with right copy constructor on that object, but before that you need to do a couple of mutations on that object. In this use case you can't avoid cast(immutable) easily. Note: it is desired to not mutate the original object. The summary is this: the construction of immutable instances can be done just through initialization statement. You can't mutate the instance and then assign/assume it as an immutable. 4. Functionality that doesn't account for @safe/immutable or any other features when it can in standard library. True, although it's just another example of my point (2). The standard library and druntime are dependencies, too... Right, didn't take it that way. The one exception here is when the array is already typed `inout` before it is passed to the constructor. But, that's an example of (2) since this logic applies transitively throughout the call stack: if you need to call `dup` anywhere, don't erase the constness with `inout`. Yeah this is a working workaround, for this specific use case. I still would prefer inout version, even if I need to do some unsafe casts due to clear intentions it gives the user, and better errors. Anyway this is just a proof of your 2nd point.
Re: how much "real-life" code can be marked @safe ?
On Friday, 2 July 2021 at 22:08:31 UTC, tsbockman wrote: (Responding out of order:) On Friday, 2 July 2021 at 00:26:52 UTC, someone wrote: But when you start attempting to declare @safe chunks of code that actually DO things ... well, it seems end-of-the-story. If you find yourself unable to get real work done in `@safe` code, this is almost certainly a sign of one of the following problems: 0) You don't fully understand the purpose and valid use of any or all of the `@trusted`, `inout`, `scope`, and `return` annotations. 1) Your code is avoiding use of the garbage collector, and/or does not have `-dip1000` enabled. (`@safe` is still quite useful without the garbage collector, but even with `-dip1000` you'll still need a lot of `@trusted` code.) 2) You have at least one dependency that isn't correctly designed for use with `@safe`. I'd add: 3. An edge case. Ex: You need to mutate some data and then assume it is immutable in a constructor. 4. Functionality that doesn't account for @safe/immutable or any other features when it can in standard library. Take for example array.dup, there is no inout alternative for it, and you're pretty much stuck with trusted code, when you'd like to dup an array that is inout. manual. Although these two should be on the lowest place in this list by priority.
Re: how much "real-life" code can be marked @safe ?
On Friday, 2 July 2021 at 00:26:52 UTC, someone wrote: ... just wondering: ... Imho, if you want all of the app to be safe, and you cannot avoid unsafe code, then there are two choices: 1. Mark the method doing unsafe stuff as @trusted, or pieces of code which are unsafe with trusted lambda hack. 2. Mark the top caller of your @system methods as @trusted. In both cases, unsafe code should be manually checked as best as it can be done. Best is to think twice whether you can redesign your code to avoid unsafe operations. On PR review step if there is such thing for your app, reviewers should carefully review those @trusted blocks of code. Oh well, and tests, tests and more tests, i.e. It should be thoroughly tested. Best regards, Alexandru.
Re: Printing Tuple!(...)[] using for loop?
On Friday, 2 July 2021 at 04:21:24 UTC, Kirill wrote: ... 1. use static foreach for tuple loop. 2. start column and end column should be known at compile time. Either make them immutable, or as enum constant, or pass them as an template argument. Tuple is basically a wrapper over built in tuple support from D. Check it's insides to se how it is done. So to index a field in a tuple you need to know which field you want to access at compile time since, each field in a tuple has different size, and cannot be indexed at runtime easily. Best regards, Alexandru.
Re: Error: function `...` without `this` cannot be `const`
On Wednesday, 30 June 2021 at 20:12:29 UTC, H. S. Teoh wrote: On Wed, Jun 30, 2021 at 07:40:40PM +, someone via Digitalmars-d-learn wrote: [...] @property int data() { return m_data; } // read property [...] string something() @property { return this.whatever; } [...] Now I am not sure which is the correct way. [...] Both are correct. :-) It's up to personal style preference. T Just to remark here, if you want to apply const to a return type put it inside brackets like: const(MyClass) foo(); otherwise compiler will try to apply it to 'this' parameter. Best regards, Alexandru.
Re: Error: function `...` without `this` cannot be `const`
On Wednesday, 30 June 2021 at 17:47:05 UTC, someone wrote: ... That is because const/immutable/shared are being applied on the object hence 'this' variable inside function body if function is a member of a struct or class. It doesn't make sense to have a const modifier on a simple function. What will that const mean then in context of that function? To what it will be applied? Best regards, alexandri.
Re: cloning array
On Wednesday, 2 June 2021 at 15:32:38 UTC, Sean wrote: ... You can implement deep copy using template recursion: import std; T[] rdup(T : U[], U)(T[] duped) { return duped.map!(arr => arr.rdup).array; } T[] rdup(T)(T[] duped) { return duped.dup; } void main() { int[][][] dupeable = [[[1], [2]], [[3]]]; auto duped = dupeable.rdup; duped[0][0][0] = 9; writeln("Hello D-eep copy of ", dupeable, " to ", duped); } Best regards, Alexandru.
Re: Wrong selection of opEquals for objects.
On Friday, 28 August 2020 at 12:29:20 UTC, Simen Kjærås wrote: Seems that these methods should be rooted out from Object, and placed in respective interfaces like: - interface Equatable(T) { bool opEquals(T value); } - Then it would be a lot more simple. People who want equality check, will implement interface with right type, for example Equatable!Object. - Alex
Re: Wrong selection of opEquals for objects.
On Friday, 28 August 2020 at 10:42:09 UTC, Alexandru Ermicioi wrote: ... Also, why it is limited to just objects? It seems that this function enforces symmetry between two objects. What about rest of the possible types, such as structs, unions?
Re: Wrong selection of opEquals for objects.
On Friday, 28 August 2020 at 10:28:07 UTC, Simen Kjærås wrote: What you'll need to do is mark every function that does compare two class objects with == as @trusted or @system. No that is not a solution at all, in template code that requires safety. You basically will have to sacrifice safety for rest of types, such as structs, unions & enums for the sake of objects being able to compare. Could we just template that opEquals in this manner: --- bool opEquals(T : Object, X : Object)(T lhs, X rhs) { if (lhs is rhs) return true; if (lhs is null || rhs is null) return false; if (!lhs.opEquals(rhs)) return false; if (typeid(lhs) is typeid(rhs) || !__ctfe && typeid(lhs).opEquals(typeid(rhs))) { return true; } return rhs.opEquals(lhs); } --- That would at least allow us to define an overload which is safe and would be picked up by new implementation. I'm wondering why it wasn't done yet, are there any reasons for that? - Alex.
Re: Wrong selection of opEquals for objects.
On Friday, 28 August 2020 at 08:16:01 UTC, Alexandru Ermicioi wrote: Hi everyone, Would be glad at least to pointers, where in dmd is logic for operator overloading happens, as well as for overloading rules, so I could fix it myself, if no-one is able to pick up it.
Wrong selection of opEquals for objects.
Hi everyone, there is https://issues.dlang.org/show_bug.cgi?id=21180 bug, anyone knows how to avoid it? Test case: - import std; class Silly { bool opEquals(const Silly silly) const @safe { return silly is this; } alias opEquals = Object.opEquals; } bool comp(T)() @safe { return new T() == new T(); } void main() { comp!Silly.writeln; comp!(const Silly).writeln; comp!(immutable Silly).writeln; } - It always tries to call Object.opEquals, when narrower overload should've been selected. - Alex.
Re: Call method if declared only
On Friday, 28 February 2020 at 06:12:37 UTC, Виталий Фадеев wrote: How to implement ? I would go for a template mixin that implements send operation in each subclass. Sine template mixin's content is declared in scope of declaration not template's module, the code inside it is aware of concrete implementation of your base class, and could introspect all methods available in it, and generate your switch statement (in send operation) for all supported messages. This would be just one line of code in each class with no complication whatsoever. Best regards, Alexandru.
Re: How create a function that receive a function and run it in another threading?
On Friday, 27 December 2019 at 07:06:52 UTC, mipri wrote: On Friday, 27 December 2019 at 06:08:16 UTC, Marcone wrote: import std; import core.thread; auto threading(lazy void fun){ return task!fun().executeInNewThread(); } void main(){ threading(writeln("Hello World!")); } I want to create a function threading() to run some function in other threading, but I get this error bellow. How can I get success? Error: static function Programa.threading.Task!(fun).Task.impl cannot access frame of function Programa.threading Error: template instance `Programa.threading.Task!(fun)` error instantiating This works: import std; import core.thread; auto threading(void function() fun){ return task(fun).executeInNewThread(); } void main(){ writeln("Main: ", thisTid); threading({ writeln("Hello, ", thisTid); }); } or you can use just https://dlang.org/library/std/concurrency/spawn.html from std.concurrency to avoid needless bike construction. Best regards, Alexandru.
Re: What type does byGrapheme() return?
On Friday, 27 December 2019 at 17:26:58 UTC, Robert M. Münch wrote: ... There are set of range interfaces that can be used to mask range type. Check for https://dlang.org/library/std/range/interfaces/input_range.html for starting point, and for https://dlang.org/library/std/range/interfaces/input_range_object.html for wrapping any range to those interfaces. Note: resulting wrapped range is an object and has reference semantics, beware of using it directly with other range algorithms as they can consume your range. Best regards, Alexandru.
Re: equivalent of typeid(Class).name at compile-time
On Thursday, 21 November 2019 at 20:48:03 UTC, Adam D. Ruppe wrote: On Thursday, 21 November 2019 at 20:45:16 UTC, Steven Schveighoffer wrote: To clarify, I need the compile time string that will match typeid(instance).name, so I can match the derived type. You have to make sure that the derived type is passed to your register function, but then std.traits.fullyQualifiedName!T ought to give it to you. Please note that fullyQualifiedName can return slightly different string than ClassInfo.name for templated types (typeinfo returns names that are fully expanded for eponymous templates while FQN function does not) and hence won't recommend mixing both of them toghether. Best regards, Alexandru.
Re: Translating Java into D
On Friday, 15 November 2019 at 03:29:16 UTC, Heromyth wrote: On Thursday, 14 November 2019 at 19:50:22 UTC, NonNull wrote: Greetings, Java seems to be almost a subset of D in various ways. No, it's not exactly right. Java is more powerful than D as for a language. Many things that Java can do can't be done by D. For example, reflection, full meta info for a type in runtime, type deduction for a template, template member override. See: https://stackoverflow.com/questions/4829631/unusual-generic-syntax-arrays-stringaslist https://www.baeldung.com/java-executor-service-tutorial Has there been any work done to automatically translate Java source into D? We ported some projects in Java by hand. Regarding template member override. Generics in java are mainly compile time thing that boils down to auto generated casts when working with generic types (in bytecode), and therefore a templated method in java is actually a standard method that just works with Object class under the hood, hence it is possible to override in implementor of interface/class. It can be done in D too you'll just need to strip out generics part in method declaration and just use casts from root Object for worst case. Also what do you mean by "type deduction for a template"? Best regards, Alexandru.
Re: Alternative to C++ macro in D
On Sunday, 3 November 2019 at 16:55:36 UTC, Vinod K Chandran wrote: Hi all, I can do this in C++. #include using namespace std ; #define end }; #define log(x) cout << x << endl #define wait std::cin.get() int main() { log("Trying to avoid the visual clutter aused by closing curly braces") ; string myStr = "Now, code looks more elegant" ; log(myStr) ; wait ; end How can i do this in D ? Especially the " #define end }; ". I've tried " alias end = } " but didn't worked. Edit : How can add syntax highlighting and coloring in code posted on this comment ? If this is about logging functionality, check std.experimental.log package, it contains all necessary logging functionality. About macros there aren't any similar to preprocessor macros in c/c++, however you can replace them with three options depending on your needs: 1. Just a simple function in conjunction eith ctfe: https://tour.dlang.org/tour/en/gems/compile-time-function-evaluation-ctfe 2. string mixins: https://dlang.org/articles/mixin.html 3. template mixins: https://dlang.org/spec/template-mixin.html I'd say number 2 should be suitable for your example given you'd like to inject statements into body of some function. Best regards, Alexandru.
Re: Alternative to C++ macro in D
On Sunday, 3 November 2019 at 17:02:30 UTC, Vinod K Chandran wrote: On Sunday, 3 November 2019 at 16:55:36 UTC, Vinod K Chandran wrote: Hi all, I can do this in C++. #include using namespace std ; #define end }; #define log(x) cout << x << endl #define wait std::cin.get() int main() { log("Trying to avoid the visual clutter aused by closing curly braces") ; string myStr = "Now, code looks more elegant" ; log(myStr) ; wait ; end How can i do this in D ? Especially the " #define end }; ". I've tried " alias end = } " but didn't worked. Edit : How can add syntax highlighting and coloring in code posted on this comment ? How can i edit my post ? There is no button or link to edit my post. You can't, web version is just a frontend for mailing list. Best regards, Alexandru.
Converting stringized array to dstring[]
Hi everyone, I've stumbled on another possible bug: - import std.stdio; import std.conv; void main() { "[ \"test\" ]".to!(dstring[]).writeln; } - It gives following error: - /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(222): Error: template std.conv.toImpl cannot deduce function from argument types !(dstring[])(string), candidates are: /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(493): std.conv.toImpl(T, S)(S value) if (isImplicitlyConvertible!(S, T) && !isEnumStrToStr!(S, T) && !isNullToStr!(S, T)) /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(607): std.conv.toImpl(T, S)(ref S s) if (isStaticArray!S) /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(623): std.conv.toImpl(T, S)(S value) if (!isImplicitlyConvertible!(S, T) && is(typeof(S.init.opCast!T()) : T) && !isExactSomeString!T && !is(typeof(T(value /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(674): std.conv.toImpl(T, S)(S value) if (!isImplicitlyConvertible!(S, T) && is(T == struct) && is(typeof(T(value /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(723): std.conv.toImpl(T, S)(S value) if (!isImplicitlyConvertible!(S, T) && is(T == class) && is(typeof(new T(value /dlang/dmd/linux/bin64/../../src/phobos/std/conv.d(222): ... (11 more, -v to show) ... onlineapp.d(5): Error: template instance `std.conv.to!(dstring[]).to!string` error instantiating - Link to code: https://run.dlang.io/is/ymJXFc Any idea why we don't support dstring/string -> dstring[] conversion? Funny enough, wstring and simple string to wstring[] is working as expected. Thank you, Alexandru.
template alias argument accepts only class/interface types.
Perhaps I missed somewhere, but it seems that you can pass only classes or interfaces to alias argument of a template. Trying to pass another type (such as int, int[]) yields an error. Example of issue: void test(alias T)(int o) { import std.stdio; writeln("coo"); } void main() { int i; test!(Object[])(0); } Try pass Object or IFoo and everything compiles perfectly. Link to example: https://run.dlang.io/is/jqr9Zi According to https://dlang.org/spec/template.html#TemplateAliasParameter, simple types and arrays are excluded from the list of supported "alias X" arguments. I'm wondering why do we have such limitation? Is there any reasoning at limiting primitive types and arrays? Thank you, Alexandru.
Cannot dispose const array?
Hi Dlang community! I've stumbled on an interesting issue with allocators. It seems that we can't get disposed of arrays with const or immutable data. Consider example below: Link: https://run.dlang.io/is/frnQI8 import std.stdio; import std.range; import std.algorithm; import std.experimental.allocator; import std.experimental.allocator.mallocator; void main(string[] args) { const(int)[] values = Mallocator.instance.makeArray!(const int)([1, 2, 3, 4]); writeln(values); Mallocator.instance.dispose(values); } We'd get following error: /dlang/dmd/linux/bin64/../../src/phobos/std/experimental/allocator/package.d(2398): Error: function std.experimental.allocator.mallocator.Mallocator.deallocate(void[] b) shared is not callable using argument types (const(int)[]) shared /dlang/dmd/linux/bin64/../../src/phobos/std/experimental/allocator/package.d(2398): cannot pass argument array of type const(int)[] to parameter void[] b onlineapp.d(11): Error: template instance `std.experimental.allocator.dispose!(shared(Mallocator), const(int))` error instantiating Is it expected to not be able to dispose out of immutable or const data, or it is a bug that should be fixed? Regards, Alexandru.
scope variable values assigned to non-scope this.placeholder
Hi Dlang community! I've been playing with dip1000 and scope storage class and stumbled upon a strange error that I can't to understand yet. Here is minimized version of code that generates the error: The link: https://run.dlang.io/is/rg2Odu -- import std.stdio; import std.range; import std.algorithm; @safe: class C { const int*[] placeholder; this(scope int*[] values) { this.placeholder = values; } } void main() { auto array = iota(0, 20).map!((int i) => new int(i)).array; auto c = new C(array); writeln(c.placeholder.map!(p => *p)); } -- I'm not sure what I'm doing wrong, but from what I understand it should check 'this' lifetime to lifetime of scoped 'values' and error only in case when passed value has shorter lifetime than the container itself. I'll be thankful if someone could explain what is wrong with this example. Regards, Alexandru.
Re: Function signature testing with is expression.
On Sunday, 17 December 2017 at 16:19:00 UTC, ag0aep6g wrote: On Sunday, 17 December 2017 at 14:44:15 UTC, Alexandru Ermicioi wrote: Suppose: struct F { static void foo(T)(T i, int o) {} } enum bool check(T) = is(F.foo!T == void function(Z, int), Z); enum correct = check!int; Upon running it will return false, though, by logic is expression could deduce that F.foo is conformat to function signature in check test. Here, `F.foo!T` is the function itself, not its type. You forgot `typeof`. It is interesting that it will not work with global functions as well: void foo(int i, double d) {}; enum bool check = is(typeof(foo) == void function(int, double)); It will be as well evaluated to false. Write `typeof(&foo)` to make it work. There are two kinds of function types in D: 1) "Proper" function types, e.g. `typeof(foo)` which gets printed as "void(int i, double d)", and 2) function pointer types, e.g. `typeof(&foo)` which gets printed as "void function(int i, double d)". As you see, the second kind is the one you're comparing against. I don't think you can use the first kind directly in an IsExpression. The first kind is really rather useless, as far as I know. Argubaly, the language would be nicer without it. Thanks for help, ag0aep6g and Ali. Now it is more clear why it didn't work. Although I did try to use FunctionTypeOf, which failed, and it seems due to explanation about two kinds of function types. It seems that FunctionTypeOf returns first kind which does not work with is expression, and not second. See the example (first line): -- import std.traits; struct T { static void coo(M)(M e, int i); } void main() { pragma(msg, is(FunctionTypeOf!(&T.coo!int) == void function(Z, int), Z)); pragma(msg, is(FunctionTypeOf!(&T.coo!X) == void function(X, int), X)); pragma(msg, is(typeof(&T.coo!int) == void function(Z, int), Z)); pragma(msg, is(typeof(&T.coo!X) == void function(X, int), X)); } -- If run, first line will return false (even without &). The initial question was related actually to another thing that I've tried to do, which is pattern matching on templated functions. It failed, see line 2, and 4. It seems that now it is impossible to do pattern matching on templates, only on instantiated types. Is there any possibility to check the internals of a template without instantiating it? It would be good for using Policy pattern where you want for example to test passed policy, has a templated function with a desired signature for it.
Function signature testing with is expression.
Hi, Have someone tried to test a function against a signature using is expression? Suppose: struct F { static void foo(T)(T i, int o) {} } enum bool check(T) = is(F.foo!T == void function(Z, int), Z); enum correct = check!int; Upon running it will return false, though, by logic is expression could deduce that F.foo is conformat to function signature in check test. It is interesting that it will not work with global functions as well: void foo(int i, double d) {}; enum bool check = is(typeof(foo) == void function(int, double)); It will be as well evaluated to false. So, the question is, is it I'm doing something wrong, that it doesn't work, or is it not implemented? If not implemented, what simple and short alternatives are available? Thanks.
ddoc and method overriding.
Hi all, Having a trivial example such as: ```D class Foo { /** * A documentation info **/ void fancy(); } class Moo { override void fancy(); } ``` Is there a way to tell ddoc to use Foo.fancy documentation block for overriding Moo.fancy method? Thx.
Re: ddoc: Can I escape a colon?
On Thursday, 23 February 2017 at 21:04:39 UTC, Nick Sabalausky (Abscissa) wrote: Suppose I want ddoc output to include this line: -- Note: Blah blabbety blah -- But the colon causes "Note" to be considered a section header. Is there a way to escape the ":" so that it's displayed as expected, but doesn't trigger a section? You can put a space before : and ddoc, or ddox won't treat it as a section. - Note : Blah blabbety blah -
Is it ok to inherit multiple times same templated interface?
Good day, Given following code example, where a templated interface Wr, and an implementation Im is present: interface Wr(T) { T get(); } class Im(T : ubyte) : Wr!ubyte, Wr!ushort, Wr!string { public T t; ubyte get() { return cast(ubyte) this.t; } ushort get() { return cast(ushort) this.t; } string get() { import std.conv; return this.t.to!string ~ " with testings"; } } void main() { auto i = new Im!ubyte; i.t = 20; assert((cast(Wr!ubyte) i).get == 20); assert((cast(Wr!ushort) i).get == 20); assert((cast(Wr!string) i).get == "20 with testings"); } Is it ok (not undefined behavior), to have Im implementing multiple times interface Wr, with different template arguments? Or doing so, will eventually lead to subtle bugs? Currently doing so is allowed, though, it is impossible to call implemented methods directly from implementation. Only by casting i to different implemented interfaces (Wr!ubyte, Wr!ushort, and Wr!string), is possible to call each implemented get method. Thanks.
code.dlang.org package readme.md
Hi all. How it is possible to show readme.md from github repository in code.dlang.org for a particular project? Thanks.
Re: delegate passed in annotation struct cannot be invoked.
On Thursday, 29 December 2016 at 21:29:47 UTC, Stefan Koch wrote: ldc accepts invalid code there. But it might be that dmd 2.071.2 did that as well. If so It will be fixed as soon as ldc updates the front-end version. Nope, tried with dmd v2.071.2 and it gives same error as v2.072.1. I think I'll add a bug report to ldc, about not emitting the error. Thanks for help.
Re: delegate passed in annotation struct cannot be invoked.
On Thursday, 29 December 2016 at 21:07:00 UTC, Stefan Koch wrote: It's a delegate and not function. Therefore it will get a frame-ptr regardless, without checking if it is needed or not, or if there is a frame to point to. Since there is no frame to point to you get the error. At least this is my guess. Make the delegate a function and the error should disappear. Yep, making it a function, will eliminate the problem. Though what I'm also curious is why on LDC it compiles and runs, while on DMD it does not? Should it be registered as a bug on issues.dlang.org, or at ldc bug tracker?
delegate passed in annotation struct cannot be invoked.
Given code below: import std.stdio; struct Annotation { public int delegate(int) dg; } void main() { import std.traits; __traits(getAttributes, Cls)[0].dg(20).writeln; } @Annotation(delegate int(int d) { return d; }) class Cls { void method() { } } Dmd will complain with following statement for the delegate passed in annotation: src/app.d(13,13): Error: delegate app.__dgliteral6 is a nested function and cannot be accessed from D main. GDC will just throw internal compiler exception: src/app.d: In function ‘D main’: src/app.d:20:2: internal compiler error: in get_frame_for_symbol, at d/d-codegen.cc:3981 __traits(getAttributes, Cls)[0].dg(20).writeln; ^ LDC will not argue, and compile it flawlessly, and return 20 as expected. So the question, is the dmd error correct behavior? If so, how the delegate is nested, and what is context that it is nested in? DMD version is: v2.072.1 LDC version is: v1.1.0 based on v2.071.2 and LLVM 3.8.1 GDC version is: 6.2.1 20161215
__traits(getOverloads, Type, member) order of elements in tuple.
Good day. In current implementation of dmd/ldc/gdc, does this trait guarantee, that the order of elements returned in tuple, is same, in several calls of it on same Type and member? Also, is guaranteed that in future versions of dmd, the order of elements won't change?
Re: Sequence separation
On Wednesday, 17 August 2016 at 19:38:22 UTC, Engine Machine wrote: Well, the is does work and that probably is the best solution. I don't mind the extra type at this point. Of course, a library solution for this type of stuff would be nice. I'd rather not have to even use a type but rather use arrays: [a,b,[c,d]]. Maybe you can use Tuple from std.typecons, instead of custom structs, that group the arguments. Ex: alias seqWithSubSeq = AliasSeq!(a, b, Tuple!(c, d)) http://dlang.org/phobos/std_typecons.html#.Tuple
Re: Rebind template
On Saturday, 20 August 2016 at 22:18:57 UTC, Engine Machine wrote: On Saturday, 20 August 2016 at 22:11:40 UTC, Engine Machine wrote: Is there a way to rebind the arguments of a template? template foo(X) { // X is like A!(a,b,c) Y = Rebind!(X,d,e,f); // Y is like A!(d,e,f); } foo(A!(a,b,c)); ? I'd also be happy if I could just remove the last element from A. template EraseLast(X) { // returns A!(a,b) when X = A!(a,b,c) } Check for ApplyLeft and ApplyRight in std.meta, maybe it can help you. http://dlang.org/phobos/std_meta.html#.ApplyLeft http://dlang.org/phobos/std_meta.html#.ApplyRight
Ascii string literal.
Good day, Is it possible somehow to convert implicitly a string literal into an ubyte array? For example: void do(immutable(ubyte)[] asciiString) { // Do something with ascii string. } And from another section of code, calling it like: do("Some ascii string"); --- If no, is there an us-ascii string literal that consists of ubytes and not chars? It's just in some of my code should work only with ascii strings, and it will be cumbersome to convert to ubyte array a string literal each time a function accepting an ubyte array is called. Thank you.
Wrap array into a range.
I have to pass an array to a function that accepts an input range. Therefore I need to transform somehow array into an input range. Is there a range that wraps an array in standard library?
Re: Why getting private member fails using getMember trait in a template?
On Saturday, 26 September 2015 at 10:10:39 UTC, Alexandru Ermicioi wrote: Suppose we have, two modules: module testOne; [...] So, is this behavior correct? If yes, then why?
Why getting private member fails using getMember trait in a template?
Suppose we have, two modules: module testOne; import std.traits; template getMember(alias T, string member) { alias getMember = Identity!(__traits(getMember, T, member)); } module app; import testOne; import std.traits; class TestOne { private { int property; } public { int func() { return 0; } } } template getMember(alias T, string member) { alias getMember = Identity!(__traits(getMember, T, member)); } void main() { pragma(msg, fullyQualifiedName!(__traits(getMember, TestOne, "property"))); pragma(msg, fullyQualifiedName!(app.getMember!(TestOne, "property"))); pragma(msg, fullyQualifiedName!(testOne.getMember!(TestOne, "property"))); } First two statements execute and I get fully qualified name, while the third one fails with next error (dmd version v2.067.1): src/testOne.d(6): Error: class app.TestOne member property is not accessible src/app.d(26): Error: template instance testOne.getMember!(TestOne, "property") error instantiating src/app.d(26):while evaluating pragma(msg, fullyQualifiedName!(testOne.getMember!(TestOne, "property")))
Re: Template detection
On Tuesday, 22 September 2015 at 15:37:32 UTC, Meta wrote: On Sunday, 13 September 2015 at 08:26:55 UTC, Alexandru Ermicioi wrote: Hello, Given: class SomeClass { public { void someSimpleMethod() {} template setOfTemplatedMethods(Type) { void templatedMethodOne() {} void templatedMethodTwo() {} } } } Is there a way to detect at compile time if a member of class/struct is a template? (in the example above, if setOfTemplatedMethods is a template). You can use __traits(isTemplate, ). Thx. Didn't know that there is such trait available. On page http://dlang.org/traits.html it's not present.
Re: Template detection
On Sunday, 13 September 2015 at 09:29:13 UTC, Enamex wrote: On Sunday, 13 September 2015 at 08:26:55 UTC, Alexandru Ermicioi wrote: Hello, Given: class SomeClass { public { void someSimpleMethod() {} template setOfTemplatedMethods(Type) { void templatedMethodOne() {} void templatedMethodTwo() {} } } } Is there a way to detect at compile time if a member of class/struct is a template? (in the example above, if setOfTemplatedMethods is a template). There's this: http://stackoverflow.com/questions/5483381/test-if-an-alias-is-a-template-in-d-2-0 and it should work with 'member templates' OK. Thx for the provided link. I've tried to implement version from the stackoverflow answer, and run against tests provided in another answer to the question in link, and failed. With dmd version 2.067.1 this implementation fails at static assert(! isTemplate!(FooS!int.func!float) ); static assert(! isTemplate!(FooS!int.bar) ); for .func it requires "this" (an value of type FooS, or isTemplate fails to instantiate). and for .bar it just fails (isTemplate detects it as a template). I've found another way to detect if a symbol is a template. The idea is that for a not instantiated template you can get with allMembers trait the list of members in template, but you can't access them using getMembers trait since the template is not instantiated yet. So if there is a symbol that has members which cannot be accessed using getMember (generates an error) then this is a template! template allMembers(alias Type) { alias allMembers = TypeTuple!(__traits(allMembers, Type)); } template anyAccessible(alias Container, T...) { static if (T.length > 1) { enum bool anyAccessible = anyAccessible!(Container, T[0 .. $ / 2]) || anyAccessible!(Container, T[$ / 2 .. $]); } else static if (T.length == 1) { enum bool anyAccessible = __traits(compiles, getMember!(Container, T[0])); } else { enum bool anyAccessible = false; } } template isTemplate(alias T) { static if ( // check if symbol has members __traits(compiles, TypeTuple!(__traits(allMembers, T))) && !T.stringof.startsWith("module ", "package ") ) { enum bool isTemplate = (allMembers!(T).length > 0) && !anyAccessible!(T, allMembers!T); } else { enum bool isTemplate = false; } } It passes almost all tests except for: static assert(! isTemplate!((int x){return x;}) ); static assert(! isTemplate!(std) ); static assert(! isTemplate!(core) ); I don't know how but in this cases, compiler attempts to parse true branch of static if, even if the expression in static if is false. For lamda function allMembers trait fails to get the members and an error is created by compiler. For std, and core packages isTemplate evaluates to true even if expression from static if is false. Is such behavior of static if correct (tested also with ldc compiler, same results)? If there are other test cases, would be glad if they are posted here (to improve the accuracy of template detection). Tests are: struct FooS(T) { struct Inner {} struct Inner2(string U="!(") {} int func(U)() { return 0; } int bar; } FooS!int foo; class FooC { int x; } union FooU { int x;} enum FooE { x } interface FooI { int x(); } template FooT(T) { struct Inner {} struct Inner2(string U="!(") {} int func(U)() { return 0; } int bar; } static assert(! isTemplate!0 ); static assert(! isTemplate!"0" ); static assert(! isTemplate!0.0f ); static assert(! isTemplate!'0' ); static assert(! isTemplate!'!' ); static assert(! isTemplate!"module std.stdio" ); static assert(! isTemplate!null ); static assert(! isTemplate!true ); static assert(! isTemplate!__FILE__ ); static assert(! isTemplate!__LINE__ ); static assert(! isTemplate!([]) ); static assert( isTemplate!FooS ); static assert(! isTemplate!(FooS!int) ); static assert( isTemplate!(FooS!int.func) ); static assert(! isTemplate!(FooS!int.func!float) ); static assert(! isTemplate!(FooS!int.bar) ); static assert(! isTemplate!(FooS!int.Inner) ); static assert( isTemplate!(FooS!int.Inner2) ); static assert(! isTemplate!(FooS!int.Inner2!"?") ); static assert( isTemplate!FooT ); static assert(! isTemplate!(FooT!int) ); static assert( isTemplate!(FooT!int.func) ); static assert(! isTemplate!(FooT!int.func!float) ); static assert(! isTemplate!(FooT!int.bar) ); static assert(! isTemplate!(FooT!int.Inner) ); static assert( isTemplate!(FooT!int.Inner2) ); static assert(! isTemplate!(FooT!int.Inner2!"?") ); static assert(! isTemplate!foo ); static assert( isTemplate!(foo.func) ); static assert( isTemplate!isTemplate ); static assert(! isTemplate!(isTemplate!isTemplate) ); static assert(! isTemplate!FooC ); static assert(! isTemplate!FooU ); static assert(! isTemplate!FooE ); static assert(! isTemplate!FooI ); static assert(! isTemplate!((int x){retur
Template detection
Hello, Given: class SomeClass { public { void someSimpleMethod() {} template setOfTemplatedMethods(Type) { void templatedMethodOne() {} void templatedMethodTwo() {} } } } Is there a way to detect at compile time if a member of class/struct is a template? (in the example above, if setOfTemplatedMethods is a template).