Re: Mixin operator 'if' directly

2018-12-21 Thread Timoses via Digitalmars-d-learn
On Wednesday, 19 December 2018 at 15:40:50 UTC, Neia Neutuladh 
wrote:

On Wed, 19 Dec 2018 15:12:14 +, bauss wrote:
Or while instantiating it:

mixin template foo()
{
  int _ignoreme()
  {
if (readln.strip == "abort") throw new AbortException;
return 1;
  }
  int _alsoIgnoreMe = _ignoreme();
}
void main()
{
  mixin foo;
}


Awesome hack!
Being a hack, it would be even nicer if it worked ouf of the box:

mixin template foo(bool b)
{
int _impl() { writeln(b); return int.init; }
int _ipml2 = _impl();
}

vs

mixin template foo(bool b)
{
writeln(b);
}




Re: Shared static this() not executed for unittest

2018-12-15 Thread Timoses via Digitalmars-d-learn
A look into `dub test --vverbose` showed that ./source/app.d is 
not even included in the compilcation step...


Shared static this() not executed for unittest

2018-12-15 Thread Timoses via Digitalmars-d-learn
Spec 27.5 states: "Unit tests, when enabled, are run after all 
static initialization is complete and before the main() function 
is called. " (https://dlang.org/spec/unittest.html)



main.d:
---
import std.stdio;

shared static this()
{
import vibe.core.log;
setLogLevel(LogLevel.trace);

logDebug("log: statc this");
WRITELN("WRiteln: static this");
}

void main()
{
writeln("Edit source/app.d to start your project.");
}

test.d:
---
import std.stdio;

unittest
{
import vibe.core.log;
logDebug("log: unittest");
writeln("writeln: unittest");
}


Running `dub test` will output:
Running ./unit-test-library
writeln: unittest
All unit tests have been run successfully.

Why is the `shared static this()` not executed?


Re: Is it's correct to say that ALL types that can grow are place on heap?

2018-09-12 Thread Timoses via Digitalmars-d-learn
On Wednesday, 12 September 2018 at 14:46:22 UTC, rikki cattermole 
wrote:

On 13/09/2018 2:34 AM, drug wrote:

12.09.2018 15:14, Timoses пишет:

On Tuesday, 11 September 2018 at 12:07:14 UTC, drug wrote:


If data size is less or equal to total size of available 
registers (that can be used to pass values) than passing by 
value is more efficient. Passing data with size less than 
register size by reference isn't efficient because you pass 
pointer (that has register size) and access memory using it.


Thank you!
So if I pass by reference it will ALWAYS use the address in 
memory to fetch the data, whereas passing it by value enables 
the (compiler?..) to use the register which has already 
loaded the data from memory (stack for example)?


Honestly, I'm not an expert in this domain, but I think so.


Recently used areas of the stack will be available in the cache 
in most cases. The issue with passing by reference is it 
increases the indirection (number of pointers) that it must go 
through to get to the raw bytes.


This is why classes are bad but structs are good. Even if the 
struct is allocated on the heap and you're accessing it via a 
pointer.


This sounds like classes should never be used.. I don't recall 
right now what issues I'm usually encountering with structs that 
make me switch to classes (in D).


So passing by reference is generally only applicable (logical) to 
structs and non-reference types + only makes sense when the 
function being called is supposed to change the referenced value 
without returning it.


Except, as Steven pointed out in his post when dealing with large 
lvalue structs.


This all seems quite complicated to "get right" when writing 
code. I'm sure there are compiler optimizations run on this? Or 
is that not possible due to the nature of difference in ref and 
value passing.



Anyhow, thanks for the answers! I bet it's possible to write 
books on this topic.. Or just mention ones that already were 
written : ~D.


Re: DMD32 compiling gtkd out of memory on 32bit Windows 7 machine

2018-09-12 Thread Timoses via Digitalmars-d-learn
On Wednesday, 12 September 2018 at 06:06:15 UTC, dangbinghoo 
wrote:

hi ,

When compiling gtkd using dub, dmd32 reported "Out for memory" 
and exit.


OS: Windows 7 32bit.
RAM : 3GB
DMD version: v2.0.82.0 32bit.

No VC or Windows SDK installed, when setting up dmd, I selected 
install vc2010 and use mingw lib.


try `dub --build-mode=singleFile` ? I believe this will compile 
each file and then link them together (instead of compiling it 
all together what dub does, afaik).
There's been another topic on memory consumption of compilation 
[1].


[1]: 
https://forum.dlang.org/post/ehyfilopozdndjdah...@forum.dlang.org


Re: Is it's correct to say that ALL types that can grow are place on heap?

2018-09-12 Thread Timoses via Digitalmars-d-learn

On Tuesday, 11 September 2018 at 12:07:14 UTC, drug wrote:


If data size is less or equal to total size of available 
registers (that can be used to pass values) than passing by 
value is more efficient. Passing data with size less than 
register size by reference isn't efficient because you pass 
pointer (that has register size) and access memory using it.


Thank you!
So if I pass by reference it will ALWAYS use the address in 
memory to fetch the data, whereas passing it by value enables the 
(compiler?..) to use the register which has already loaded the 
data from memory (stack for example)?


Re: "immutable string" vs "const string*"

2018-09-11 Thread Timoses via Digitalmars-d-learn
On Sunday, 9 September 2018 at 08:41:37 UTC, Christian Mayer 
wrote:
On Sunday, 9 September 2018 at 08:14:41 UTC, rikki cattermole 
wrote:


Are you aware that a string is just an alias of 
immutable(char)[]?


Yes, I'm aware of that. But it's the same, for example, with 
just one char. "immutable char" vs "const char*".


Or int, or any other data type. As of my current understanding 
"char" will create a new variable and copy the content of the 
original to the new variable. "char*" will just use the 
pointer. And "const char*" is good for when not modifying. But 
I also can achieve the same using "immutable char". But I'm not 
sure when better using "immutable char".


In C I would rather use a const pointer. But since I just 
started learing D I'm not so sure because there are so many 
ways.


Since strings are slices (immutable(char)[]) it could also be 
worth reading into slices [1]. Assigning an existing slice to 
another slice will not copy the content but only the slice struct 
(length and pointer to data).


[1] https://dlang.org/articles/d-array-article.html


Re: Is it's correct to say that ALL types that can grow are place on heap?

2018-09-11 Thread Timoses via Digitalmars-d-learn

On Saturday, 8 September 2018 at 22:51:17 UTC, Ali Çehreli wrote:

On 09/08/2018 02:19 AM, Suliman wrote:
> Is it's correct to say that ALL types that can grow are place
on heap
> and types that not growing (int, char, pointer) are place on
stack?

The question is not that simple. :)

First, there is also the area used for objects that are static 
and object that are defined at module scope. That is different 
from both the call stack and the heap. Let's ignore them...


There are automatic objects like local variables inside a 
function and function parameters. They normally live on the 
stack. (However, the compiler may pass some parameters in CPU 
registers without allocating any memory at all.)


Is this why it is said that passing parameters by value can be 
more efficient?
Cause for a ref parameter it would require passing the address 
which would require to be allocated?


Aww, I really would love some insights into function parameter 
passing. Why is it said that passing by value can be more 
efficient at times?
Since it is also said that passing large structs by value can be 
expensive, why then would it not be cheaper to ALWAYS pass 
everything by reference? What mechanism is behind the scene that 
follows one to reason that sometimes passing by value is less 
expensive?


I get that passing an int by reference would cause indirections 
which need to be resolved whereas passing the int by value is 
just one copy (I guess).



This topic kinda seemed fit for my question that I was carrying 
around for some time.





Re: traits getOverload of a template method

2018-09-10 Thread Timoses via Digitalmars-d-learn

On Thursday, 6 February 2014 at 23:06:03 UTC, QAston wrote:

How do i get aliases to overloads of a template method like

Class A
{
int a(T)(T tq,T tw);
int a(T)(T tq);
}
__traits(getOverloads, A, "a(int)")doesnt work


Is there any way to "select" overloaded template functions?

I require to select one of `std.bitmanip.peek`

import std.bitmanip : peek;
import std.system : Endian;
alias myPeek = peek!(int, Endian.bigEndian, 
immutable(ubyte)[]);


Error:
template std.bitmanip.peek matches more than one template 
declaration:
/dlang/dmd/linux/bin64/../../src/phobos/std/bitmanip.d(3269): 
peek(T, Endian endianness = Endian.bigEndian, R)(R range) if 
(canSwapEndianness!T && isForwardRange!R && is(ElementType!R : 
const(ubyte)))

and
/dlang/dmd/linux/bin64/../../src/phobos/std/bitmanip.d(3306): 
peek(T, Endian endianness = Endian.bigEndian, R)(R range, size_t* 
index) if (canSwapEndianness!T && isForwardRange!R && 
hasSlicing!R && is(ElementType!R : const(ubyte)))


How to "select" one?


Re: Mutable ForwardRange save() method not callable using const object

2018-09-04 Thread Timoses via Digitalmars-d-learn
On Tuesday, 4 September 2018 at 14:26:44 UTC, Steven 
Schveighoffer wrote:

[...]
As general advice, I wouldn't expect const to work well with 
Ranges anyway -- const ranges are useless (you can't iterate 
them). So not much code is expecting to handle const, including 
the wrappers that Phobos provides.


Thanks, that sounds like some good advice. I've actually bumped 
into this right after when I had an immutable range which was 
supposed to fill in its cache when being iterated.
My argument for why this should work is that "from the outside of 
the range" it is immutable, since accessing via opIndex will 
always give the same value.
... In the end, that'll lead nowhere. The immutable attribute 
would become a "promise" rather than an enforcement (or too hard 
for the compiler to enforce).



Thanks for the clarification, Steve!


Mutable ForwardRange save() method not callable using const object

2018-09-04 Thread Timoses via Digitalmars-d-learn

Hey,

I'm fiddling around with ranges a bit and am wondering why save 
is not callable on a const object:


class Range
{
ForwardRange!(const uint) offsets;

this(const S s)
{
this.offsets = s.s.map!(e => e.i).inputRangeObject;
}

this(const Range a) // ERROR line 22
{
this.offsets = a.offsets.save;
}

Range save()
{
return new Range(this);
}
}
struct I
{
uint i;
}
struct S
{
I[] s = [I(1), I(2), I(3)];
}

unittest
{
S s;
auto a = new Range(s);
}

onlineapp.d(22): Error: mutable method 
std.range.interfaces.ForwardRange!(const(uint)).ForwardRange.save 
is not callable using a const object
onlineapp.d(22):Consider adding const or inout to 
std.range.interfaces.ForwardRange!(const(uint)).ForwardRange.save



In this case the Forwardrange Offsets is a
ForwardRange of MapResult(I => uint) of I[]

Since the type of MapResult.front is uint, the ForwardRange is 
essentially a uint[] array.


I could imagine that save is not marked as const because it is 
uncertain whether any indirections are part of the content..? But 
couldn't the compiler check that?


Could anybody explain what exactly is going on? Is there a reason 
the `save()` is not working on const objects?



Given that I haven't done much with ranges yet, any feedback on 
the above implementation is also greatly appreciated (it's just a 
reduced example).


Re: Struct immutable data and dict

2018-09-04 Thread Timoses via Digitalmars-d-learn

On Tuesday, 4 September 2018 at 12:27:47 UTC, nkm1 wrote:
I also had this problem recently. I think aa.require() should 
allow to add immutables (feature request). Anyway, my 
workaround was along the lines of:


final class AA(Key, Value)
{
Value[] _storage;
size_t[Key] _aa;

void opIndexAssign(Value value, Key key)
{
if (key !in _aa)
{
_storage ~= value;
_aa[key] = _storage.length - 1;
}
}

Value opIndex(Key key)
{
if (auto index = key in _aa)
return _storage[*index];

throw new Exception("no key");
}
}

immutable struct S
{
int num;
}

void main()
{
import std.stdio : writeln;

auto aa = new AA!(string, S);

aa["one"] = S(1);
aa["two"] = S(2);

writeln(aa["one"]);
writeln(aa["two"]);
}


Thanks for the replies. It seems quite annoying.

I just use classes for now.


Re: Struct immutable data and dict

2018-09-04 Thread Timoses via Digitalmars-d-learn

On Thursday, 6 October 2016 at 02:09:44 UTC, Adam D. Ruppe wrote:
On Thursday, 6 October 2016 at 01:23:35 UTC, Patric Dexheimer 
wrote:

Why?


Because you'd be overwriting that immutable member. Structs 
just put structure around their contents, but it doesn't change 
their nature. That struct is no different than if you wrote 
`immutable size_t` as the value - and of course, overwriting 
that; changing that violates that promise that you won't change 
it.


You could store pointers to those structs though, and overwrite 
the pointer.


Hm... so is there any way around this?

In my case I have a RandomAccessRange which caches it's results. 
Reduced example:


struct Res
{
immutable int i;
}

struct Range
{
Res[size_t] c;

Res fun(size_t i)
{
if (auto p = i in c)
return *p;
else
{
c[3] = Res(3);   /// ERROR line 26
return c[3];
}
}
}

unittest
{
auto r = Range();
r.fun(3);
}

which errors at compilation with
onlineapp.d(26): Error: cannot modify struct this.c[3] Res with 
immutable members


A workaround I thought could be to use an array

struct Range
{
//Res[size_t] c;
struct Con { Res c; bool valid; }
Con[] c;

Res fun(size_t i)
{
if (c.length > i && c[i].valid)
return c[i].c;
else
{
if (c.length <= i) c.length = i + 1;
auto r = Con(Res(3), true);
c[i] = r;   /// same ERROR!
return c[i].c;
}
}
}

However, of course this also fails because randomly assigning the 
array elements will overwrite it. So the associative array seems 
like the better idea. However, not being able to INITIALIZE an 
assoc array element disallows its usage.


Is there any solution, trick or workaround??


Re: Concat enum of strings into one string

2018-08-14 Thread Timoses via Digitalmars-d-learn

On Tuesday, 14 August 2018 at 14:37:33 UTC, Andrey wrote:
Thank you. Hmm, I thought that standard library already has 
this stuff.


There might be more elegant solutions and I'd be happy to see 
some more. I'm always just digging into std.traits [1] and Traits 
spec part [2] and try to fumble things together somehow until I 
get what I want. It's good practice (as in 
training/accustomization, not as in method...), but perhaps also 
a sign that there's an area for improvement.


[1] https://dlang.org/phobos/std_traits.html
[2] https://dlang.org/spec/traits.html


Re: Concat enum of strings into one string

2018-08-14 Thread Timoses via Digitalmars-d-learn

On Tuesday, 14 August 2018 at 13:42:04 UTC, Andrey wrote:

Hello,
I have a enum:

enum Type : string
{
One = "Q1",
Two = "W2",
Three = "R3"
}

I want to concat it in compile-time:

enum result = doConcat!Type();

And get this result:

writeln(result); // output: "Q1 W2 R3"

Delimiter here is space symbol.
How do do it?


Here's one version:

template StringEnumValues(alias Enum)
{
import std.traits : EnumMembers;
string[] StringEnumValues()
{
string[] enumValues;
static foreach (member; EnumMembers!Enum)
enumValues ~= member;
return enumValues;
}
}

import std.string : join;
pragma(msg, StringEnumValues!Type.join(" "));


Re: How to declare static compile-time assoc array inside struct?

2018-08-13 Thread Timoses via Digitalmars-d-learn

On Monday, 13 August 2018 at 13:21:45 UTC, Andrey wrote:
On Monday, 13 August 2018 at 11:53:06 UTC, rikki cattermole 
wrote:

You must use a module constructor to initialize it.


Tried this:
static this()
{
Test.DESCRIPTION = [Test.Type.One: "One!", Test.Type.Two: 
"It's Two...", Test.Type.Three: "And... Three!"];

}

struct Test
{
// ...
}

I have an error: cannot modify immutable expression DESCRIPTION


I suppose something along these lines was meant:

immutable string[Test.Type] DESCRIPTION;

shared static this()
{
DESCRIPTION = [Test.Type.One: "One!", Test.Type.Two: 
"It's Two...", Test.Type.Three: "And... Three!"];

}

struct Test
{
enum Type { One, Two, Three };
}

See also:
https://forum.dlang.org/post/p941qc$43q$1...@digitalmars.com


Re: Importing struct

2018-08-13 Thread Timoses via Digitalmars-d-learn

On Monday, 13 August 2018 at 14:16:47 UTC, Mike Parker wrote:

On Monday, 13 August 2018 at 13:09:24 UTC, Andrey wrote:

On Monday, 13 August 2018 at 13:05:28 UTC, evilrat wrote:
however the best option is simply avoid naming anything with 
same name as module.


Hmm, I thought that name of class should match name of file...

And how to name a file that contains only one class/struct? 
Like in my case. What usually true D coders do?)


The convention is to use lowercase for the module name:

module myclass;

struct MyClass {}


Using lowercase letters for module names (and their respective 
file names!!) also prevents weird errors when different OSes 
treat lower/capital case letters differently which can sometimes 
lead to modules not being found.


So from my experience: always use lower-case letters for modules 
and the file names.


Re: vibe.d: Finding out if currently in webinterface request

2018-08-10 Thread Timoses via Digitalmars-d-learn

On Thursday, 9 August 2018 at 21:59:24 UTC, Johannes Loher wrote:
I already posted this in the vibe.d forums 
(https://forum.rejectedsoftware.com/groups/rejectedsoftware.vibed/thread/58891/), but it seems, there is not a lot of activity over there, so I am cross posting this here:


[...]


Do you have some code segments boiled down to the problem?

Are you using vibe.core.log?


Re: How do you put log calls in constructors when they may be created in a static context?

2018-08-10 Thread Timoses via Digitalmars-d-learn

On Wednesday, 8 August 2018 at 21:54:34 UTC, aliak wrote:

I'm trying to debug stuff, so I want to add verbose logging

struct S(T) {
  this() {
writeln("created S(T) with properties and ID");
  }
}

static a = S!int(); // bah

I guess users can call this code from any context, but when i'd 
also like to see the log output for debugging purposes. Is 
there a way around this?


Can I maybe only do a writeln in a non compile-time context?

Cheers,
- ali


How about debug [1]?

struct S()T {
this() {
debug { writeln("Created..."); }
}
}

and compile with the debug flag. You can also specify a debug 
identifier or level.


[1]: https://dlang.org/spec/version.html#debug


Re: Why does templated interface function return something different than final function?

2018-08-08 Thread Timoses via Digitalmars-d-learn

On Monday, 6 August 2018 at 14:27:01 UTC, Timoses wrote:
On Thursday, 2 August 2018 at 20:35:57 UTC, Steven 
Schveighoffer wrote:


Looking at the AST, it appears that toImpl doesn't recognize 
what inout(iface) is:


toImpl!(string, inout(iface))
{
@system string toImpl(ref inout(iface) value)
{
import std.array : appender;
import std.format : FormatSpec, formatValue;
Appender!string w = appender();
FormatSpec!char f = FormatSpec;
formatValue(w, value, f);
return w.data();
}

}

Vs. the nice neat call for const(iface)

toImpl!(string, const(iface))
{
@system string toImpl(const(iface) value)
{
return toStr(value);
}

}

Note the ref there, too. This means it can't cast to const. I 
wonder if that's an issue.


-Steve


Thanks for the insight. To me it sounds like std.conv `toImpl` 
doesn't properly handle inout types in this case.


Well, my "workaround" now is to simply cast the inout type to 
const before passing to std.conv.to ...



I've experimented a bit more and compiled it a bit together.

import std.stdio;
import std.conv : to;

interface I
{
void toString(scope void delegate(const(char)[]) sink) 
const;


final void printI()
{
writeln(this.to!string); // this is class A
}
final void printIinout() inout
{
writeln(this.to!string); // app.A
}
}

class A : I
{
void print()
{
writeln(this.to!string); // this is class A
}
// Compilation error
// std\format.d(3890,13): Error: template instance 
`std.format.formatObject!(Appender!string, inout(A), char)` does 
not match template declaration `formatObject(Writer, T, Char)(ref 
Writer w, ref T val, ref const FormatSpec!Char f) if 
(hasToString!(T, Char))`

/*void printinout() inout
{
writeln(this.to!string);
}*/
override void toString(scope void delegate(const(char)[]) 
sink) const

{
sink("this is class A");
}
}

unittest
{
I i = new A();
i.printI();
i.printIinout();

A a = new A();
a.print();
//a.printinout();
}

It seems inconsistent to me. What do you think? Should I open a 
bug report for this?

Also the compilation error should not occur, should it?


Re: Why does templated interface function return something different than final function?

2018-08-06 Thread Timoses via Digitalmars-d-learn
On Thursday, 2 August 2018 at 20:35:57 UTC, Steven Schveighoffer 
wrote:


Looking at the AST, it appears that toImpl doesn't recognize 
what inout(iface) is:


toImpl!(string, inout(iface))
{
@system string toImpl(ref inout(iface) value)
{
import std.array : appender;
import std.format : FormatSpec, formatValue;
Appender!string w = appender();
FormatSpec!char f = FormatSpec;
formatValue(w, value, f);
return w.data();
}

}

Vs. the nice neat call for const(iface)

toImpl!(string, const(iface))
{
@system string toImpl(const(iface) value)
{
return toStr(value);
}

}

Note the ref there, too. This means it can't cast to const. I 
wonder if that's an issue.


-Steve


Thanks for the insight. To me it sounds like std.conv `toImpl` 
doesn't properly handle inout types in this case.


Re: hasUDA with this

2018-07-26 Thread Timoses via Digitalmars-d-learn

On Wednesday, 25 July 2018 at 21:17:38 UTC, jmh530 wrote:

On Friday, 20 July 2018 at 18:24:11 UTC, Timoses wrote:

[snip]

It works in module scope

https://run.dlang.io/is/OQKYag

I don't know why though...


This was reported in 2013. IMO, it should be mentioned in the 
spec if they don't plan on changing it.


https://issues.dlang.org/show_bug.cgi?id=11064


I don't think that bug report relates to the initial question 
(UDA not applying to run-time instance).



Regarding this example

void fun() {
/*const*/
{
double bar;
}

static assert(!is (typeof(bar)));
}

it would kind of violate that `bar` is declared within its own 
scoped block if the static assert failed just because `const` was 
applied to the block.


Re: How to avoid inout type constructor with Optional type wrapper undoing string type

2018-07-25 Thread Timoses via Digitalmars-d-learn

On Tuesday, 24 July 2018 at 14:11:51 UTC, Ali Çehreli wrote:

On 07/24/2018 02:47 AM, Timoses wrote:

> Why does this fail while it works when replacing T with U in
struct
> W(T)?? It's so odd. Both T and U seem to resolve to "string".
>
>  struct W(T) {
>  const T value;
>  // Replacing `T value` with `U value` compiles
>  this(U : T)(auto ref const T value) {

That means, "any U that can implicitly be converted to string". 
However, when U does not appear in the function parameter list, 
there is no way for the compiler to deduce U. (I don't think 
there is syntax to specify constructor template parameters 
explicitly.)


And if the parameter is always T, why is the constructor a 
template? Ok, perhaps U is used inside the constructor and the 
programmer needs to specify it... Still, I don't think there is 
such syntax.


Ali


Ah, thanks!


Re: trait to get the body code of a function?

2018-07-24 Thread Timoses via Digitalmars-d-learn

On Tuesday, 24 July 2018 at 04:43:33 UTC, Guillaume Lathoud wrote:

Hello,

__traits and std.traits already offer access to function 
information like input parameters, e.g. in std.traits: 
ParameterIdentifierTuple ParameterStorageClassTuple


Even if that might sound strange, is there a compile time 
access to the body of the function, e.g. as a code string, or 
at least to the filename where it was declared?


I have not found a direct "string" access, but I found these:

https://dlang.org/phobos/std_traits.html#moduleName

https://dlang.org/phobos/std_traits.html#packageName

...and I am not sure how to proceed from here to get the code 
as a string that declared the function. Context: I have some 
compile-time ideas in mind (code transformation).


Best regards,
Guillaume Lathoud


Not sure if this could be of interest:
https://forum.dlang.org/thread/ifllo2$a45$1...@digitalmars.com


Re: How to avoid inout type constructor with Optional type wrapper undoing string type

2018-07-24 Thread Timoses via Digitalmars-d-learn

On Monday, 23 July 2018 at 18:39:59 UTC, aliak wrote:

Hi,

I'm playing around with an Optional wrapper type. It stores a 
type T and a bool that defines whether a value is defined or 
not:


struct Optional(T) {
  T value;
  bool defined = false;
  this(U : T)(auto ref inout(U) value) inout {
this.value = value;
this.defined = true;
  }
}

To facilitate it's use I have two type constructors:

inout(Optional!T) some(T)(auto ref inout(T) value) {
return inout(Optional!T)(value);
}

Optional!T no(T)() {
return Optional!T();
}

The above produces a problem when working with strings. 
Basically the type information gets slightly altered so you 
can't do this:


auto a = [no!string, some("hello")];

You get a type mismatch:

* no!string = Optional!string
* some("hello") = immutable(Optional!(char[]))

I've created a short code gist, so basically I'm wondering how 
to get it to compile without changing what's in main()


https://run.dlang.io/is/BreNdZ

I guess I can specialize on string type T, but this is a more 
general problem that can be shown with:


struct S {}
alias Thing = immutable S;
Thing thing = S();

auto x = some(thing);
auto y = no!Thing;
auto arr = [x, y]; // no can do buddy

Cheers,
- Ali



I'm not being very helpful here, just throwing in more questions 
again:


Why does this fail while it works when replacing T with U in 
struct W(T)?? It's so odd. Both T and U seem to resolve to 
"string".


struct W(T) {
const T value;
// Replacing `T value` with `U value` compiles
this(U : T)(auto ref const T value) {
pragma(msg, T); // string
pragma(msg, U); // string
this.value = value;
}
}

auto defined(T)(auto ref const T value) {
return W!T(value);
}

void main() {
auto a = defined("hello");
}

Is this a bug?


Re: How to get an inout constructor working with a template wrapper

2018-07-23 Thread Timoses via Digitalmars-d-learn

On Monday, 23 July 2018 at 12:02:58 UTC, aliak wrote:


Thank you Ali! That helped :) I've gotten most of it sorted out 
now, and the factory wrap is definitely the way to go, it also 
turned out that inout(T) and inout T (so inout without parens) 
was surprisingly different (maybe it's a bug? - to test you can 
remove the parens around U on line 3 in this sample: 
https://run.dlang.io/is/gd5oxW


Also over there, line 24:

auto si = wrap!(immutable int)(3);


Both of these seem to work (as you pointed out)

// immutable(W!int)
auto si = wrap!(int)(cast(immutable)3); // or 
wrap(cast(immutable)3);

// W!(immutable(int))
auto si2 = W!(immutable int)(3);



seems to be giving problems. Any ideas there? Error is:

onlineapp.d(8): Error: inout on return means inout must be on a 
parameter as well for pure nothrow @nogc @safe 
inout(W!(immutable(int)))(immutable(int) t)
onlineapp.d(23): Error: template instance 
`onlineapp.wrap!(immutable(int))` error instantiating


To make it compile successfully you can either:

1) Chance immutable to const, then it works for some reason.
2) Change the line to: "auto si = wrap(cast(immutable int)3);" 
- i.e. do not explicitly provide type information.


I don't know why

wrap!(immutable int)(3);

is not working. The error message

"Error: inout on return means inout must be on a parameter as 
well for pure nothrow @nogc @safe 
inout(W!(immutable(int)))(return immutable(int) t)"


sounds very odd and not at all helpful, at least regarding that 
removing immutable from the template argument works.




Cheers,
- Ali


The depths of D. Why does the following only work with "return 
ref"?


struct W(T) {
T val;
this(U : T)(auto ref inout U val) inout {
pragma(msg, typeof(val));
this.val = val;
}
}

// Fails without "return ref" (escaping t warning...)
auto wrap(T)(return ref inout T t) {
return inout W!T(t);
}

class C {}

void main() {
immutable C ci = new immutable C;
auto i = wrap(im);
pragma(msg, typeof(i));
}


Re: hasUDA with this

2018-07-20 Thread Timoses via Digitalmars-d-learn

On Friday, 20 July 2018 at 16:53:12 UTC, jmh530 wrote:
Hmm, on that part about the attributes copying their values, I 
suppose it would be sufficient if I could apply the attributes 
to a group of declarations. However, it didn't seem to work 
properly for me with UDAs, and I noticed that even some of the 
examples in the spec don't compile. Below is taken from section 
8.5 and doesn't compile with DMD 2.081.1. (here's a version on 
run.dlang.org: https://run.dlang.io/is/pKHoBA)


void main()
{
const int foo = 7;
static assert(is(typeof(foo) == const(int)));

const
{
double bar = foo + 6;
}
static assert(is(typeof(bar) == const(double)));
}


It works in module scope

https://run.dlang.io/is/OQKYag

I don't know why though...


Re: hasUDA with this

2018-07-20 Thread Timoses via Digitalmars-d-learn

On Thursday, 19 July 2018 at 19:18:43 UTC, jmh530 wrote:
I wanted to create a struct with a member function whose 
behavior was different depending on whether the struct instance 
had a particular UDA.


However, it seems like hasUDA doesn't seem to produce the 
result I would have expected here. I tried using getAttributes, 
but that didn't work either.


Am I missing something, or should I submit an enhancement 
request?




import std.traits : hasUDA;

enum test;

struct Foo
{
int x;

bool checkUDA()
{
static if (hasUDA!(this, test))
{
return true;
}
else
{
return false;
}
}
}


void main()
{
import std.stdio : writeln;

@test Foo foo = Foo(1);
static assert(hasUDA!(foo, test));

writeln(foo.checkUDA()); //prints false, expected true
}


I haven't worked with UDAs myself yet, but I believe that when 
you apply something like


@test Foo foo;

then you apply the UDA to `foo` and not to `Foo`.

See below:

enum test;

struct Foo
{}

bool checkUDA(alias f)()
{
static if (hasUDA!(f, test))
{
return true;
}
else
{
return false;
}
}

void main()
{
@test Foo foo;
// same as `hasUDA!(foo, test)`
assert(checkUDA!foo); //prints true
}

Now I'm really not sure how UDAs are best utilized, so above 
example might not be how it should be done.. However, you could 
make a templated version of checkUDA depending on what calls it. 
E.g.


bool checkUDA(T, alias f)(T t)
{
// ...
}

although this leads to awkward calls like

foo.checkUDA!foo

which doesn't seem right either. Perhaps wait for somebody more 
knowledgeable to answer your question : D.


Re: Member function passed through template alias only requiring `this` in certain conditions?

2018-07-19 Thread Timoses via Digitalmars-d-learn

On Thursday, 19 July 2018 at 22:16:22 UTC, Ali Çehreli wrote:

On 07/19/2018 08:12 AM, Emma wrote:
> [...]
> If I try to compile it, dmd complains, which I guess makes
sense:
>
> ---
> Error: need this for bar of type void()
> Error: need this for baz of type void()
> ---
>
> [...]

I think it's a compiler bug. The second template argument 
should be a lambda as well. When I added the following lines to 
test()


pragma(msg, typeof(fn1));
pragma(msg, typeof(fn2));

the output is different:

void delegate() @system
void()


That is for the version of calling test with one lamdba and one 
function? (`test!(() => bar, baz)`)


Just a question: The compiler should not automatically convert 
those (functions) to lambdas?


Interesting is this:

void test(alias fn1, alias fn2)()
{
pragma(msg, typeof(fn1)); // void delegate() @system
pragma(msg, typeof(fn2)); // void()
fn1();
fn2(); // Error: this for baz needs to be type Boo not type 
Foo

}
struct Foo
{
void foo()
{
test!(()=>bar, b.baz);
}
int i = 1337;

struct Boo
{
int j = 3;
void baz()
{writeln(j);}
}
Boo b;

void bar()
{writeln(i);}
}
unittest
{
auto foo = Foo();
foo.foo();
}

Looks like the compiler just assumes the context of the first 
delegate to be applicable for the second function?




I think it's a bug probably related to multiple local lambdas. 
We had similar issues in the past. Although it works as is, I 
recommend you make the second one a lambda as well.


Others, please confirm that it's a bug and let's create a bug 
report.


Ali





Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-19 Thread Timoses via Digitalmars-d-learn

On Thursday, 19 July 2018 at 06:35:36 UTC, Simen Kjærås wrote:

On Wednesday, 18 July 2018 at 11:28:54 UTC, Timoses wrote:
But why is a context pointer a problem? Is it problematic 
because the context pointer to the main scope can not 
guarantee `immutable`? E.g. if I happened to use data from 
main in a function of the immutable struct then... well then 
what?
The struct would still be immutable, but what would prevent a 
function from using non-immutable data?


It's a known bug: https://issues.dlang.org/show_bug.cgi?id=18563
In the associated discussion 
(https://forum.dlang.org/thread/p7lp2b$1jod$1...@digitalmars.com), 
Steven Schveighoffer points out that an immutable struct may be 
passed to other threads, which would give one thread access to 
another thread's stack. This could be a good enough reason to 
prevent this kind of conversion, but a better error message 
would still make sense.


--
  Simen


Thanks so much for the pointer, Simen. Interesting discussion.


Re: Why does templated interface function return something different than final function?

2018-07-18 Thread Timoses via Digitalmars-d-learn

On Wednesday, 18 July 2018 at 11:09:12 UTC, Timoses wrote:
Why is the interface templated function not also returning the 
class C toString return value "in C"??


interface iface
{
void toString(scope void delegate(const(char)[]) sink) const;

final string convert() inout
{
import std.conv;
// assert(std.conv.to!string(this) == "in C"); // fails!
return std.conv.to!string(this);
}

final string convert2() const
{
import std.conv;
assert(std.conv.to!string(this) == "in C");
return std.conv.to!string(this);
}
}

class C : iface
{
void toString(scope void delegate(const(char)[]) sink) const
{
sink("in C");
}
}

void main ()
{
iface i = new C();
import std.stdio;
writeln(i.convert); // "app.C"
writeln(i.convert2()); // "in C"
}

It seems like `inout` triggers some odd behaviour??


Sorry, I experimented a bit and forgot to change the topic to 
something more fitting, e.g.

"Why does inout struct function return different results?"


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-18 Thread Timoses via Digitalmars-d-learn

On Tuesday, 17 July 2018 at 06:24:12 UTC, Simen Kjærås wrote:


That makes sense. The problem is F has a context pointer to the 
main() block, since it's a non-static struct with methods 
inside a block. It doesn't actually use the context pointer for 
anything, so it possibly shouldn't have one, but it does, so we 
have to work around it.


The fix is to mark F as static, or move it outside the main() 
block.


--
  Simen


Thanks for the explanation.

But why is a context pointer a problem? Is it problematic because 
the context pointer to the main scope can not guarantee 
`immutable`? E.g. if I happened to use data from main in a 
function of the immutable struct then... well then what?
The struct would still be immutable, but what would prevent a 
function from using non-immutable data?

E.g. I could do this

int gnumber = 3;

struct F
{
int i;
void fun() immutable
{
gnumber = 5;
}
}

void main ()
{
immutable F f = F();
f.fun;
}

I declared `fun()` to be an immutable function. So calling the 
immutable struct function `F.fun()` changes a module scope int. 
The same could be applied to local data of the main scope, 
however the following fails:


void main ()
{
int mnumber = 3;
struct F
{
int i;
void fun() immutable
{
// Error: immutable function onlineapp.main.F.fun 
cannot access mutable data mnumber

mnumber = 5;
}
}

immutable F f = F();
f.fun;
}

Is this connected why I can't implicitly convert a local struct 
with a context pointer to immutable? What's the reason behind it?


Why does templated interface function return something different than final function?

2018-07-18 Thread Timoses via Digitalmars-d-learn
Why is the interface templated function not also returning the 
class C toString return value "in C"??


interface iface
{
void toString(scope void delegate(const(char)[]) sink) const;

final string convert() inout
{
import std.conv;
// assert(std.conv.to!string(this) == "in C"); // fails!
return std.conv.to!string(this);
}

final string convert2() const
{
import std.conv;
assert(std.conv.to!string(this) == "in C");
return std.conv.to!string(this);
}
}

class C : iface
{
void toString(scope void delegate(const(char)[]) sink) const
{
sink("in C");
}
}

void main ()
{
iface i = new C();
import std.stdio;
writeln(i.convert); // "app.C"
writeln(i.convert2()); // "in C"
}

It seems like `inout` triggers some odd behaviour??


Re: Is it feasible to slowly rewrite a C++ codebase in D?

2018-07-16 Thread Timoses via Digitalmars-d-learn

On Monday, 16 July 2018 at 11:31:32 UTC, Seb wrote:

On Monday, 16 July 2018 at 11:12:20 UTC, Dukc wrote:
On Saturday, 14 July 2018 at 03:08:50 UTC, Vladimir Panteleev 
wrote:
I'll follow up with Alawain. Regardless, dscripten-tools 
borrows very little from the redistributable parts of 
dscripten - mostly the "minimalistic runtime", which I think 
was itself borrowed from somewhere else.


Indeed, it appears Alawain himself just changed the runtime 
part to be boost! If he is reading this, thank you!


https://github.com/Ace17/dscriptenQ/issues/4


Superfluous Q attack.

Working link: https://github.com/Ace17/dscripten/issues/4


Re: Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Timoses via Digitalmars-d-learn

On Monday, 16 July 2018 at 12:00:57 UTC, Simen Kjærås wrote:

On Monday, 16 July 2018 at 11:43:03 UTC, Timoses wrote:

Why does this fail?


It doesn't. Not using DMD 2.081.1 under Windows, at least. I 
tried adding a bitfield since you mentioned it, but it compiles 
nicely for me. Which version of DMD are you using, and are you 
having the issues with the exact code you posted here?


--
  Simen


https://run.dlang.io/is/Pgs527

I'm on 2.080.1. But above is on latest 2.081.1 I believe.

Note that the bottom code snippet in the original post does work, 
while the first one does not.


Implicit conversion of struct with methods to immutable in pure function fails

2018-07-16 Thread Timoses via Digitalmars-d-learn

Why does this fail?

struct F
{
int i;
ushort _x;
void x(ushort v) pure
{_x = v;}
ushort x() const
{ return _x; }
}

immutable F f1 = () pure {
F lf = F();
return lf; }();
// Error: cannot implicitly convert expression delegate () => 
lf() of type F to immutable(F)


F makeF() pure
{
F lf = F();
return lf;
}
immutable F f2 = makeF();
// Error: cannot implicitly convert expression makeF() of 
type F to immutable(F)


Removing the methods in struct F compiles fine.

Background: I have a mixin(bitfields!(...)) in the struct which 
utilizes member functions.



/
Idea:
Just found out that it works when making the struct static. But 
why does that help?


Is it because the compiler wouldn't be able to check whether 
methods in the struct are accessing non-immutable data in the 
enclosing context?

That would not make much sense though because the following works:

// Compiles fine!
int modi = 3;
void main ()
{
static struct F
{
int var() immutable { return modi; } // accessing modi 
from module scope

}
immutable f = () pure { F f = F(); return f; }();
}

So my explanation wouldn't make sense, since why would it be okay 
to use module-scope data and not enclosing context data?


So where does that limitation come from that I implicitly convert 
a nested struct to immutable in a pure function?





Re: Is there any tool that will auto publish my changes.

2018-07-16 Thread Timoses via Digitalmars-d-learn

On Sunday, 15 July 2018 at 00:25:22 UTC, Venkat wrote:
I am writing a simple vibe.d app. The following is what I do 
right now.


- I make changes.
- build
- Restart the server.

Is there any tool that will auto publish my changes as I save 
them ? I am using Visual Studio Code.


Thanks
Venkat


I don't believe there currently exists a tool to rebuild the Diet 
templates on the fly. The Diet templates require a step during 
compilation (I think), so that the entire application has to be 
rebuilt (at least the part that has the diet templates).
If you have a large project, what I've heard from others what 
they do, is split the project into smaller pieces and can 
therefore have shorter compilation times [1].


There's also DiamondMVC which you could try depending on your use 
case [2], though I haven't tried it out myself.


[1] 
https://forum.dlang.org/post/txgoxzroscysfbvio...@forum.dlang.org

[2] https://github.com/DiamondMVC/Diamond


Re: Find out druntime/import and phobos folder on Linux

2018-07-15 Thread Timoses via Digitalmars-d-learn

On Saturday, 14 July 2018 at 19:04:01 UTC, Andre Pany wrote:

On Saturday, 14 July 2018 at 19:00:56 UTC, Anonymouse wrote:

On Saturday, 14 July 2018 at 17:19:20 UTC, Andre Pany wrote:
Is there a way to find out both paths based on the dmd 
executable folder?


What I found out so far, these paths are not always correct:
/usr/include/dmd/druntime/import
/usr/include/dmd/phobos


Arch Linux and derivatives keep them under 
/usr/include/dlang/{dmd,gdc,ldc}/*


You may have to hardcode some common paths and try them in 
each in turn. I'm happy to be proven wrong here though.


Somehow also the DMD executable needs to know which 
Phobos/DRuntime it should use.

How does DMD is working here? Maybe I can do the same...

Kind regards
André


Maybe this helps?
https://github.com/dlang/installer/blob/master/linux/dmd_deb.sh#L331
Or check th


Re: Call method with Variant array as parameters

2018-07-14 Thread Timoses via Digitalmars-d-learn

On Saturday, 14 July 2018 at 11:08:21 UTC, Andre Pany wrote:

Hi,

I have a class with methods and I want to call a method by 
using a variant array.
The length of the array and the types exactly fits the method 
signature.


In the last line of main you see the coding which should be 
generated.
I need some coding which looks at the signature of bar and uses 
this information

to create "(args[0].get!string, args[1].get!long)".

I think it is possible with string mixins, but is there some 
better way?

Maybe a staticMap?

class Foo
{
void bar(string s, long l) {}
}

void main()
{
import std.variant: Variant;

Foo foo = new Foo();

Variant[] args = [Variant("Hello"), Variant(42)];
__traits(getMember, foo, "bar")(args[0].get!string, 
args[1].get!long);

}

Kind regards
André


How about this?


import std.variant: Variant;
import std.traits : isCallable;

class Foo
{
void bar(string s, long l)
{
import std.stdio : writeln;
writeln(s); writeln(l);
}
}

void call(T)(T fun, in Variant[] args)
 if (isCallable!fun)
{
import std.traits : Parameters;
alias Params = Parameters!fun;

Params params;
static foreach(i, param; params)
{
if (auto p = args[i].peek!(Params[i]))
{
param = *p;
}
// perhaps create a warning if peeking was unsuccessful...
}
fun(params);
}

unittest
{
Foo foo = new Foo();
Variant[] args = [Variant("Hello"), Variant(42L)];
call(, args);
}


Re: @safe - why does this compile?

2018-07-14 Thread Timoses via Digitalmars-d-learn

On Friday, 13 July 2018 at 22:17:59 UTC, Dukc wrote:

On Friday, 13 July 2018 at 13:52:27 UTC, Timoses wrote:
I suppose this is another good example of how casting can be 
dangerous?


E.g. also:

immutable int i = 3;
int* j = cast(int*)
assert(i == 3);
*j = 4;
assert(j == ); // data occupies same address space
assert(i == 3 && *j == 4); // yet the values differ


No, casting classes to their subclasses is not dangerous to 
program integrity, because it is checked. It is just a regular 
bug that terminates the program when encountered.


But casting away immutable can break program integrity as your 
example demonstrates. For that reason the compiler won't let 
you do that if you wrap that code in @safe, unlike the class 
cast.


Thanks for the explanation. Only read the function safety chapter 
in depth after posting this : D.


Still, is `cast`ing seen as something "dangerous" or as something 
that should only be done as a last resort? Should std.conv : to 
be prioritized?


Re: Orange not working?

2018-07-14 Thread Timoses via Digitalmars-d-learn

On Friday, 13 July 2018 at 21:38:18 UTC, JN wrote:


I'm curious, are the tests in any way OS specific? I see the 
tests are passing, but trying the latest DMD on Windows and 
orange v2.0.0, when I add "@nonSerialized" to a struct member, 
I get this:


C:\Users\jacek\Desktop\test_orange>dub run
Performing "debug" build using C:\D\dmd2\windows\bin\dmd.exe 
for x86.

orange 2.0.0: target for configuration "" is up to date.
test_orange ~master: building configuration "application"...
..\..\AppData\Local\dub\packages\orange-2.0.0\orange\orange\serialization\Serializer.d(1504,13):
 Warning: statement is not reachable
..\..\AppData\Local\dub\packages\orange-2.0.0\orange\orange\serialization\Serializer.d(1510,17):
 Warning: statement is not reachable
..\..\AppData\Local\dub\packages\orange-2.0.0\orange\orange\serialization\Serializer.d(1512,13):
 Warning: statement is not reachable
..\..\AppData\Local\dub\packages\orange-2.0.0\orange\orange\serialization\Serializer.d(1514,13):
 Warning: statement is not reachable
C:\D\dmd2\windows\bin\dmd.exe failed with exit code 1.


Wasn't aware of the `buildRequirements "silenceWarnings"` switch 
in dub.sdl.


Now there should hopefully be no more warnings with below PR.

https://github.com/jacob-carlborg/orange/pull/51

Could perhaps bump it to 2.0.1 ? @Jacob


Re: @safe - why does this compile?

2018-07-13 Thread Timoses via Digitalmars-d-learn

On Friday, 13 July 2018 at 11:04:40 UTC, Piotr Mitana wrote:

This code:

import std.stdio;

class X1 {}
class X2 : X1
{
void run() @safe
{
writeln("DONE");
}
}

void main() @safe
{
X1 x1 = new X1;
X2 x2 = cast(X2) x1;
x2.run();
}

is obviously wrong gets killed by OS's signal. Why is it @safe? 
I thought @safe should prevent such errors as well.


I suppose this is another good example of how casting can be 
dangerous?


E.g. also:

immutable int i = 3;
int* j = cast(int*)
assert(i == 3);
*j = 4;
assert(j == ); // data occupies same address space
assert(i == 3 && *j == 4); // yet the values differ


Re: Orange not working?

2018-07-13 Thread Timoses via Digitalmars-d-learn

On Friday, 13 July 2018 at 05:39:24 UTC, JN wrote:

On Friday, 13 July 2018 at 05:29:58 UTC, Timoses wrote:

On Thursday, 12 July 2018 at 20:44:43 UTC, JN wrote:
I am trying to make use of the Orange package, I added the 
latest version from dub to my project: "orange": "~>1.0.0" 
and copy pasted the "simple usage" code from 
https://github.com/jacob-carlborg/orange , but I am getting a 
long list of errors:


..\..\AppData\Local\dub\packages\orange-1.0.0\orange\orange\serialization\Serializer.d(714,21):
 Error: undefined identifier typedef
[...]


Hm, v1.0.0 is from 2016 and meanwhile typedef was deprecated
https://dlang.org/deprecate.html#typedef .

Perhaps use

"orange": "~master"

to use the latest code.


Looks better, but still doesn't compile:

C:\Users\jacek\Desktop\test_orange>dub run
[...]
test_orange ~master: building configuration "application"...
..\sertest\orange-master\orange\serialization\archives\Archive.d(1313,9): 
Warning: statement is not reachable
[...]
..\sertest\orange-master\orange\serialization\Serializer.d(1215,9): Warning: 
statement is not reachable
C:\D\dmd2\windows\bin\dmd.exe failed with exit code 1.


Huh, see this issue on github:
https://github.com/jacob-carlborg/orange/issues/39

which references to https://github.com/jacob-carlborg/mambo . 
Although that repository has last been updated in 2016 whereas 
Orange's was Oct. 2017.


Went ahead and applied a few fixes for the warnings I encountered:
https://github.com/jacob-carlborg/orange/pull/50


Re: Orange not working?

2018-07-12 Thread Timoses via Digitalmars-d-learn

On Thursday, 12 July 2018 at 20:44:43 UTC, JN wrote:
I am trying to make use of the Orange package, I added the 
latest version from dub to my project: "orange": "~>1.0.0" and 
copy pasted the "simple usage" code from 
https://github.com/jacob-carlborg/orange , but I am getting a 
long list of errors:


..\..\AppData\Local\dub\packages\orange-1.0.0\orange\orange\serialization\Serializer.d(714,21):
 Error: undefined identifier typedef
[...]


Hm, v1.0.0 is from 2016 and meanwhile typedef was deprecated
https://dlang.org/deprecate.html#typedef .

Perhaps use

"orange": "~master"

to use the latest code.


Re: Troubles creating templated inout objects

2018-07-12 Thread Timoses via Digitalmars-d-learn
On Thursday, 12 July 2018 at 12:22:34 UTC, Steven Schveighoffer 
wrote:

On 7/11/18 8:55 AM, Timoses wrote:

 class TestA(T : T[])
 {
     Test!T[] arr;

     // ERROR: Can't initialize inout variable in 
a for loop...

     this(inout(T[]) arr) inout
     {
     // 1: Nope
     foreach (mem; arr)
     this.arr ~= test(mem);

     // 2: Nope
     //Test!T[] a;
     //foreach (mem; arr)
     //   a ~= test(mem);



On the right track, but inside inout (or const or immutable) 
constructors, the members can only be initialized once. So you 
have to initialize a local, and then set the member once.


The issue is, your input is *also* inout (a necessary 
condition), so you didn't declare a properly:


inout(Test!T)[] a;
foreach (mem; arr) a ~= test(mem);
this.arr = a;

-Steve


Aw, thanks! This is much nicer than casting...


Re: Troubles creating templated inout objects

2018-07-12 Thread Timoses via Digitalmars-d-learn

On Tuesday, 10 July 2018 at 14:34:55 UTC, Timoses wrote:
`Unqual` in this case just turns `inout(int[])` into 
`inout(int)[]`, which is why it complains. That's a side effect 
of this example [...]



See also:
https://issues.dlang.org/show_bug.cgi?id=3567


Re: Troubles creating templated inout objects

2018-07-12 Thread Timoses via Digitalmars-d-learn

On Wednesday, 11 July 2018 at 12:55:35 UTC, Timoses wrote:
On Tuesday, 10 July 2018 at 18:01:59 UTC, Steven Schveighoffer 
wrote:
You are overthinking :) inout typically is much easier than 
you expect, until you need to create temporary structs or 
types with inout members, then it becomes problematic.


https://run.dlang.io/is/kosYuC

I had to put in a static if, because your function doesn't 
work once you get down to the array type. See the // fixme 
comment.


Ok, well that helped a tiny bit for the example.

I'm trying to reproduce the errors from my project. It's 
starting to get out of control : D. inout is on a rampage!


https://run.dlang.io/is/5TN7XX

I guess it's the same as for immutable initialization of 
arrays. I can't seem to find a proper response to this one..


[...]
class TestA(T : T[])
{
Test!T[] arr;

// ERROR: Can't initialize inout variable in a 
for loop...

this(inout(T[]) arr) inout
{
// 1: Nope
foreach (mem; arr)
this.arr ~= test(mem);

// 2: Nope
//Test!T[] a;
//foreach (mem; arr)
//   a ~= test(mem);

import std.algorithm : map;
// 3: Nope
// this.arr = arr.map!((e) => test(e)).array;
}
}

[...]



I guess the problem here is focused around the problem that the 
incoming type in the constructor is inout and that the 
constructed object itself is inout.


I can't seem to find another way, I'm just blatantly casting 
now...


class TestA(T : T[])
{
Test!T[] arr;
this(inout(T[]) arr) inout
{
import std.algorithm : map;
import std.range: array;
// should be okay to cast to const, won't change anything
auto ts = cast(const T[])arr;
// should be okay as well, as `test(t)` creates a new 
object
this.arr = cast(inout(Test!T[]))(ts.map!(t => 
test(t)).array);

}
}

I also found `assumeUnique` in std.exception, or 
std.experimental.allocator.makeArray. I'm not to sure how they 
might be able to circumvent the casting though, since I need an 
inout array of the objects...


Am I missing something or is `inout` simply not that well 
"implemented" yet?





Re: Using dub and rdmd together?

2018-07-11 Thread Timoses via Digitalmars-d-learn

On Wednesday, 11 July 2018 at 16:43:24 UTC, Seb wrote:

I don't know of an easy way to do out of the box.
However, with dmd's new -i option, it could be as easy as:

---
dub fetch requests
cat > test.d << EOF
import std.stdio;
import requests;

void main() {
auto content = postContent("http://httpbin.org/post;, 
queryParams("name", "any name", "age", 42));

writeln(content);
}
EOF
dub fetch requests
dmd -I~/.dub/packages/requests-0.8.2/requests/source -i -run 
tests.d

---

However, dmd itself doesn't do any caching (though it would 
work similarly with rdmd).

But, of course, this won't work for more complex dub packages.
There's `dub describe` (and a backend generator) for which they 
might be used.


So this is kind of similar to what dub does already?
Would be nice if dub could cache such compiled scripts somewhere. 
I mean dub already caches inside .dub folder in a dub project. 
Why not also cache compiled scripts somewhere?


Re: Troubles creating templated inout objects

2018-07-11 Thread Timoses via Digitalmars-d-learn
On Tuesday, 10 July 2018 at 18:01:59 UTC, Steven Schveighoffer 
wrote:
You are overthinking :) inout typically is much easier than you 
expect, until you need to create temporary structs or types 
with inout members, then it becomes problematic.


https://run.dlang.io/is/kosYuC

I had to put in a static if, because your function doesn't work 
once you get down to the array type. See the // fixme comment.


Ok, well that helped a tiny bit for the example.

I'm trying to reproduce the errors from my project. It's starting 
to get out of control : D. inout is on a rampage!


https://run.dlang.io/is/5TN7XX

I guess it's the same as for immutable initialization of arrays. 
I can't seem to find a proper response to this one..


import std.traits;

struct S
{
int[3] arr;
}
struct SS
{
S s;
}

interface I
{
inout(I) opIndex(size_t idx) inout;
}

class Test(T) : I
{
T member;

this(inout T mem) inout
{
this.member = mem;
}

inout(Test!T) get() inout
{
return new inout Test!(Unqual!(typeof(member)))(member);
}

inout(I) opIndex(size_t idx) inout
{
static if (is(T == struct))
{
switch (idx)
static foreach (index, t; T.tupleof)
{
case index:
return new inout

Test!(Unqual!(typeof(this.member.tupleof[index])))

(this.member.tupleof[index]);
default:
return null;
}
}
else
return null;
}
}

auto test(T)(inout T t)
{
return new inout Test!(Unqual!T)(t);
}

class TestA(T : T[])
{
Test!T[] arr;

// ERROR: Can't initialize inout variable in a 
for loop...

this(inout(T[]) arr) inout
{
// 1: Nope
foreach (mem; arr)
this.arr ~= test(mem);

// 2: Nope
//Test!T[] a;
//foreach (mem; arr)
//   a ~= test(mem);

import std.algorithm : map;
// 3: Nope
// this.arr = arr.map!((e) => test(e)).array;
}
}


void main()
{
auto ss = SS(S([1,2,3]));
auto t = new const Test!SS(ss);
auto ta = new const TestA!(Test!SS[])([t]);
}



Re: taskPool.reduce vs algorithm.reduce

2018-07-11 Thread Timoses via Digitalmars-d-learn

On Wednesday, 11 July 2018 at 08:31:30 UTC, Dorian Haglund wrote:

Hi.

I'm trying to use taskPool.reduce with a delegate, for example:

import std.parallelism;

int main(string[] args)
{
  int f(int a, int b)
  {
if (args.length > 1)
  return a+b;
else
  return a-b;
  }

  auto res = taskPool.reduce!f([1, 2, 3]);

  return 0;
}

But it fails to compile (with gdc 8.1.0, dmd v2.081) 
complaining that


template instance reduce!(f) cannot use local 'f' as parameter 
to non-global template reduce(functions...)


The snippet above compiles with the reduce function from 
std.algorithm.


Is there a way to make the code compile with taskPool.reduce ?
(I don't want to write two functions and choosing one depending 
on args.length)


Why the interface difference between std.algorithm's reduce and 
taskPool.reduce ?


Best regards,

Dorian


As the error message says taskPool.reduce is a non-global 
template. It's embedded in a taskPool struct. I can't say what 
the reason is that a delegate cannot be used with such a 
template. I'd be interested in hearing what the reason is.

(See Paul's reply).

I'm trying to trick around it, but can't get this to work...

https://run.dlang.io/is/EGbtuq

import std.parallelism;

int main(string[] args)
{
static int f(bool cond)(int a, int b)
{
static if (cond)
return a+b;
else
return a-b;
}

template getF(alias func)
{
auto getF(T)(T arg)
{
if (args.length > 1)
return func!(f!true)(arg); // line 18
else
return func!(f!false)(arg); // line 20
}
}

auto res = getF!(taskPool.reduce)([1,2,3]);

return 0;
}


onlineapp.d(18): Error: need this for reduce of type @system 
int(int[] _param_0)
onlineapp.d(20): Error: need this for reduce of type @system 
int(int[] _param_0)


Re: Passing function(whose parameter would be dynamic and the type is unknown) as a parameter to another function.

2018-07-10 Thread Timoses via Digitalmars-d-learn

On Tuesday, 10 July 2018 at 14:58:42 UTC, vino.B wrote:


Hi Alex,

 I am getting the output as tuples of multiple arrays, but the 
requirement is to get the all the tuple in a single array like 
the below so that we can perform sorting and printing the 
output is easy.


Something along the way

unittest
{
import std.typecons : Tuple, tuple;
alias pair = Tuple!(string, int);

pair[] values;
values ~= tuple("du", 7);
values ~= tuple("Vino", 3);
values ~= tuple(",", 4);
values ~= tuple("hur", 5);
values ~= tuple("Hej", 2);
values ~= tuple("?", 8);
values ~= tuple("mår", 6);

import std.algorithm : sort, each;
import std.stdio : write;
values.sort!((p1, p2) => p1[1] < p2[1])
  .each!(p => write(p[0] ~ " "));
}

?



Troubles creating templated inout objects

2018-07-10 Thread Timoses via Digitalmars-d-learn

How do I create an inout object with template parameters?

Take following code:

import std.stdio;
import std.traits;

struct S
{
int[] arr;
}

interface I
{
inout(I) opIndex(size_t idx) inout;
}

class Test(T) : I
{
// Error: variable 
`onlineapp.Test!(inout(int)[]).Test.member` only parameters or 
stack based variables can be inout

T member;

this(inout T mem) inout
{
this.member = mem;
}

inout(Test!T) get() inout
{
return new inout Test!(Unqual!(typeof(member)))(member);
}

inout(I) opIndex(size_t idx) inout
{
switch (idx)
static foreach (index, t; T.tupleof)
{
case index:
// Error: template 
instance `onlineapp.Test!(inout(int)[])` error instantiating

return new inout

Test!(Unqual!(typeof(this.member.tupleof[index])))

(this.member.tupleof[index]);
default:
return null;
}
}
}


unittest
{
auto s = S([1,2,3]);
auto t = new const Test!S(s);
}


`Unqual` in this case just turns `inout(int[])` into 
`inout(int)[]`, which is why it complains. That's a side effect 
of this example, however the main question is how one would go 
about achieving something like this idiomatically?


I would like to return a new object and that object should have 
the same mutability as the one creating it.


Re: guard clause style static if

2018-07-10 Thread Timoses via Digitalmars-d-learn

On Tuesday, 10 July 2018 at 12:10:27 UTC, Jonathan M Davis wrote:
On Tuesday, 10 July 2018 05:38:33 MDT kdevel via 
Digitalmars-d-learn wrote:
I would like to suggest an extension of the language by 
introducing


 static return Expression_opt;

which shall have the effect of a return plus that the 
remaining lines in the current block are treated as if they 
were enclosed in an else block.


Well, you can propose it, but it really doesn't fit with how 
static if works. static if doesn't have anything to do with 
control flow, whereas what you're proposing here would, which 
would arguably make it that much more confusing. I confess that 
I don't understand what the problem is with simply adding an 
else block. It's simple, and it works right now without any 
language changes.


- Jonathan M Davis


Actually, it's kind of controlling "compile-time control flow". 
If you had


auto func(T)(T args)
{
static if (T.length == 0)
static return;

return args[0];
}

then `static return;` would instruct the compiler to skip the 
rest of the code and only insert a `return;`, omitting any code 
that follows. So the result in above case with `T.length == 0` 
would be:


void func()
{
return;
}

To me that sounds like a very nice feature, considering that I 
often found myself in the same situation where I didn't feel like 
the static `else` statement was really necessary (comparing to 
the usual way to control flow (at run-time) with convential 
if-else statements).


Re: guard clause style static if

2018-07-10 Thread Timoses via Digitalmars-d-learn

On Tuesday, 10 July 2018 at 12:05:11 UTC, kdevel wrote:

On Saturday, 7 July 2018 at 13:12:59 UTC, Alex wrote:

The site you cited for the guard clause above (c2.com)
works at runtime.


?


static if works at compile team and only inserts code into the 
final code for run-time depending on the condition (which has to 
be known at compile time). In your case


   void bar (T ...) (T args)
   {
  static if (args.length == 0)
 return;

  writeln (args [0]);
  return bar (args [1 .. $]);
   }

you could also write

  static if (T.length == 0)

so in case T.length == 0 the resulting run-time code would yield

   void bar (T args) // in that case T is nothing
   {
  return;

  writeln (args [0]);
  return bar (args [1 .. $]);
   }

So the only thing you can control with static if statements is 
"what code to run" depending on the template arguments.


The problem with the error messages you are getting 
(https://forum.dlang.org/post/yndsroswikghknzlx...@forum.dlang.org) is that the compiler checks during compilation time whether `args[0]` is valid (which in above case it is not). So you can't use args like a "normal array" as you would in control statements during run-time. I don't know what exactly `args` represents in the background.



[...]


Re: Passing function(whose parameter would be dynamic and the type is unknown) as a parameter to another function.

2018-07-09 Thread Timoses via Digitalmars-d-learn

On Monday, 9 July 2018 at 05:54:27 UTC, vino.B wrote:

On Sunday, 8 July 2018 at 19:22:32 UTC, Timoses wrote:
Perhaps you could tell us what your goal is. People here might 
come up with a nice solution. Why do you feel like having to 
use templated functions in the first place? That is, what is 
the generic goal of the functions you are trying to define?


Hi Timoses,

 We are converting a Power shell script to D in phased manner; 
the PS script has many functions and we converted few function 
to D in Phase 1.


Phase 1:

Structure of the Program
  Main -> Thread Manager->CoFunction1(Fs1,2,3,4,5)
  Main -> Thread Manager->CoFunction2(Fs1,2,3,4,5)


The thread manager will call the Cofunctions and the function 
gets executed on “N” of file systems each of size 5-10 TB.


The function that we transformed all has the same number of 
parameters (3) and the type was same (string, string, int), so 
we wrote a static thread manager as below


void ptManager (T)(T function(string, string, int) coRoutine, 
Array!string Dirlst, string Step, int Size) {
 alias scRType = typeof(coRoutine(string.init, string.init, 
int.init));

 auto PFresult = taskPool.workerLocalStorage!scRType();
 ReturnType!coRoutine rData;
foreach (string FFs; parallel(Dirlst[0 .. $],1)) { 
PFresult.get ~= coRoutine(FFs.strip, Step); }

 foreach(i; PFresult.toRange) { writeln(i[][]); }
}

void main () {
ptManager(, Fn1Dirlst, Step, Size);
ptManager(, Fn2Dirlst, Step, Age);

}

Phase 2:

In phase 2 we are transferring few more function to the 
existing D code, and these functions has variable number of 
parameter and different type eg: Function3(string, string, 
string), Function(string, int, string, int).


Initially I tried to re-write the ptManager function for each 
type of function which ended with 8 ptManager functions, Eg : 
ptManager1(string, string, int), ptManager2(string, string, 
string), ptManager3(string,int), so now trying as to whether we 
can use 1 ptManager function which can process function with 
“N” of parameter and types to process all the function, hence 
trying to implement the Variadic function. Hence request your 
help and suggestion to achieve this.


Command Parameter to all the functions:
Array!string Dirlist : This parameter will contain the the Fs 
names

File logF: This parameter is used to store the outoput
File logE: This parameter is used to store the Error 
Information.


Rest of the function has variable parameters/type.

From,
Vino.B


Ok, interesting. I don't really know my way around parallelism, 
though I think you should take a look at Alex's suggestion 
(https://forum.dlang.org/post/adepbwetsiuwguuaa...@forum.dlang.org) for a template solution. You could e.g. do


void ptManager(alias func, T ...)(T args)
{
import std.traits : Parameters, ReturnType;
static assert(is(Parameters!func == T), "Arguments don't 
fit function!");

alias RetType = ReturnType!func;

// only receive value if return type is not void
static if (!is(RetType == void))
RetType mVal = func(args);

// write it to stdout if mVal is a valid symbol
// (could also combine that in the above static if...)
static if (is(typeof(mVal)))
{
import std.stdio : writeln;
writeln(mVal);
}
}

unittest
{
ptManager!((int i) => i+1)(2);
void someDelegate(string s1, string s2, int i1) { /* ... 
*/ }

ptManager!someDelegate("hello", "ptManager", 100);
}


Re: Passing function(whose parameter would be dynamic and the type is unknown) as a parameter to another function.

2018-07-08 Thread Timoses via Digitalmars-d-learn

On Sunday, 8 July 2018 at 18:46:31 UTC, vino.B wrote:

Hi All,

 Request you help, in the below code we pass the function 
"Testfun" as a parameter to another function "process" in order 
for the function "process" to work we have to specify the type 
of the parameter that is passed to the function "(T 
function(string, int) coRoutine, string Test, int Size) ", so 
now how do we pass a function whose parameter would be dynamic 
and the type is unknown.


void process(T)(T function(string, int) coRoutine, string Test, 
int Size) {


This would templetize the return type of the coRoutine, thus 
within that function you could do


T returnedValue = coRoutine(string.init, int.init);


alias scRType = typeof(coRoutine(string.init, int.init));

Eg:

Run1 : process(, Test, Size);
void process(T ...)(T function(string, int) coRoutine, string 
Test) {

alias scRType = typeof(coRoutine(string.init, int.init));


Run2 : process(, Test, Size, Str1);
void process(T)(T function(string, int, string) coRoutine, 
string Test, int Size, string Str1) {
alias scRType = typeof(coRoutine(string.init, int.init, 
string.int));



Run3 : process(, Test);
void process(T)(T function(string, string) coRoutine, string 
Test, int Size) {

alias scRType = typeof(coRoutine(string.init));
PFresult.get = coRoutine(args);

Some what like this

auto Testfun (string FFs, int Size) { return tuple(FFs, Size); }

void process(T ...)(T function(T args) coRoutine, T args) {


This would mean that if you pass a function that returns for 
example an int, it must also

- take an int as argument
- and process has to accept another int
e.g.
process((int i) => i+1, 3);

if T would be (int, string) you would have to pass something like

process((int i, string s) {
return AliasSeq!(int, string); }, // error: not even sure 
how to express this

3, "hello");

where I'm not sure how to express the return type of (int, 
string)... Does anybody know this? Would the Tuple Dip make this 
possible? 
(https://forum.dlang.org/post/p3bdp1$2b4e$1...@digitalmars.com)



alias scRType = typeof(coRoutine(T.init));
PFresult.get = coRoutine(T);

void main() {
string Test ="C:\\Temp\\BACKUP1"; int Size = 1;
process(, Test, Size);
}


Code : Working
import std.stdio: writeln;
import std.container.array;
import std.typecons: tuple;
import std.parallelism: taskPool;

auto Testfun (string FFs, int Size) { return tuple(FFs, Size); }

void process(T)(T function(string, int) coRoutine, string Test, 
int Size) {

alias scRType = typeof(coRoutine(string.init, int.init));
auto PFresult = taskPool.workerLocalStorage!scRType();
PFresult.get = coRoutine(Test, Size);
foreach(i; PFresult.toRange) { writeln(i[][]); }
}

void main() {
string Test ="C:\\Temp\\BACKUP1"; int Size = 1;
process(, Test, Size);
}

From,
Vino.B


I suggest taking a look at 
https://dlang.org/phobos/std_traits.html .


E.g. ReturnType and Parameters:

int func() { return 3; }
assert(is(ReturnType!func == int));

void gunc(int i, double j) {}
import std.meta : AliasSeq;
assert(is(Parameters!gunc == AliasSeq!(int, double)));


Perhaps you could tell us what your goal is. People here might 
come up with a nice solution. Why do you feel like having to use 
templated functions in the first place? That is, what is the 
generic goal of the functions you are trying to define?




Re: Outside array bounds

2018-07-07 Thread Timoses via Digitalmars-d-learn

On Saturday, 7 July 2018 at 15:25:51 UTC, vino.B wrote:


Hi All,

  If we replace the statement as args[$ -1] the program works 
are expected, if we apply the same logic in different approach 
it does not work, in the below code if we command the first 
block "if (fnID == "ListFilesNames") {} " then the second "if 
(fnID == "ListFilesSize") {}" works fine, and vice versa but if 
both the "if" block is un-commented it does not work , rather 
it passes wrong parameter to the function. Tried change the 
args as args[$] , args[1], args[2],


Error:
Test.d(31): Error: function Test.ListFilesSize(string FFs, int 
Size) is not callable using argument types (string, 
Array!string)
VarTest.d(31):cannot pass argument _param_1 of type 
Array!string to parameter int Size
Test.d(42): Error: template instance 
`Test.process!(Array!string)` error instantiating



Code:

[...]

void process(T ...)(string fnID, T args) {


Throw in a pragma here:

  void process(T ...)(string fnID, T args) {
  pragma(msg, T);
  ...
  }

[...]

void main() {
Array!string NameDir, SizeDir;
NameDir.insert("C:\\Temp\\BACKUP1");
SizeDir.insert("C:\\Temp\\TEAM1");
int Size = 1;
string fnID1 = "ListFilesNames", fnID2 = "ListFilesSize";
process(fnID1, NameDir); // 1
process(fnID2, SizeDir, Size); // 2


If you call '// 1' first, then the output would be

(Array!string)
... ERROR

and switch the order:

 process(fnID2, SizeDir, Size);   // 2
 process(fnID1, NameDir);   // 1

Now you'll see from the pragma output:

(Array!string, int)
(Array!string)
... ERROR

So the '// 2' call actually compiled fine.

The compiler complains because the function would try to call 
ListFilesSize(int) with the parameter args[$-1], which in this 
case would be the last element, so Array!string.


`args` is a compile time-construct. In effect you instantiate two 
templates with the following calls:


process(fnID1, NameDir);  // same as 
process!(Array!string)(fnID1, NameDir)


instantiates the function

void process(string fnID, (Array!string) args) {
...
// accessing args[$-1] equals accessing args[0] (only one 
element)

ListFilesSize(FFs, args[$ - 1]);
// above function will call ListFilesSize(string, 
Array!string).. which does not exist, hence the error

}

and

process(fnID2, SizeDir, Size);  // same as 
process!(Array!string, int)(fnID1, NameDir, Size)


instantiates the function

void process(string fnID, (Array!string, int) args) {
...
// this time args.length == 2
// hence the call to args[$-1] == args[1] == int
ListFilesSize(FFs, args[$-1]); // compiles!!! args[$-1] 
fits ListFilesSize signature!



It helps me to think in two domains. There is the "static" CT 
(compile-time) and the RT (run-time) domain. You can vary how CT 
code is laid out with "static" statements (such as "static if" or 
"static foreach", or use aliases. Beware that "static this()" or 
static functions are something different once again).


So you would have to determine _at compile time_ how the 
'process' function should look given it's arguments:


void process(T ...)(T args)
{
static if (T.length == 1 && is(T[0] == Array!string))
{
// 1
}
else static if (T.length == 2 && is(T[0] == Array!string) && 
is(T[1] == int))

{
 // 2
}
}

So in case above function get's called with only one argument 
which is an Array!string, only the '// 1' part is left for the 
run-time to be executed.


OR you could test if the function compiles

void process(T ...)(T args)
{
static if (is(typeof(ListFilesSize(args[$-1]
ListFilesSize(args[$-1]);
else
static assert(false);
}

Another option would be to use template constraints

void process(T ...)(T args)
if (is(typeof(ListFilesSize(args[$-1]
{
ListFilesSize(args[$-1]);
}

This is a nice chapter to read (in fact the whole book is a great 
read):

http://ddili.org/ders/d.en/cond_comp.html


Re: Outside array bounds

2018-07-07 Thread Timoses via Digitalmars-d-learn

On Saturday, 7 July 2018 at 08:35:27 UTC, Alex wrote:

On Saturday, 7 July 2018 at 08:24:21 UTC, Timoses wrote:
Interesting.. Looks like the compiler does some boundschecking 
during compile time. You could circumvent this:



void process(T ...)(string ID, T args) {
if (ID == "I1") { writeln(args.length, "\t", args[0]); 
}
static if (T.length > 1) // only add below code if 
cond. true
if (ID == "I2") { writeln(args.length, "\t", 
args[1]);}

}

Oddly, when leaving out the "static if" statement, the error 
still occurs when compiling with "-release" or with 
"-boundscheck=off"... I thought those would/should disable 
bounds checking at compile time???


Nonono ))

In this case, the bound checks are like interface checking... 
or like type checking... As there are different processes 
instantiations for different number of args.

I hope this can't be turned off so easily... 


Aw, got it. So args is actually a tuple type where accessing 
beyond the defined tuple (T) is invalid?


  auto a = [1, 2, 4];
  // works
  pragma(msg, typeof(a[3]));

  auto t = tuple(3, 4, 5.3);
  // ERROR:
  // pragma(msg, typeof(t[3]));


Re: Outside array bounds

2018-07-07 Thread Timoses via Digitalmars-d-learn

On Saturday, 7 July 2018 at 08:09:51 UTC, vino.B wrote:

Hi All,

  Request you help, on the below code

import std.stdio: writeln;

void process(T ...)(string ID, T args) {
if (ID == "I1") { writeln(args.length, "\t", args[0]); }
else if (ID == "I2") { writeln(args.length, "\t", args[1]);}
}

void main() {
string S1 = "Test1", S2 = "Test2", ID1 = "I1", ID2 = "I2";
int Size = 1;
process(ID1, S1);
process(ID2, S2, Size);
}

Error:
Test.d(5): Error: array index [1] is outside array bounds [0 .. 
1]
Test.d(11): Error: template instance `Test.process!string` 
error instantiating


From,
Vino.B


Interesting.. Looks like the compiler does some boundschecking 
during compile time. You could circumvent this:



void process(T ...)(string ID, T args) {
if (ID == "I1") { writeln(args.length, "\t", args[0]); }
static if (T.length > 1) // only add below code if cond. 
true
if (ID == "I2") { writeln(args.length, "\t", 
args[1]);}

}

Oddly, when leaving out the "static if" statement, the error 
still occurs when compiling with "-release" or with 
"-boundscheck=off"... I thought those would/should disable bounds 
checking at compile time???


Re: how to link self made lib using dub

2018-07-06 Thread Timoses via Digitalmars-d-learn

On Friday, 6 July 2018 at 17:08:48 UTC, Flaze07 wrote:

[...]
then, I made a project, with this main in this path : 
Z:\programming\D\experimentLib\source\main.d


it contains this

module main;

import std.stdio;

import source.output;


Shouldn't this be 'import output'?



void main( string[] args ) {
Output.write( "lol" );
readln();
}

and then, I have a dub file in this path : 
Z:\programming\D\experimentLib\dub.json


it contains :

{
  "name" : "experimentlib",
  "targetType": "executable",
  "targetPath": "bin",
  "importPaths": [
"Z:\\programming\\D\\usefulFiles\\experiment\\",


and this '...\\experiment\\source\\'? (I'm not accustomed to 
Windows..)



  ],
  "lflags": [
"+Z:\\programming\\D\\usefulFiles\\experiment\\lib\\",
  ],
}

so, I have made lflags to include the lib in experiment, but 
still, it failed to linker ( it compiles fine, but the linker 
fails )


You could also add a dependency to your other dub project and dub 
should automatically add the import and linker flags.

Add this to your dub.json:

"dependencies":
{
"experiment": {"version": "*", "path": "../experiment"}
}

I didn't test this now, but it should work something like that 
(again, not sure about Windows path...).


See also: 
http://code.dlang.org/package-format?lang=json#version-specs


Re: immutable / inout / pure headaches

2018-07-06 Thread Timoses via Digitalmars-d-learn
On Friday, 6 July 2018 at 15:44:28 UTC, Steven Schveighoffer 
wrote:


I'm long overdue for an inout article...

I can point you at my talk from 2016: 
https://www.youtube.com/watch?v=UTz55Lv9FwQ

Thanks, will definitely take a look when I get home.




I never really used 'pure' and just now found a use case with 
immutable [1], i.e. to return unique objects from functions 
which can be assigned to a mutable or immutable reference.
What other "use cases" or reasons to use 'pure' are there 
(aside from compiler optimizations)?


The reason pure functions allow mutability changes is due to 
the nature of what pure means semantically -- you have 
guarantees that nothing else goes in or out, so it's possible 
to deduce what is unique and what is not.


This is powerful to a human reader of a function as well! 
Without seeing the insides, it tells you exactly what it can 
and cannot affect, giving you more understanding of when it can 
be used and when it can't. It helps write safer more tractable 
code, IMO.


In the end, all these attributes are to help reason about large 
code bases without having to read ALL the code.


Sounds like a good idea to always use it whenever possible. For 
me as a kind of novice it takes time to understand the purpose 
and meaning of each of those attributes. I guess I got one step 
closer to understanding "Why pure?".


That leaves @nogc, @safe and @trusted :D. I feel the best way to 
understand these idioms is to experience the "trouble" oneself. I 
knew in some way what pure functions were from the spec, but I 
didn't have an example at hand that made "non-usage" of pure 
painful.


Re: Passing a reference to a returned reference

2018-07-06 Thread Timoses via Digitalmars-d-learn

On Friday, 6 July 2018 at 15:51:34 UTC, Michael wrote:
Also, yes, I am using the setter method to play around with the 
precision of the double values, and do some normalising.
While writing I realized that the following is even the case 
without the 'ref' parameter:
The caller of the setter will still be able to change the content 
of your private data after you checked it for validity. Take 
following example:


class A
{
private static string[] _disallowed = ["damn"];
private string[int] _dict;

// called before and after every member method call
invariant
{
import std.algorithm : any, canFind;
// don't allow _dict to contain any from _disallowed
 assert(!this._dict.byValue()
.any!((entry) => _disallowed.canFind(entry)));
}

@property dict(string[int] dict)
{
 // checks ...
this._dict = dict;
}

void check() {
import std.stdio : writeln;
writeln(this._dict);
}
}

unittest
{
string[int] loc;
auto a = new A();
loc[1] = "hello john";
a.dict = loc; // using the @property setter
loc[1] = "damn";
a.check;
}

What might be safer is using 'opIndexAssign'

void opIndexAssign(string value, int key)
{
import std.algorithm.searching : canFind;
if (!_disallowed.canFind(value))
this._dict[key] = value;
}

and also duping the dictionary that is handed to the Agent

@property dict(string[int] dict)
{
 // checks ...
this._dict = dict.dup;
}

So you can call

string[int] loc;
auto a = new A();
loc[1] = "hello john";
a.dict = loc;
a[1] = "damn";
loc[1] = "damn";
a.check;

without assigning bad values.



I always want it to access the setter method, but I had hoped 
that, given it's an associative array, that the creation of the 
object in create() would simply create it on the heap and I 
could pass back a reference. It seems that I was incorrect, as 
if I set create() to explicitly return a reference, it 
complains about returning a reference to a local variable. Any 
advice on the best way to pass it as a reference?


I suppose this might already answer your question:
https://forum.dlang.org/post/edrejkakhaylivlqj...@forum.dlang.org



Re: Passing a reference to a returned reference

2018-07-06 Thread Timoses via Digitalmars-d-learn

On Friday, 6 July 2018 at 15:33:18 UTC, Michael wrote:


This is definitely to do with my use of the setter syntax, 
which maybe I am misunderstanding? Because if I change it to a 
normal function call like so:


a.beliefs(Operator.create());

then it complains if I use ref, and doesn't complain if I don't.


You can try removing the "auto" from the Operator class method

// Error: returning dict escapes a reference to local variable 
dict

false
static ref create()
{
double[int] dict;
dict[2] = 1.0;
dict[1] = 0.0;
return dict;
}

That indicates that 'dict' is actually returned by value (at 
least the reference). This sounds a bit confusing.
AFAIK, in above code a reference 'dict' is created pointing 
towards memory that stores that dictionary entries. The reference 
itself is a "pointer"(?) which will "die" when running out of the 
method's scope. This pointer lives on the function's stack. So 
returning this "pointer" (essentially a value type, e.g. int) 
will return it by value.


You could return a reference like so:

class Operator
{
static double[int] hdict;
static this()
{
 hdict[2] = 1.0;
 hdict[1] = 0.0;
}
static ref create()
{
return hdict;
}
}

then


a.beliefs(Operator.create());


should work on the "ref" setter.


Re: Passing a reference to a returned reference

2018-07-06 Thread Timoses via Digitalmars-d-learn

On Friday, 6 July 2018 at 15:14:01 UTC, Michael wrote:

class Agent
{
private
{
double[int] mDict;
}

// Setter: copy
void beliefs(ref double[int] dict)
{
import std.stdio : writeln;
writeln("Setter function.");
this.mDict = dict;
}

// Getter
auto ref beliefs()
{
return this.mDict;
}
}

class Operator
{
static auto ref create()
{
double[int] dict;
dict[2] = 1.0;
dict[1] = 0.0;
return dict;
}
}


Throw in a writeln statement in getter and be amazed : D

class Agent
{
private
{
double[int] mDict;
}

// Setter: copy
void beliefs(ref double[int] dict)
{
import std.stdio : writeln;
writeln("Setter function.");
this.mDict = dict;
}

// Getter
auto ref beliefs()
{
writeln("getter");
return this.mDict;
}
}

class Operator
{
static auto ref create()
{
double[int] dict;
dict[2] = 1.0;
dict[1] = 0.0;
return dict;
}
}

unittest
{
import std.stdio : writeln;

Agent a = new Agent();

writeln("Statement 1");
a.beliefs = Operator.create();
writeln("Statement 2");
assert(a.beliefs.keys.length == 2);

writeln("Statement 3");
writeln(a.beliefs);
}

If you remove the ref then "Statement 1" will use the setter 
method. Otherwise it calls the "auto ref" function to get a 
reference of 'mDict' and assign it a value. Essentially


// Getter
auto ref beliefs()
{
return this.mDict;
}

makes your "private" variable not private any more, since you are 
leaking a reference to it. So any program calling "a.beliefs" can 
get a reference to your private data and modify it.


My guess is that (if ref is removed from the setter) it serves as 
a @property function:

https://dlang.org/spec/function.html#property-functions
So this allows the function to work in a statement like:
a.beliefs = 

And apparently it is prioritized over the "ref beliefs()" 
function.



I guess it is nicer to actually use the "setter" function, as it 
allows you to inspect what the private data will be assigned to 
and take appropriate measures, whereas with the "ref beliefs()" 
method the private data is open for any manipulation out of your 
control.


Re: immutable / inout / pure headaches

2018-07-06 Thread Timoses via Digitalmars-d-learn
On Friday, 6 July 2018 at 14:28:39 UTC, Steven Schveighoffer 
wrote:
inout is not a compile-time wildcard, it's a runtime one. So it 
doesn't know how to convert an immutable to an inout. 
Essentially, inside this function, the compiler has no idea 
whether the real thing is an immutable, const, mutable, etc.


The fix is simple, replace both your constructors with one 
inout constructor:


this(inout(S) t) inout { this.s = t; }


Slowly getting acquainted to inout... Feels like magic.


And it will work for everything.

One word of caution though -- inout is viral (just like 
immutable). Everything you use has to support it, or it breaks 
down.


"viral" is very fitting. Throw in pure and I quickly reach the 
bottom of my program hitting a library function I used which is 
not pure.


I never really used 'pure' and just now found a use case with 
immutable [1], i.e. to return unique objects from functions which 
can be assigned to a mutable or immutable reference.
What other "use cases" or reasons to use 'pure' are there (aside 
from compiler optimizations)?


[1]: 
https://forum.dlang.org/post/nmcnuenazaghjlxod...@forum.dlang.org


Re: Passing a reference to a returned reference

2018-07-06 Thread Timoses via Digitalmars-d-learn

On Friday, 6 July 2018 at 13:13:43 UTC, Michael wrote:

static auto ref consensus( ... )


`auto ref` infers the return type from the return statement [1]. 
So it's not necessarily returning a ref type.


However, I don't think this matters if the only concern you have 
is that the setter function actually modifies the passed object.




and the agent's setter method looks like the following:

void beliefs(ref double[int] beliefs)

Now obviously if I remove ref in the above signature, 
everything works fine, but I am surprised I wasn't getting any 
kind of warning about the reference because the setter function 
just doesn't run at all. I tried checking if (beliefs is null) 
but perhaps this isn't the correct way to check if an 
associative array's reference is no longer reachable?


Some explanation would be great, thanks!


This works for me:

auto create()
{
string[int] dict;
dict[2] = "hello";
return dict;
}

void modifyNoRef(string[int] m)
{
 writeln("Address not ref: ", );
 m[0] = "modified";
}

void modifyRef(ref string[int] m)
{
 writeln("Address ref: ", );
 m[1] = "modified";
}

unittest
{
auto r = create();
writeln("Address r: ", );
assert(r.keys.length == 1);
modifyNoRef(r);
assert(r.keys.length == 2); 
modifyRef(r);
assert(r.keys.length == 3); 
}

So either with ref or not as parameter storage class the assoc. 
array is modified. Note the address in the "ref" one is the same 
as "r" in the unittest.


[1]: https://dlang.org/spec/function.html#auto-ref-functions


immutable / inout / pure headaches

2018-07-06 Thread Timoses via Digitalmars-d-learn
I dared once again getting into immutable by adding an 
"immutable" keyword which causes a chain of actions to be taken.
I feel like I'm lost in a jungle of immutable, inout and pure 
(perhaps more will join the party...).


To start off, why does this not work?


class Test
{
private S s;
this(S t) { this.s = t; }
this(immutable S t) immutable { this.s = t; }

inout(Test) get() inout
{
// Error: none of the overloads of __ctor are 
callable using a inout object, candidates are:

//onlineapp.d(10):onlineapp.Test.this(S t)
//onlineapp.d(11):onlineapp.Test.this(immutable(S) t)
return new inout Test(this.s);
}
}

struct S
{
int[] a;
}
void main()
{
immutable S s = immutable S([1,2,3]);
auto t = new immutable Test(s);
}



Re: Function Template for Dynamic Parameter

2018-07-06 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 16:23:36 UTC, vino.B wrote:

Hi All,

  Request your help on the below code

auto coCleanFiles(T ...) (T FFs) {
auto dFiles = Array!(Tuple!(string, 
SysTime))(dirEntries(FFs, SpanMode.depth).map!(a => 
tuple(a.name, a.timeCreated)));

return dFiles;
}

void process(T)(T pfunction, Array!string Dirlst) {
alias wlsType = typeof(pfunction(T));
auto Result = taskPool.workerLocalStorage!wlsType();
foreach (FFs; parallel(Dirlst[],1)) { Result.get ~= 
pfunction(FFs); }

foreach(i; Result.toRange) { writeln(i[][]); }
}

void main() {
Array!string Cleanlst;
Cleanlst.insert("C:\\Temp\\BACKUP1");
process(, Cleanlst);
}

Error : Error: coCleanFiles(T...)(T FFs) is not an lvalue and 
cannot be modified


I guess since in above code `coCleanFiles` is a template, you can 
not simply take the address of that function template. You'd have 
to instantiate the template first


process(!string, ...)

If you want to pass the template to process you could define 
process as something like


void process(alias func)(Array!string Dirlst)
{
func!string(Dirlst[0]);
}

and call

process!coCleanFiles(Cleanlst);



Re: Safe to cast to immutable and return?

2018-07-05 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 12:15:35 UTC, vit wrote:


Try pure functions:

class A {}
A getA()pure @safe  //pure whitout mutable parameters 
guarantees that function doesn't leak data.

{
 A a;
 // .. do stuff with a
 // not leaking a to any functions

 // is this safe
 return a;
}
A getA2(A x)pure @safe  //pure with mutable param
{
 A a;
 // .. do stuff with a
 // not leaking a to any functions

 // is this safe
 return a;
}

void test()@safe{
immutable(A) a1 = getA();//ok
immutable(A) a2 = getA2(null);   //ok
immutable(A) a3 = getA2(new A);  //ok
immutable(A) a4 = getA2(a3);//error in theory can leak
}


Very nice!
I assume the @safe is not a must?

Good read:
https://dlang.org/spec/function.html#pure-functions


Re: 'is(T==return)' How does is expression with return keyword as TypeSpecialization

2018-07-05 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 10:32:01 UTC, Timoses wrote:

int fun(T)(T i)
{
static assert(is(typeof(return) == T)); //true
pragma(msg, is(T == return)); // false
static if (is(T ReturnType == return))
pragma(msg, ReturnType); // does not enter
return i;
}
unittest
{
fun(3);
}

What's the purpose of 'is(T == return)' if not the above?


Found it:
http://ddili.org/ders/d.en/is_expr.html
Section "is (T identifier == Specifier)"

int fun() { return 1337; }
template Temp(T)
{
//pragma(msg, typeof(T));
// is T a function, if so assign its return type to 
'retType'

static if (is(T retType == return))
{
retType Temp(T func)
{
return func();
}
}
}
void main()
{
   int i = Temp!(typeof())();
   assert(i == 1337);
}

So, 'return' checks if T is a callable and if so assigns its 
return type to 'identifier'.


Re: 'is(T==return)' How does is expression with return keyword as TypeSpecialization

2018-07-05 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 11:37:16 UTC, Timoses wrote:

I think it refers to this section:
https://dlang.org/spec/expression.html#is_expression


should mention that I mean the 6th paragraph.




Re: 'is(T==return)' How does is expression with return keyword as TypeSpecialization

2018-07-05 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 11:21:41 UTC, Alex wrote:

On Thursday, 5 July 2018 at 10:32:01 UTC, Timoses wrote:

int fun(T)(T i)
{
static assert(is(typeof(return) == T)); //true
pragma(msg, is(T == return)); // false
static if (is(T ReturnType == return))
pragma(msg, ReturnType); // does not enter
return i;
}
unittest
{
fun(3);
}

What's the purpose of 'is(T == return)' if not the above?


I always thought that "return" is a keyword.

https://dlang.org/spec/lex.html#keywords

And the fact, that you can ask the keyword about its type is 
just a nice feature... ;)


I think it refers to this section:
https://dlang.org/spec/expression.html#is_expression

I don't remember where I read this usage (think it was in a 
book), but I noted it down and now I wonder how it can be used.


Safe to cast to immutable and return?

2018-07-05 Thread Timoses via Digitalmars-d-learn

Is this safe?

class A {}
immutable(A) getA()
{
A a;
// .. do stuff with a
// not leaking a to any functions

// is this safe
return cast(immutable A)a;
}

What if A is replaced with A[] or A[int]?
If it's not safe, what would be the proper way to return an 
immutable instance from a function which needs to make 
adjustments to the instance before returning it as immutable?


'is(T==return)' How does is expression with return keyword as TypeSpecialization

2018-07-05 Thread Timoses via Digitalmars-d-learn

int fun(T)(T i)
{
static assert(is(typeof(return) == T)); //true
pragma(msg, is(T == return)); // false
static if (is(T ReturnType == return))
pragma(msg, ReturnType); // does not enter
return i;
}
unittest
{
fun(3);
}

What's the purpose of 'is(T == return)' if not the above?


Re: ranges.chunks and map! does not work

2018-07-05 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 09:47:32 UTC, Andre Pany wrote:

Hi,

the purpose of this code is to generate CSV based on 3 double 
arrays.
I wonder why map cannot directly use the result of the chunks 
function.


import std.experimental.all;

void main()
{
double[] timestamps = [1.1];
double[] temperatures = [2.2];
double[] pressures = [3.3];

string content = roundRobin(timestamps, temperatures, 
pressures)

.chunks(3)
//.map!(c => c.array)
.map!(c => "%.10g,%.10g,%.10g".format(c[0],c[1],c[2]))
.join("\n");

writeln(content);
}


I always find this kind of confusing as well. What kind of ranges 
are returned by functions handling ranges and returning another 
range?


It is clear what type of range can be passed by looking at the 
constraint for chunks[1]:

Chunks!Source chunks(Source)(Source source, size_t chunkSize)
if (isInputRange!Source);

It would be awesome to have something like and output constraint:
out(Output; isForwardRange!Output && 
isInputRange!(ElementType!Output))


or something similar to know what the function will return..

In your case it seems like the typeof(c.front) is not a random 
access range:

auto c = roundRobin(timestamps, temperatures, pressures)
.chunks(3);
pragma(msg, isRandomAccessRange!(typeof(c.front)));
// prints false

So you could do

auto content = roundRobin(timestamps, temperatures, pressures)
.evenChunks(timestamps.length)
.map!(c =>
  c.map!(a => format("%.10g", a))
   .join(",")
  )
.join("\n");

although there might be more elegant solutions.

[1]: https://dlang.org/phobos/std_range.html#chunks


Re: how to import file from another path in dub ?

2018-07-05 Thread Timoses via Digitalmars-d-learn

On Thursday, 5 July 2018 at 05:38:29 UTC, Flaze07 wrote:
I have a dub project, and I put the importPath to the path of 
the file I want to import and the source file to the source 
folder, and it appears that I have succeeded at importing the 
module, but there's one problem, it appears like I need to 
define some sort of thing, because the error says " Error 42: 
Symbol Undefined __D9animation12__ModuleInfoZ" ( I am using 
coedit ), do I need to compile the file into .lib ?


You can follow what happens when you do `dub -v`. When using the 
`importPaths` the compiler will import the path during 
compilation, but not compile the files in importPath and put it 
in the object file. The call is something like this:


dmd -I 

Afterwards the linker tries to find the function defined in 
import path, which however is not found as it was not compiled.
My guess is that this could be useful when using something like 
interface files (in D .di files, or in C/C++ header files) which 
only has declarations).
Then you would have to pass the linker the library or object file 
which actually contains the compiled functions. Otherwise you get 
an error like the one you have.


Depending on your use case I see these options:
- If you have a library that defines the symbols that you are 
using in the imported files you could use the dub `libs` setting
- Otherwise, if you're just using the other folder to separate 
code you can redefine dub's `sourcePaths`. I believe it 
overwrites the previous, so you have to include your 'source' 
folder again:


"sourcePaths": ["source", ""]


When using sourcePaths, dub actually passes all files within all 
mentioned paths to dmd to compile.



Hope I got it right : D.


Re: Inference of auto storage classes for interface function return type

2018-07-04 Thread Timoses via Digitalmars-d-learn

On Wednesday, 4 July 2018 at 15:12:15 UTC, Jonathan M Davis wrote:


You can make opIndex inout instead of const. That way, inout 
applies to the invisible this reference, just like it would 
with const.


Awww, thanks! I was kinda hovering around this[1] section and 
didn't quite see the MemberFunctionAttribute list[2]. Is there no 
further description of the behaviour with the inout attribute 
other than for parameters[1] in the spec?
There's an empty 19.10.10 point without content[3] : D. Maybe a 
placeholder?


[1]: https://dlang.org/spec/function.html#inout-functions
[2]: https://dlang.org/spec/function.html#MemberFunctionAttribute
[3]: https://dlang.org/spec/function.html#inout-functions


Inference of auto storage classes for interface function return type

2018-07-04 Thread Timoses via Digitalmars-d-learn

How can I return inferred storage class from interface functions?
I can't use auto as return value in interface. Neither can I use 
"inout" as I don't pass a parameter.


// Ref Type
interface IRef
{
Ref opIndex(size_t idx) const;
}
class CRef : IRef
{
Ref[] a;
this() immutable
{ this.a = [new Ref()]; }
Ref opIndex(size_t idx) const
		{ return a[idx]; } // Error: cannot implicitly convert 
expression this.a[idx] of type const(Ref) to app.Ref

}
class Ref{}

void main()
{
auto a = new immutable(CRef)();
auto s = a[3];
}

For value types it works, I presume since they are passed by 
value, so the instance returned is an actual copy of the stored 
value.


// Value Type
interface IValue
{
Value opIndex(size_t idx) const;
}
class CValue : IValue
{
this() immutable { i = [Value()]; }
Value[] i;
Value opIndex(size_t idx) const
{ return i[idx]; }
}
struct Value{}

However, for ref types this doesn't work.

Do I have to define two `opIndex` in the interface? One mutable, 
one for immutable type instances?


Re: template alias that includes a parameter

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 13:01:20 UTC, Timoses wrote:


Aw, okay, then that won't work.

Still, this looks like it should work:

void foo(F, T)(T param) { writeln("Called with type: ", 
T.stringof); }

alias tfoo = ApplyLeft!(foo, int);

tfoo!string("hi");
// tfoo("hi"); // Error


https://issues.dlang.org/show_bug.cgi?id=9365


Re: template alias that includes a parameter

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 11:55:15 UTC, Simen Kjærås wrote:

On Sunday, 1 July 2018 at 09:46:55 UTC, Timoses wrote:
Would be nice if std.meta.ApplyLeft did the job here.. Is 
there no way of achieving that?

[snip]
Would have to find a way to determine whether Template would 
resolve to a function or not. Can't find anything in Traits[1] 
or std.traits[2]. Template inspection looks rather limited : /.


It is, but for a fairly good reason. This is perfectly valid D:

template foo(int n) {
static if (n == 0) {
struct foo {}
} else static if (n == 1) {
enum foo = 24;
} else {
void foo() {}
}
}

Given an uninstantiated foo, you can't know if it'll resolve to 
a function or not, so I guess some version of the template I 
wrote could be added to Phobos as ApplyLeftFn or something.


Aw, okay, then that won't work.

Still, this looks like it should work:

void foo(F, T)(T param) { writeln("Called with type: ", 
T.stringof); }

alias tfoo = ApplyLeft!(foo, int);

tfoo!string("hi");
// tfoo("hi"); // Error



Re: Function Template for Dynamic Parameter

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 11:58:30 UTC, vino.B wrote:

On Sunday, 1 July 2018 at 11:52:19 UTC, Alex wrote:
NewType.d(19): Error: function declaration without return type. 
(Note that constructors are always named this)


[...]

auto coCleanFiles(T ...)(T args) {
	auto dFiles = Array!(Tuple!(string, SysTime))(dirEntries(FFs, 
SpanMode.shallow).filter!(a => a.isFile).map!(a => 
tuple(a.name, a.timeLastModified)));

return dFiles;
}

void ptManagecoRoutine(T)(T function(T ...)(T args), 
Array!string Dirlst) {

alias scRType = typeof(coRoutine(args.init));
auto PFresult = taskPool.workerLocalStorage!scRType;
ReturnType!coRoutine rData;
foreach (string FFs; Dirlst[]) { PFresult.get ~= 
coRoutine(FFs.strip); }

foreach(i; PFresult.toRange) { rData ~= i[][]; }
if (!rData[].empty) { rData[].sort!((a,b) => a[1] < 
b[1]).each!(e => writefln!"%-83s %.20s"(e[0], e[1].to!string)); 
}

}
 void main () {
 Array!string CleanDirlst;
 CleanDirlst.insertBack("C:\\Temp\\BACKUP1");
 ptManagecoRoutine(, CleanDirlst);
 }



auto coCleanFiles(T ...)(T args)
{ ... }

void ptManagecoRoutine(T)(T fun, Array!string DirList)
{
foreach (dir; DirList)
fun(dir);
}

or

 void ptManagecoRoutine2(alias func)(Array!string DirList)
   if (is (typeof(func!(typeof(DirList[0]))) == function))
 {
 alias t = typeof(DirList[0]);
 ptManagecoRoutine(!t, DirList);
 }

callable via

Array!string CleanDirlst;
ptManagecoRoutine(!string, CleanDirlst);
ptManagecoRoutine2!coCleanFiles(CleanDirlst);



Re: Function Template for Dynamic Parameter

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 11:19:50 UTC, vino.B wrote:

On Sunday, 1 July 2018 at 09:55:34 UTC, Timoses wrote:>
Hi Timoses,

  Thank you very much, can you help me on how to rewrite the 
below using Variadic template


Passing function as a parameter to another function:

void ptFun(T)(T function(string, string, int) coRoutine, 
Array!string Dirlst, ) {
alias scRType = typeof(coRoutine(string.init, string.init, 
int.init));


where the "function(string, string, int) coRoutine" should be a 
variadic function


What's your use case?

You can pretty much pass anything to a template and use "static 
if" and "static foreach" in the template to steer how the 
template is instantiated.


void func(T ...)(T args)
{
foreach (i, arg; args)
{
static if (isSomeFunction!(T[i]))
{
arg();
}
else
writeln(arg);
}
}

unittest
{
func(() => writeln("I'm a lambda function), "I'm a 
string", 3);

}

which would print:

I'm a lambda function
I'm a string
3


I'm actually a bit suprised that `isSomeFunction!(T[i])` works 
here, I'd expect an error because `i` looks like a run-time 
variable... And using that in a compile-time (static if) 
statement usually throws a CT error.



With templates one has to think "compile-time". Any "static if", 
"static foreach" or alias declarations are compile time 
constructs. What results from that after compilation is an 
instantiated template for a specific use case. For example in 
above case the template exists (is instantiated) with the 
template parameters `(void function() @safe, string, int)`.


A good source to get some more insights is always:
http://ddili.org/ders/d.en/templates.html
(including all other sections of the book)


Re: Function Template for Dynamic Parameter

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 09:46:32 UTC, vino.B wrote:

All,

   Request your help, the D document states that "Template 
functions are useful for avoiding code duplication - instead of 
writing several copies of a function, each with a different 
parameter type, a single function template can be sufficient" 
which mean we can passing any type of parameter using function 
template, similarly who we we pass in any number of parameter 
of any type(dynamic parameters) , like in python


Python

def myfunc(*arg)
def myfunc(**kwargs) // multiple key-value
def myfunc(*args, **kwargs): mix

Do we have any thing similar to the above python in D
void (func(T)( T *args) // Example


Examples:
void func(T)(T x)
{
writeln(x);
}
void main()
{ func("x");  // pass a string }


void func(T)(T n3)
{
writeln(n); // where n = 3 parameters (1, string, char)
}

void func(T)(T n2)
{
writeln(n); // where n = 3 parameters (1, string)
}

void func(T)(T n1)
{
writeln(n); // where n = 3 parameters (1 or string or char)
}

From,
Vino.B


Perhaps https://dlang.org/spec/template.html#variadic-templates

void func(T ...)(T args)
{
static assert(T.length <= 3);

static assert(is(T[0] == int)); // 1

pragma(msg, T.stringof);
foreach (arg; args)
{
writeln(arg);
}
}

void main()
{
func(3, "s", 1.3);
//func(1.3); // error, first argument is not an int, see 
// 1

}


Re: template alias that includes a parameter

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 01:48:15 UTC, Simen Kjærås wrote:


I'd send you straight to std.meta.ApplyLeft, but it seems to do 
the wrong thing here, in that it doesn't handle IFTI. This 
thing does:


void fooImpl(int n, T)(const T line) { }

unittest {
alias fun = applyLeft!(fooImpl, 3);
fun(`aaa`);
applyLeft!(fooImpl, 3)(`aaa`);
}

template applyLeft(alias Fn, T...) {
auto applyLeft(U...)(U args) {
return Fn!T(args);
}
}


Would be nice if std.meta.ApplyLeft did the job here.. Is there 
no way of achieving that?

It's current implementation looks like this:

template ApplyLeft(alias Template, args...)
{
alias ApplyLeft(right...) = SmartAlias!(Template!(args, 
right));

}

private template SmartAlias(T...)
{
static if (T.length == 1)
{
alias SmartAlias = Alias!T;
}
else
{
alias SmartAlias = AliasSeq!T;
}
}

Would have to find a way to determine whether Template would 
resolve to a function or not. Can't find anything in Traits[1] or 
std.traits[2]. Template inspection looks rather limited : /.


[1]: https://dlang.org/spec/traits.html
[2]: https://dlang.org/phobos/std_traits.html





Re: Call different member functions on object sequence with a generic handler function?

2018-07-01 Thread Timoses via Digitalmars-d-learn

On Sunday, 1 July 2018 at 06:55:35 UTC, Robert M. Münch wrote:


The looping needs to be done in the handler because there are 
two loops running one after the other and the range to loop 
over is detected in the handler too. Otherwise a lot of code 
duplication would happen.


Maybe an application for filter?

C[] cs = ...;
cs.filter!((c) => )
  .each!((c) => c.a())


Re: template alias that includes a parameter

2018-06-30 Thread Timoses via Digitalmars-d-learn

On Saturday, 30 June 2018 at 21:11:54 UTC, Anonymouse wrote:
I have a template that I want to provide easy aliases for, 
where the aliases includes (partially applies?) a template 
parameter.



void fooImpl(char token, T)(const T line)
{
// ...
}

alias quoteFoo(T) = fooImpl!('"', T);


would be the same as

template quoteFoo(T)
{
alias quoteFoo = fooImpl!('"', T);
}

There is no "Implicit Function Template Instantiation (IFTI)" 
(https://dlang.org/spec/template.html#function-templates) here, 
as that only works for function templates. That means the 
compiler won't deduce the template parameter type. So that alias 
would have to be called with


quoteFoo!string("I'm a quoted sentence.");


alias singlequoteFoo(T) = fooImpl!('\'', T);

void main()
{
quoteFoo(`"asdf"`);
singlequoteFoo(`'asdf'`);
}


...was how I'd imagined it would look.

onlineapp.d(11): Error: template onlineapp.quoteFoo cannot 
deduce function from argument types !()(string), candidates are:

onlineapp.d(6):onlineapp.quoteFoo(T)


If I manually pass string as a template parameter, like 
quoteFoo!string("bar") or singlequoteFoo!string("baz"), it 
works.


Can I do it this way or do I need to write wrapping functions?


Instead of using aliases you could instantiate the function and 
use a function pointer to it (I hope my lingo is correct...).


auto quoteFooString = !('"', string);

and use it with

quoteFooString("I'm another quoted sentence.");

I'm trying to find a way to partially apply something to the 
template like


//alias quoteFoo = ApplyLeft!(fooImpl, '"', AliasSeq!(int));
//quoteFoo(3);

so the template fooImpl would only be partly instantiated with a 
'"', but the second argument would be left for when calling the 
function.. Unfortunately, above yields the error


std/meta.d(1232): Error: template instance `Template!'"'` 
does not match template declaration fooImpl(char token, T)(const 
T line)


... Hm..


https://run.dlang.io/is/di8zjl

import std.stdio;

void fooImpl(char token, T)(const T line)
{
writefln("%s%s%s", token, line, token);
}

auto quoteFooString = !('"', string);
auto singlequoteFooString = !('\'', string);

void main()
{
quoteFooString("test quote");
singlequoteFooString("test single quote");


import std.meta;
// std/meta.d(1232): Error: template instance 
`Template!'"'` does not match template

//alias quoteFoo = ApplyLeft!(fooImpl, '"');
//quoteFoo(3);
}


Re: Call different member functions on object sequence with a generic handler function?

2018-06-29 Thread Timoses via Digitalmars-d-learn

On Friday, 29 June 2018 at 20:28:55 UTC, Timoses wrote:

On Friday, 29 June 2018 at 16:44:36 UTC, Robert M. Münch wrote:

Trying to fiddle around a bit with delegates.. But why is the 
context for delegates not working for classes??


Aw.. Class = reference type so

class A { }
struct B { }
void delegate() del;
A a = new A();
del.ptr = a;   // NOT its address, as that would be the address 
of the reference on the stack

B b = B();
del.ptr =// value type => address of object in stack

... How would one print the address of the object then though?
Since  is the address of the reference' types stack location.

cast(void*)a

would be on solution I guess.


Re: Call different member functions on object sequence with a generic handler function?

2018-06-29 Thread Timoses via Digitalmars-d-learn

On Friday, 29 June 2018 at 16:44:36 UTC, Robert M. Münch wrote:

I hope this is understandable... I have:

class C {
void A();
void B();
void C();
}

I'm iterating over a set of objects of class C like:

foreach(obj; my_selected_objs){
...
}

The iteration and code before/afterwards always looks the same, 
I need this iteration for many of the memember functions like 
C.A() and C.B(), etc.


foreach(obj; my_selected_objs){
...
obj.A|B|C()
...
}

So, how can I write a generic handler that does the iteration, 
where I can specify which member function to call?


void do_A() {
handler(C.A()); ???
}

void do_B() {
handler(C.B()); ???
}

handler(???){
foreach(obj: my_selected_objs){
???
}
}

Viele Grüsse.


Trying to fiddle around a bit with delegates.. But why is the 
context for delegates not working for classes??


https://run.dlang.io/is/Rxeukg

import std.stdio;

class Aclass
{
int i;
void foo() { writeln("called ", i); }
}
struct Bstruct
{
int i;
void foo() { writeln("called ", i); }
}


template callFoo(T)
{
alias Dun = void delegate();

void callFoo(T t)
{
Dun fun;
fun.funcptr = 
fun.ptr = cast(void*)();

Dun gun;
gun = 

writeln(fun.ptr, " (fun.ptr of " ~ T.stringof ~ ")");
writeln(gun.ptr, " (gun.ptr of " ~ T.stringof ~ ")");
writeln(, " (Address of instance (context))");

fun();
gun();
}

}

void main()
{
auto a = new Aclass();
a.i = 5;
auto b = Bstruct();
b.i = 7;
writeln(" Doesn't work ");
callFoo(a);
writeln("\n Works ");
callFoo(b);
}


Re: Call different member functions on object sequence with a generic handler function?

2018-06-29 Thread Timoses via Digitalmars-d-learn

On Friday, 29 June 2018 at 20:08:56 UTC, Robert M. Münch wrote:

On 2018-06-29 18:05:00 +, Ali ‡ehreli said:


On 06/29/2018 09:44 AM, Robert M. Münch wrote:
void handler(alias func)(C[] cs) {
 foreach (c; cs) {
 func(c);
 }
}


Is it possible to make C[] a template type so that I can use 
different classes and lambdas?


My guess would be:

void handler(alias func, T)(T[] ts) {

}



Ok, the "strange" syntax for me is the handler(alias func) or 
handler(string func) ... I'm alway thinkin in lines of a 
parameter... which of course doesn't work.


Looking at the D grammer for functions these things should be 
the FuncDeclaratorSuffix, is this right? And then, which part 
does this fall into?


FuncDeclaratorSuffix:
   Parameters MemberFunctionAttributesopt
   TemplateParameters Parameters MemberFunctionAttributesop


It's definitely the "TemplateParameters" one:

void func()() { ... }

is the short form of

template()
{
void func() { ... }
}

https://dlang.org/spec/template.html


Re: Issues with undefined symbols when using Vibe on Windows

2018-06-29 Thread Timoses via Digitalmars-d-learn

On Friday, 29 June 2018 at 19:25:42 UTC, Chris M. wrote:
This doesn't appear to specifically be a Vibe issue, just 
noticing this error when I use eventcore from it (trying to use 
async).


C:\dmd2\windows\bin\lld-link.exe: warning: 
eventcore.lib(sockets_101f_952.obj): undefined symbol: 
SetWindowLongPtrA
C:\dmd2\windows\bin\lld-link.exe: warning: 
eventcore.lib(sockets_101f_952.obj): undefined symbol: 
GetWindowLongPtrA


I'm using DMD 2.080 from the zip file provided on the downloads 
page, plus DMC (unfortunately acquiring a Visual Studio license 
would not be easy at my workplace, and I don't see how to use 
the provided DMD installer without it). As far as I can tell, 
this issue seems to be happening because user32.lib from the 
windows/lib64/mingw folder does not define these two functions. 
Seems to work when I build the project as 32-bit though. 
Wondering if someone could double-check my reasoning here.


Did you see this?
https://github.com/vibe-d/vibe.d#note-for-building-on-win64
Perhaps it could be that?


Re: Why tuples are not ranges?

2018-06-28 Thread Timoses via Digitalmars-d-learn

On Thursday, 28 June 2018 at 14:35:33 UTC, Mr.Bingo wrote:

Seems like it would unify things quite a bit.

import std.typecons, std.range, std.array, std.algorithm, 
std.stdio;


void main()
{
auto t = tuple(3,4,5,6);
//auto t = [3,4,5,6];

writeln(t.map!(a => 3*a).sum());


}


You could make a range out of tuples. This seems to work:

import std.typecons, std.range, std.array, std.algorithm, 
std.stdio;


void main()
{
auto t = tuple(3,4,5,6);
auto m = t.expand.only;
writeln(m.map!(a => 3*a).sum());
}

Tuple.expand will expand the elements when calling a function (in 
this case only from std.range).

https://dlang.org/library/std/typecons/tuple.expand.html


Re: Getting Source code from complied code.

2018-06-28 Thread Timoses via Digitalmars-d-learn

On Thursday, 28 June 2018 at 08:01:42 UTC, vino.B wrote:

Hi All,

  Request your help on how to get the source code, i wrote a 
program named clean.d, complied it and by mistake deleted the 
source code(clean.d), so can we get back the source using the 
complied program(clean), if yes, can you any one help on the 
same.



From,
Vino.B


Use a versioning system and push important changes as soon as 
you're done with smth to a remote location ; ). E.g. Git


Re: anyway to pass the context of an inner type to a template so it can be constructed?

2018-06-27 Thread Timoses via Digitalmars-d-learn

On Wednesday, 27 June 2018 at 12:02:10 UTC, aliak wrote:

This currently fails unless you mark the class as static:

auto construct(T)() {
return new T;
}
void main() {
class C {}
auto s = construct!C;
}

So wondering if there's anything that can be done to get the 
above working?



Or if there isn't then how could the compiler be enhanced to 
allow for something like this if possible?


===
The use case is for a non-nullable type, where I want to 
guarantee that the value inside will never be null. I can't do 
it for inner classes though. And I can't allow the user to do 
something like:


void main() {
class C {}
auto s = construct(new C);
}

Because I can't guarantee that's not null.


Cheers,
- Ali


After a bit of experimentation

import std.stdio;
template construct1(T)
{
enum construct1 = "new " ~ T.stringof;
}

template construct2(T)
{
// Attempt 1
// can't do this : /
//alias construct2 = mixin(construct1!T);

// Attempt 2
T construct2()
{
// Error: outer function context of D main is needed 
to new nested class onlineapp.main.C

//return new T;

// Error: undefined identifier C
//mixin("return new " ~ T.stringof ~ ";");

return null; // ...
}
}

mixin template construct3(string s, T)
{
mixin("auto " ~ s ~ " = new " ~ T.stringof ~ ";");
}

void main() {
class C { int i = 4;}

auto a = mixin(construct1!C);
assert(a.i == 4);

mixin construct3!("b", C);
b.i = 3;
assert(b.i == 3);

// trying to get around using mixin here...
auto c = construct2!C;
}


Can't seem to avoid using mixin in main..


Re: Making sense of recursion

2018-06-26 Thread Timoses via Digitalmars-d-learn

On Monday, 25 June 2018 at 17:45:01 UTC, zbr wrote:
Hi, this question is not specifically D related but I'll just 
ask anyway. Consider the following snippet:


void mergeSort(int[] arr, int l, int r)
{
   if (l < r)   // 1
   {
  int m = l+(r-l)/2;// 2
  mergeSort(arr, l, m); // 3
  mergeSort(arr, m+1, r);   // 4
  merge(arr, l, m, r);  // 5
   }// 6
}   // 7

mergeSort(arr, 0, 4);

When I see this, I visualize the recursion to perform this way:

mergeSort(arr, 0, 4):
0 < 4 ? true: mergeSort(0, 2):
0 < 2 ? true: mergeSort(0, 1):
0 < 1 ? true: mergeSort(0, 0):
0 < 0 ? false: //reach the end of mergeSort / 
reach line 6 and then 7


I don't see the computer ever reaching line 4 and 5? Obviously 
I'm wrong but where is my mistake?


Thanks.


It's a stack (https://en.wikipedia.org/wiki/Call_stack).

When the program calls a function it is pushed onto the stack. If 
that function returns it pops from the stack and the previous 
function gets to continue execution from where it stopped before.


Re: Using systemDependencies in DUB

2018-06-24 Thread Timoses via Digitalmars-d-learn

On Sunday, 24 June 2018 at 11:44:06 UTC, Dechcaudron wrote:

Hi,

I'm trying to use dub to compile a quick experiment that uses 
Deimos libclang bindings, which of course requires linking 
against an installed libclang. I believe this is what I need to 
include in dub.json:


 "systemDependencies": "libclang-6.0"

But it just won't link against the lib in the compilation 
process. Using the -v option reveals the linking stage call:


/usr/bin/dmd 
-of.dub/build/application-debug-linux.posix-x86_64-dmd_2081-7C29937BC9011750CFA15D7325224156/damnc .dub/build/application-debug-linux.posix-x86_64-dmd_2081-7C29937BC9011750CFA15D7325224156/damnc.o -L--no-as-needed -g


It does not mention libclang at all. I've tried with all 
"clang", "libclang-6.0.so.1", but I just don't seem to be able 
to make it work. Would anyone mind helping me out?


BTW, I am aware Deimos bindings for libclang are based on v3.7 
and not 6.0, but 3.7 is not available for Ubuntu 18.04 and I 
was wagering the interface probably hasn't changed much.


Hm, the description sounds like it might not be used for passing 
linker arguments, but serves for adding documentation to linker 
errors:
"A textual description of the required system dependencies 
(external C libraries)
required by the package. This will be visible on the registry 
and will be
displayed in case of linker errors - this setting does not 
support platform

suffixes".

What about the "libs" build settings (or "lflags")? 
(http://code.dlang.org/package-format?lang=json)


"libs": "clang"


Re: Can I parse this kind of HTML with arsd.dom module?

2018-06-24 Thread Timoses via Digitalmars-d-learn

On Sunday, 24 June 2018 at 03:46:09 UTC, Dr.No wrote:

string html = get(page, client).text;
auto document = new Document();
document.parseGarbage(html);
Element attEle = document.querySelector("span[id=link2]");
Element aEle = attEle.querySelector("a");
string link = aEle.href; // <-- if the href contains space, it 
return "href" rather the link


[...]




Hello, dear world!

https://hostname.com/?file=foo.png=baa;>G!




missing 

Seems to be buggy, the parsed document part refering to "a" looks 
like this:


G!




Re: Is HibernateD dead?

2018-06-23 Thread Timoses via Digitalmars-d-learn

On Thursday, 3 May 2018 at 10:27:47 UTC, Pasqui23 wrote:

Last commit on https://github.com/buggins/hibernated
was almost a year ago

So what is the status of HibernateD?Should I use it if I need 
an ORM? Or would I risk unpatched security risks?


Okay... wall of text.
TLDR: project definition / future of HibernateD?; prospects of an 
OGM layer integration (personally interested in Neo4j)?



I've been thinking of trying to implement an OGM (Object-graph 
mapping; i.e. NoSQL) for Neo4j in D as I'd love using it for a 
project of mine. The question is, whether it should be a separate 
project or whether something like this could be integrated with 
HibernateD.


I've taken a look at Hibernate ORM and OGM. There OGM is a 
separate project leveraging a lot of ORMs capabilities.


I'm still in the process of diving deeper into Hibernate's 
ORM/OGM documentation(/implementation) to get an idea of how it 
all works. I'm not particularly experienced with it.


One question that arises in respect to HibernateD is:
What is the purpose of HibernateD? The README states "HibernateD 
is ORM for D language (similar to Hibernate)". I guess there are 
two Extremes:


A. Replicate the structure of Hibernate into D, in a way porting 
it 1:1,


B. Implement an ORM from scratch.

Both approaches would be impractical for the following reasons:

contra A. An exact replica would leave no room for optimizations 
or creating a more D-idiomatic library,


contra B. Creating a completely new solution and interface would 
miss out on leveraging what Hibernate already "knows". Further, 
Hibernate users might love seeing a familiar interface they can 
work with. Option B wouldn't deserve the name "HibernateD"..


This solely highlights that the project's purpose/description 
might need some more explanation.


A small look into the code reveals that the approach leans 
towards implementing the component structure of Hibernate (such 
as dialects, a Hibernate(D) basic type system, ...).


I'd guess this would be the most practical approach:

Leverage Hibernate's insights into what components are required 
to implement an ORM(/OGM) (Dialects, Hibernate(D) types, 
annotations, Persistence Strategies, ...) and find D-idiomatic 
ways for implementation. Any space for optimization should 
naturally be capitalized on.


A complete 1:1 replica does not seem practical as for example 
I've stumbled across the "@Immutable" annotation in the Hibernate 
documentation. As there is the "immutable" qualifier in D, 
through introspection, this quality could be deduced from 
entities/members. This leads to thinking that solutions tailored 
towards D need to be found and therefore deviation from Hibernate 
sounds reasonable.



I am in no way an expert in ORMs (I just started reading 
Hibernate's ORM documentation) and I have no idea what other ORMs 
are out there (D or non-D). However, Hibernate seems quite 
popular (and it offers a Neo4j OGM interface) and the fact that 
it exists for D (at least in a "starting positition") caught my 
attention.


What do you think? Especially bauss, Matthias and singingbush, as 
you seem motivated to move the project forward. Maybe Vadim also 
has a standpoint : ).





Re: Convert path to file system path on windows

2018-06-21 Thread Timoses via Digitalmars-d-learn

On Thursday, 21 June 2018 at 18:46:05 UTC, Dr.No wrote:

How can I do that with D?

In C# you can do that:

var filename = @"C:\path\to\my\file.txt";
var file = new Uri(filename).AbsoluteUri;
// file is "file:///C:/path/to/my/file.txt"

How can I do that in D?


I don't know of a specific implementation that does the same, but 
I can point you to some spots you might look into:


std.path: https://dlang.org/phobos/std_path.html
std.uri: https://dlang.org/phobos/std_uri.html

vibe.inet.url: http://vibed.org/api/vibe.inet.url/URL
vibe.core.path: http://vibed.org/api/vibe.core.path/


I really feel like vibed's documentation api site is missing some 
nice examples of usage to get a quick feel of the provided api.


Re: scope(success) lowered to try-catch ?

2018-06-17 Thread Timoses via Digitalmars-d-learn

On Sunday, 17 June 2018 at 10:58:29 UTC, Cauterite wrote:

Hello,
I'm not sure whether I'm missing something obvious here, but is 
there a reason for scope(success) being lowered to a try-catch 
statement?
I would have expected only scope(exit) and scope(failure) to 
actually interact with exception handling, while scope(success) 
simply places code on the path of normal control flow.


Example (windows x32):

---

// main.d
void main() {
scope(success) {}
}


dmd -betterC main.d

Error: Cannot use try-catch statements with -betterC

---

Regardless of whether -betterC is used, you can see in the 
disassembly that having a scope(success) anywhere in the 
function causes the SEH prologue to be emitted in the code.


Is there a reason scope(success) needs to set up for exception 
handling?

Or is this a bug / potential enhancement ?


In Andrei's book 'The D Programming Language' the following is 
written:


{

scope(success) 

}
is lowered to
{

bool __succeeded = true;
try {

} catch(Exception e) {
__succeeded = false;
throw e;
} finally {
if (__succeeded)  // vice-versa for 
scope(failure): `if (!__succeeded) ...`

}
}

If it weren't and it would simply be integrated one would have to 
write


potentiallyThrowingFunc();
scope(success) {...};

I suppose? And this seems like breaking how scope works with 
failure and exit?!


Re: foreach DFS/BFS for tree data-structure?

2018-06-16 Thread Timoses via Digitalmars-d-learn

On Thursday, 14 June 2018 at 11:31:50 UTC, Robert M. Münch wrote:

I have a simple tree C data-structure that looks like this:

node {
node parent:
vector[node] children;
}

I would like to create two foreach algorthims, one follwing the 
breadth first search pattern and one the depth first search 
pattern.


Is this possible? I read about Inputranges, took a look at the 
RBTree code etc. but don't relly know/understand where to start.


What I found really interesting when reading Ali Çehreli's book 
'Programming in D' was using fibers for tree iteration.


Check out http://ddili.org/ders/d.en/fibers.html and skip to the 
section "Fibers in range implementations"


  1   2   >