Re: Parse .eml files

2018-04-10 Thread bachmeier via Digitalmars-d-learn

On Monday, 9 April 2018 at 19:17:20 UTC, Adam D. Ruppe wrote:

[...]

I had a chance to try this out and it worked without a problem. I 
did have to download color.d in addition to the other 
dependencies you listed. In the event that Google brings someone 
here, this is a complete working program:


import std.file, std.stdio, std.string;
import arsd.email;

void main(string[] args) {
  string[] f = std.file.readText(args[1]).splitLines();
  auto em = new IncomingEmailMessage(f);
  writeln("From: ", em.from);
  writeln("To: ", em.to);
  writeln("Subject: ", em.subject);
  writeln(em.textMessageBody);
}

Compile with

dmd *.d -ofreademail

And run

./reademail 'email message.eml'



Re: Strange Thread Causing Duplicating `writeln`

2018-04-10 Thread Steven Schveighoffer via Digitalmars-d-learn

On 4/9/18 6:56 PM, Jonathan wrote:

On Monday, 9 April 2018 at 22:53:31 UTC, Jonathan wrote:

On Monday, 9 April 2018 at 22:49:07 UTC, Cym13 wrote:
I don't know, but I can't reproduce either with dmd or ldc. What was 
your compilation line?


dmd -run file.d


I am on Window 10 btw.


It's a windows 32-bit issue (specifically, DMC's FILE *, upon which 
std.stdio.File is based, is thread unsafe).


Try -m64.

https://issues.dlang.org/show_bug.cgi?id=18483
http://bugzilla.digitalmars.com/issues/show_bug.cgi?id=327

-Steve


Re: Should "a is b" compile if a and b have unrelated classes?

2018-04-10 Thread Steven Schveighoffer via Digitalmars-d-learn

On 4/10/18 5:52 PM, Michael Coulombe wrote:
I had a bug in my code that was messing me up for a while, and it boiled 
down to an identity check between two Object references with unrelated 
static types, like below:


class A {}
class B {}
void main() {
     A a = new A;
     B b = new B;
     if (a is b) {} // compiles
}

I was surprised that the type system failed me here. It's true that A 
and B could be upcast to Object and then comparisons would make sense 
type-wise, but the comparison should never pass (and the compiler should 
know it won't since they are in separate inheritance subtrees) unless 
the programmer is intentionally breaking the type system.


Is there reasoning for this? If not, should it be a warning or error, as 
it is for example when comparing two pointers to structs of different 
types?


Probably the reason is laziness. Sure it could be outlawed.

But `is` has a special connotation of "identity", meaning it's EXACTLY 
the same. Let's look at what does compile:


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

So there is at least some type checking for `is`, when it comes to 
pointers. There's definitely a precedent for this.


The question is, should it just fold to "false", or should it fail to 
compile? If we change it to an error, there may be some unintentional 
code breakage out there.


-Steve


Re: Range length property

2018-04-10 Thread Steven Schveighoffer via Digitalmars-d-learn

On 4/10/18 6:07 PM, Cym13 wrote:

On Tuesday, 10 April 2018 at 20:08:14 UTC, Jonathan M Davis wrote:
On Tuesday, April 10, 2018 19:47:10 Nordlöw via Digitalmars-d-learn 
wrote:

On Tuesday, 10 April 2018 at 14:34:40 UTC, Adam D. Ruppe wrote:
> On Tuesday, 10 April 2018 at 14:25:52 UTC, Nordlöw wrote:
>> Should ranges always provide a length property?
>
> No.
>
>> If so, in which cases is a length property an advantage or >> a 
requirement?

>
> Just provide it whenever it is cheap to do so. If you need > to do 
complex calculations or especially loop over contents > to figure out 
the length, do NOT provide it.

>
> But if it is as simple as returning some value, provide it > and 
algorithms can take advantage of it for optimizations > etc. as needed.


I'm thinking of my own container Hashmap having its range ByKeyValue 
requiring one extra word of memory to store the iteration count 
which, in turn, can be used to calculate the length of the remaining 
range. Is this motivated?


That would depend entirely on what you're trying to do, but in 
general, if a range has length, then some algorithms will be more 
efficient, and some algorithms do require length. So, if you can 
provide length, then the range will be more useful, just like a 
bidirectional range can be more useful than a forward range or a 
random-access range can be more useful than either. However, if you're 
not doing anything that ever benefits from it having length, then it 
doesn't buy you anything. So, it ultimately depends on what you're 
doing. In a general purpose library, I'd say that it should have 
length if it can do so in O(1), but if it's just for you, then it may 
or may not be worth it.


The other thing to consider is what happens when the container is 
mutated. I don't think that ranges necessarily behave all that well 
when an underlying container is mutated, but it is something that has 
to be considered when dealing with a range over a container. Even if 
mutating the underlying container doesn't necessarily invalidate a 
range, maintaining the length in the manner that you're suggesting 
probably makes it so that it would be invalidated in more cases, since 
if any elements are added or removed in the portion that was already 
popped off the range, then the iteration count couldn't be used to 
calculate the length in the same way anymore. Now, with a hash map, 
the range is probably fully invalidated when anything gets added or 
removed anyway, since that probably screws with the order of the 
elements in the range, but how the range is going to behave when the 
underlying container is mutated and how having the length property 
does or doesn't affect that is something that you'll need to consider.


- Jonathan M Davis


I find that discussion very interesting as I had never considered that 
because of design by introspection having a costly length method would 
lead to unexpected calls by generic algorithms making it a disadventage 
if present.


On the other hand I don't think the end user should have to scratch his 
head to find the length of a range, especially if it's not trivial to 
get (say, O(log n) kind of case). Therefore exposing a method in any 
case seems the best from an API perspective.


O(lg n) is fine for .length, it doesn't need to be O(1). It just can't 
be O(n). I think we established that "fast" operations are O(lg n) or 
better.


That being said, I don't know of a use case where you can get the length 
in O(lg n). It's usually O(1) or O(n).


But to avoid the performance issues mentionned earlier it means it 
should bear a different name (get/setLength comes to mind). I believe 
this is the same kind of issue that lead to having "in" for associative 
arrays but not regular ones. However this also leads to less coherent 
APIs in contradiction with the principle of least surprise.


It's definitely a tradeoff. It pushes some implementation details to the 
user, but it also makes the runtime complexity more predictable.


In retrospect since only "unexpected" calls to such methods cause the 
issue I wonder if it wouldn't be best to have an UDA saying "Hey, 
please, this method is costly, if you're a generic template performing 
introspection you should probably not call me". And writing that 
Andrei's work on complexity annotations comes to mind. Anyway, I don't 
think the user should use different names just to alleviate an issue on 
the library side but the alternative would be costly to put in place...


Potentially, but remember at the time length and walkLength were 
conceived, UDA's didn't exist!


Using UDAs would also have the unfortunate side effect of eliminating 
self-documentation. When you see walkLength right now, you know it's 
"slow", when you see length, you know "fast". If you have to look at 
UDAs to figure that out, then reading the code is that much harder.


-Steve


Re: Range length property

2018-04-10 Thread H. S. Teoh via Digitalmars-d-learn
On Tue, Apr 10, 2018 at 10:07:40PM +, Cym13 via Digitalmars-d-learn wrote:
[...]
> On the other hand I don't think the end user should have to scratch
> his head to find the length of a range, especially if it's not trivial
> to get (say, O(log n) kind of case). Therefore exposing a method in
> any case seems the best from an API perspective.
> 
> But to avoid the performance issues mentionned earlier it means it
> should bear a different name (get/setLength comes to mind). I believe
> this is the same kind of issue that lead to having "in" for
> associative arrays but not regular ones. However this also leads to
> less coherent APIs in contradiction with the principle of least
> surprise.
[...]

I've run into this in my own code, and I've been using `walkLength` as
the name of the method, just for consistency with Phobos' walkLength.
I'm not 100% sure this is a good idea, since overloading Phobos names
can sometimes lead to annoying symbol conflict situations.  But the one
good thing is that you won't forget what it's called because it's so
familiar.


T

-- 
An elephant: A mouse built to government specifications. -- Robert Heinlein


Re: Should "a is b" compile if a and b have unrelated classes?

2018-04-10 Thread Jonathan M Davis via Digitalmars-d-learn
On Tuesday, April 10, 2018 21:52:22 Michael Coulombe via Digitalmars-d-learn 
wrote:
> I had a bug in my code that was messing me up for a while, and it
> boiled down to an identity check between two Object references
> with unrelated static types, like below:
>
> class A {}
> class B {}
> void main() {
>  A a = new A;
>  B b = new B;
>  if (a is b) {} // compiles
> }
>
> I was surprised that the type system failed me here. It's true
> that A and B could be upcast to Object and then comparisons would
> make sense type-wise, but the comparison should never pass (and
> the compiler should know it won't since they are in separate
> inheritance subtrees) unless the programmer is intentionally
> breaking the type system.
>
> Is there reasoning for this? If not, should it be a warning or
> error, as it is for example when comparing two pointers to
> structs of different types?

Well, the compiler can't simply say that they're different classes and
refuse to compare their references. It could look at the class hierarchy and
determine that there's no way that the two are the same reference, because
neither A nor B is a subclass of the other and thus treat it as an error -
which I gather is what you're suggesting it should do. However, because
doing that is more complicated, I suspect that it just doesn't bother. With
struct pointers, it can at least see at a glance that one can't be the
other, whereas it has to do a lot more examination of the type if it's class
references.

It's probably a reasonable enhancement request, though I'm not sure that it
really matters much. One potential issue is that since opEquals is
unfortunately part of Object, it's perfectly legal to do

if(a == b)

even though a and b can never be equal, so if is were disallowed in this
case, then we'd get a situation where a == b compiles but a is b doesn't
which would be a bit weird - though presumably, if we do end up going with
some form of Andrei's ProtoObject proposal where we get a new root class
beneath Object, then we'd definitely have classes that could be compared
with is but not ==. So, that may not be all that big a deal as weird as it
may be.

My bigger concern would be how it would interact with generic code. It's not
uncommon that stuff that at first glance seems like it should be disallowed
would actually cause a fair but of grief in generic code (e.g. that's at
least part of why it's usually the case that function attributes that don't
apply are just ignored rather than treated as errors). If it definitely
wasn't going to cause problems for generic code, then such a change would
probably be reasonable, but I have no idea how likely it would be to cause
problems in generic code.

So, maybe? You can certainly open an enhancement request about it.

- Jonathan M Davis



Re: Range length property

2018-04-10 Thread Jonathan M Davis via Digitalmars-d-learn
On Tuesday, April 10, 2018 22:07:40 Cym13 via Digitalmars-d-learn wrote:
> On Tuesday, 10 April 2018 at 20:08:14 UTC, Jonathan M Davis wrote:
> > On Tuesday, April 10, 2018 19:47:10 Nordlöw via
> >
> > Digitalmars-d-learn wrote:
> >> On Tuesday, 10 April 2018 at 14:34:40 UTC, Adam D. Ruppe wrote:
> >> > On Tuesday, 10 April 2018 at 14:25:52 UTC, Nordlöw wrote:
> >> >> Should ranges always provide a length property?
> >> >
> >> > No.
> >> >
> >> >> If so, in which cases is a length property an advantage or
> >> >> a requirement?
> >> >
> >> > Just provide it whenever it is cheap to do so. If you need
> >> > to do complex calculations or especially loop over contents
> >> > to figure out the length, do NOT provide it.
> >> >
> >> > But if it is as simple as returning some value, provide it
> >> > and algorithms can take advantage of it for optimizations
> >> > etc. as needed.
> >>
> >> I'm thinking of my own container Hashmap having its range
> >> ByKeyValue requiring one extra word of memory to store the
> >> iteration count which, in turn, can be used to calculate the
> >> length of the remaining range. Is this motivated?
> >
> > That would depend entirely on what you're trying to do, but in
> > general, if a range has length, then some algorithms will be
> > more efficient, and some algorithms do require length. So, if
> > you can provide length, then the range will be more useful,
> > just like a bidirectional range can be more useful than a
> > forward range or a random-access range can be more useful than
> > either. However, if you're not doing anything that ever
> > benefits from it having length, then it doesn't buy you
> > anything. So, it ultimately depends on what you're doing. In a
> > general purpose library, I'd say that it should have length if
> > it can do so in O(1), but if it's just for you, then it may or
> > may not be worth it.
> >
> > The other thing to consider is what happens when the container
> > is mutated. I don't think that ranges necessarily behave all
> > that well when an underlying container is mutated, but it is
> > something that has to be considered when dealing with a range
> > over a container. Even if mutating the underlying container
> > doesn't necessarily invalidate a range, maintaining the length
> > in the manner that you're suggesting probably makes it so that
> > it would be invalidated in more cases, since if any elements
> > are added or removed in the portion that was already popped off
> > the range, then the iteration count couldn't be used to
> > calculate the length in the same way anymore. Now, with a hash
> > map, the range is probably fully invalidated when anything gets
> > added or removed anyway, since that probably screws with the
> > order of the elements in the range, but how the range is going
> > to behave when the underlying container is mutated and how
> > having the length property does or doesn't affect that is
> > something that you'll need to consider.
> >
> > - Jonathan M Davis
>
> I find that discussion very interesting as I had never considered
> that because of design by introspection having a costly length
> method would lead to unexpected calls by generic algorithms
> making it a disadventage if present.
>
> On the other hand I don't think the end user should have to
> scratch his head to find the length of a range, especially if
> it's not trivial to get (say, O(log n) kind of case). Therefore
> exposing a method in any case seems the best from an API
> perspective.
>
> But to avoid the performance issues mentionned earlier it means
> it should bear a different name (get/setLength comes to mind). I
> believe this is the same kind of issue that lead to having "in"
> for associative arrays but not regular ones. However this also
> leads to less coherent APIs in contradiction with the principle
> of least surprise.
>
> In retrospect since only "unexpected" calls to such methods cause
> the issue I wonder if it wouldn't be best to have an UDA saying
> "Hey, please, this method is costly, if you're a generic template
> performing introspection you should probably not call me". And
> writing that Andrei's work on complexity annotations comes to
> mind. Anyway, I don't think the user should use different names
> just to alleviate an issue on the library side but the
> alternative would be costly to put in place...
>
> Any thoughts?

In general, if you care about efficient code, it becomes critical that
anything that's going to be used in generic code has well-known Big-O
complexity, which is why C++ cares about that sort of thing with its
containers and why Andrei specifically put the Big-O complexity of all of
the generic container operations in std.container. And that extends to
ranges. If ranges are implemented without any care about the algorithmic
complexity of the operations, then performance is ultimately going to tank.
And in the case of ranges, it's really not all that hard to understand the
algorithmic complexity, because 

Re: Range length property

2018-04-10 Thread Cym13 via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 20:08:14 UTC, Jonathan M Davis wrote:
On Tuesday, April 10, 2018 19:47:10 Nordlöw via 
Digitalmars-d-learn wrote:

On Tuesday, 10 April 2018 at 14:34:40 UTC, Adam D. Ruppe wrote:
> On Tuesday, 10 April 2018 at 14:25:52 UTC, Nordlöw wrote:
>> Should ranges always provide a length property?
>
> No.
>
>> If so, in which cases is a length property an advantage or 
>> a requirement?

>
> Just provide it whenever it is cheap to do so. If you need 
> to do complex calculations or especially loop over contents 
> to figure out the length, do NOT provide it.

>
> But if it is as simple as returning some value, provide it 
> and algorithms can take advantage of it for optimizations 
> etc. as needed.


I'm thinking of my own container Hashmap having its range 
ByKeyValue requiring one extra word of memory to store the 
iteration count which, in turn, can be used to calculate the 
length of the remaining range. Is this motivated?


That would depend entirely on what you're trying to do, but in 
general, if a range has length, then some algorithms will be 
more efficient, and some algorithms do require length. So, if 
you can provide length, then the range will be more useful, 
just like a bidirectional range can be more useful than a 
forward range or a random-access range can be more useful than 
either. However, if you're not doing anything that ever 
benefits from it having length, then it doesn't buy you 
anything. So, it ultimately depends on what you're doing. In a 
general purpose library, I'd say that it should have length if 
it can do so in O(1), but if it's just for you, then it may or 
may not be worth it.


The other thing to consider is what happens when the container 
is mutated. I don't think that ranges necessarily behave all 
that well when an underlying container is mutated, but it is 
something that has to be considered when dealing with a range 
over a container. Even if mutating the underlying container 
doesn't necessarily invalidate a range, maintaining the length 
in the manner that you're suggesting probably makes it so that 
it would be invalidated in more cases, since if any elements 
are added or removed in the portion that was already popped off 
the range, then the iteration count couldn't be used to 
calculate the length in the same way anymore. Now, with a hash 
map, the range is probably fully invalidated when anything gets 
added or removed anyway, since that probably screws with the 
order of the elements in the range, but how the range is going 
to behave when the underlying container is mutated and how 
having the length property does or doesn't affect that is 
something that you'll need to consider.


- Jonathan M Davis


I find that discussion very interesting as I had never considered 
that because of design by introspection having a costly length 
method would lead to unexpected calls by generic algorithms 
making it a disadventage if present.


On the other hand I don't think the end user should have to 
scratch his head to find the length of a range, especially if 
it's not trivial to get (say, O(log n) kind of case). Therefore 
exposing a method in any case seems the best from an API 
perspective.


But to avoid the performance issues mentionned earlier it means 
it should bear a different name (get/setLength comes to mind). I 
believe this is the same kind of issue that lead to having "in" 
for associative arrays but not regular ones. However this also 
leads to less coherent APIs in contradiction with the principle 
of least surprise.


In retrospect since only "unexpected" calls to such methods cause 
the issue I wonder if it wouldn't be best to have an UDA saying 
"Hey, please, this method is costly, if you're a generic template 
performing introspection you should probably not call me". And 
writing that Andrei's work on complexity annotations comes to 
mind. Anyway, I don't think the user should use different names 
just to alleviate an issue on the library side but the 
alternative would be costly to put in place...


Any thoughts?


Should "a is b" compile if a and b have unrelated classes?

2018-04-10 Thread Michael Coulombe via Digitalmars-d-learn
I had a bug in my code that was messing me up for a while, and it 
boiled down to an identity check between two Object references 
with unrelated static types, like below:


class A {}
class B {}
void main() {
A a = new A;
B b = new B;
if (a is b) {} // compiles
}

I was surprised that the type system failed me here. It's true 
that A and B could be upcast to Object and then comparisons would 
make sense type-wise, but the comparison should never pass (and 
the compiler should know it won't since they are in separate 
inheritance subtrees) unless the programmer is intentionally 
breaking the type system.


Is there reasoning for this? If not, should it be a warning or 
error, as it is for example when comparing two pointers to 
structs of different types?


Re: Range length property

2018-04-10 Thread Per Nordlöw via Digitalmars-d-learn
On Tuesday, 10 April 2018 at 20:16:18 UTC, Steven Schveighoffer 
wrote:
e.g. std.array.array is going to pre-allocate an array of the 
correct length and fill it in, vs. appending each element as it 
gets them from the range.


Personally, I would store the length because typically a 
container range is short-lived. It also jives with the 
container itself which likely has O(1) length.


Thanks, that's what I thought too.


Re: Range length property

2018-04-10 Thread Steven Schveighoffer via Digitalmars-d-learn

On 4/10/18 4:08 PM, Jonathan M Davis wrote:

On Tuesday, April 10, 2018 19:47:10 Nordlöw via Digitalmars-d-learn wrote:

I'm thinking of my own container Hashmap having its range
ByKeyValue requiring one extra word of memory to store the
iteration count which, in turn, can be used to calculate the
length of the remaining range. Is this motivated?


That would depend entirely on what you're trying to do, but in general, if a
range has length, then some algorithms will be more efficient, and some
algorithms do require length.


e.g. std.array.array is going to pre-allocate an array of the correct 
length and fill it in, vs. appending each element as it gets them from 
the range.


Personally, I would store the length because typically a container range 
is short-lived. It also jives with the container itself which likely has 
O(1) length.


-Steve


Re: Range length property

2018-04-10 Thread Jonathan M Davis via Digitalmars-d-learn
On Tuesday, April 10, 2018 19:47:10 Nordlöw via Digitalmars-d-learn wrote:
> On Tuesday, 10 April 2018 at 14:34:40 UTC, Adam D. Ruppe wrote:
> > On Tuesday, 10 April 2018 at 14:25:52 UTC, Nordlöw wrote:
> >> Should ranges always provide a length property?
> >
> > No.
> >
> >> If so, in which cases is a length property an advantage or a
> >> requirement?
> >
> > Just provide it whenever it is cheap to do so. If you need to
> > do complex calculations or especially loop over contents to
> > figure out the length, do NOT provide it.
> >
> > But if it is as simple as returning some value, provide it and
> > algorithms can take advantage of it for optimizations etc. as
> > needed.
>
> I'm thinking of my own container Hashmap having its range
> ByKeyValue requiring one extra word of memory to store the
> iteration count which, in turn, can be used to calculate the
> length of the remaining range. Is this motivated?

That would depend entirely on what you're trying to do, but in general, if a
range has length, then some algorithms will be more efficient, and some
algorithms do require length. So, if you can provide length, then the range
will be more useful, just like a bidirectional range can be more useful than
a forward range or a random-access range can be more useful than either.
However, if you're not doing anything that ever benefits from it having
length, then it doesn't buy you anything. So, it ultimately depends on what
you're doing. In a general purpose library, I'd say that it should have
length if it can do so in O(1), but if it's just for you, then it may or may
not be worth it.

The other thing to consider is what happens when the container is mutated. I
don't think that ranges necessarily behave all that well when an underlying
container is mutated, but it is something that has to be considered when
dealing with a range over a container. Even if mutating the underlying
container doesn't necessarily invalidate a range, maintaining the length in
the manner that you're suggesting probably makes it so that it would be
invalidated in more cases, since if any elements are added or removed in the
portion that was already popped off the range, then the iteration count
couldn't be used to calculate the length in the same way anymore. Now, with
a hash map, the range is probably fully invalidated when anything gets added
or removed anyway, since that probably screws with the order of the elements
in the range, but how the range is going to behave when the underlying
container is mutated and how having the length property does or doesn't
affect that is something that you'll need to consider.

- Jonathan M Davis




Re: Range length property

2018-04-10 Thread Nordlöw via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 14:34:40 UTC, Adam D. Ruppe wrote:

On Tuesday, 10 April 2018 at 14:25:52 UTC, Nordlöw wrote:

Should ranges always provide a length property?


No.

If so, in which cases is a length property an advantage or a 
requirement?


Just provide it whenever it is cheap to do so. If you need to 
do complex calculations or especially loop over contents to 
figure out the length, do NOT provide it.


But if it is as simple as returning some value, provide it and 
algorithms can take advantage of it for optimizations etc. as 
needed.


I'm thinking of my own container Hashmap having its range 
ByKeyValue requiring one extra word of memory to store the 
iteration count which, in turn, can be used to calculate the 
length of the remaining range. Is this motivated?


Re: Destructor call

2018-04-10 Thread Steven Schveighoffer via Digitalmars-d-learn

On 4/10/18 3:24 PM, Jonathan M Davis wrote:

On Tuesday, April 10, 2018 18:52:19 kinke via Digitalmars-d-learn wrote:

On Tuesday, 10 April 2018 at 18:34:54 UTC, n0fun wrote:

Why the destructor is called in the second case and why not in
the first?


The first case is RAII, where destruction isn't done for not
fully constructed instances.


Yeah, which is arguably a bug:

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


The second case is GC finalization at program shutdown and looks
like a bug, as the GC should probably immediately reclaim the
allocated heap memory if construction wasn't successful.


Maybe it should reclaim the memory immediately, but I don't see how it could
be argued to be a bug. When memory is freed by the GC is an implementation
detail, and it's never guaranteed that a finalizer will actually ever run.


Actually, it is a bug, because the destructor is going to run the 
finalizer on a collection cycle, and the object may be partially created.


This is due to the way it's created using new:

1. a memory block is allocated
2. The typeinfo is stored in the block
3. The runtime returns the pointer to the block.
4. the compiler calls the constructor on the block.

Because the typeinfo is unconditionally stored, the finalizer will run, 
even if it shouldn't.


The issue is that the compiler is much better at calling the constructor 
of the struct. This means we need 2 hooks for the construction -- 1. the 
memory allocation, and 2. a "post construction" call. I'd hate to pass 
the constructor parameters to a template function rather than the 
compiler handle all of these messy details.


-Steve


Re: Destructor call

2018-04-10 Thread Jonathan M Davis via Digitalmars-d-learn
On Tuesday, April 10, 2018 18:52:19 kinke via Digitalmars-d-learn wrote:
> On Tuesday, 10 April 2018 at 18:34:54 UTC, n0fun wrote:
> > Why the destructor is called in the second case and why not in
> > the first?
>
> The first case is RAII, where destruction isn't done for not
> fully constructed instances.

Yeah, which is arguably a bug:

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

> The second case is GC finalization at program shutdown and looks
> like a bug, as the GC should probably immediately reclaim the
> allocated heap memory if construction wasn't successful.

Maybe it should reclaim the memory immediately, but I don't see how it could
be argued to be a bug. When memory is freed by the GC is an implementation
detail, and it's never guaranteed that a finalizer will actually ever run.

- Jonathan M Davis



Re: Destructor call

2018-04-10 Thread kinke via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 18:34:54 UTC, n0fun wrote:
Why the destructor is called in the second case and why not in 
the first?


The first case is RAII, where destruction isn't done for not 
fully constructed instances.
The second case is GC finalization at program shutdown and looks 
like a bug, as the GC should probably immediately reclaim the 
allocated heap memory if construction wasn't successful.


Destructor call

2018-04-10 Thread n0fun via Digitalmars-d-learn

import std.stdio;

struct S(alias n) {
this(int) {
throw new Exception("Exception");
}
~this() {
writeln("destructor " ~ n);
}
}

void main() {
writeln("--- 1 ---");
try {
auto s = S!"1"(0);
} catch (Exception) {}
writeln("--- 2 ---");
try {
auto s = new S!"2"(0);
} catch (Exception) {}
}

Output:
--- 1 ---
--- 2 ---
destructor 2

Why the destructor is called in the second case and why not in 
the first?

How to design structs with such different behavior?



Re: Is std.variant.visit not @nogc?

2018-04-10 Thread Steven Schveighoffer via Digitalmars-d-learn

On 4/10/18 12:59 PM, Paul Backus wrote:

On Tuesday, 10 April 2018 at 12:34:07 UTC, aliak wrote:

Awesome!

this is a neat trick:

union
{
  AliasSeq!(T0, T1) values;
}

Is that usage documented somewhere, or is it somewhere in phobos maybe?

Also, can Algebraic be fully replaced with this version then or is 
there some functionality that would stop it going through?


It's called "type sequence instantiation", and it's documented in the 
"Compile-time Sequences" article [1] on dlang.org. I discovered it 
reading the source of the 'tagged_union' dub package [2]. It's not 
mentioned anywhere in the language spec, as far as I can tell.


Ooh! that's really cool.

I've put AliasSeq of types into a struct, but never considered putting 
it into a union. This has a lot of potential when you want to 
auto-generate unions.


Nice trick!

-Steve


Re: Range length property

2018-04-10 Thread Jonathan M Davis via Digitalmars-d-learn
On Tuesday, April 10, 2018 14:25:52 Nordlöw via Digitalmars-d-learn wrote:
> Should ranges always provide a length property?
>
> If so, in which cases is a length property an advantage or a
> requirement?

Whether a range has a length property or not is primarily dependent on how
efficient it is to implement length.
https://dlang.org/phobos/std_container.html lists the Big-O complexity of
the various functions and properties that are expected for containers, and
in the case of length, that also applies to ranges. It lists O(log n) as the
Big-O complexity of length, so length should only be implemented if its
Big-O complexity is no worse than O(log n). In most cases, that means
implementing it only if it's O(1) (I think that it's O(log n) rather than
O(1) because of binary trees), and length should certainly never be
implemented if it's O(n). Basically, if you can just return the length
without calculating it, then it makes sense to implement it, but if you have
to calculate it, then in most cases, it shouldn't be there. Range-based
functions are going to expect length to be very cheap to call if it is
present, and any function that needs to ascertain the length of a range even
if it doesn't have length will call walkLength (which returns length if
present and iterates the entire range to count it if it's not). As iterating
the entire range to count it, is O(n), most algorithms won't do that are
more likely to require length if they need to know how many elements there
are in the range, but that depends on what they're doing.

A function that requires a length property or which has a path optimized for
ranges that have a length property checks for that with
std.range.primitives.hasLength. Random access ranges are required to either
be infinite or provide length, but for other range types, it's optional and
must be checked for if an algorithm is going to use it.

And actually, a large percentage of ranges are lazy, in which case, it's
pretty rare that they can have a length property, because you usually have
no way of knowing how long they're going to be without actually iterating
through the range. So, while it's not uncommon for a range to define length,
it's very common that they don't.

- Jonathan M Davis




Re: Is std.variant.visit not @nogc?

2018-04-10 Thread Paul Backus via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 12:34:07 UTC, aliak wrote:

Awesome!

this is a neat trick:

union
{
  AliasSeq!(T0, T1) values;
}

Is that usage documented somewhere, or is it somewhere in 
phobos maybe?


Also, can Algebraic be fully replaced with this version then or 
is there some functionality that would stop it going through?


It's called "type sequence instantiation", and it's documented in 
the "Compile-time Sequences" article [1] on dlang.org. I 
discovered it reading the source of the 'tagged_union' dub 
package [2]. It's not mentioned anywhere in the language spec, as 
far as I can tell.


SumType should be capable of doing anything that Algebraic can do 
(if it's not, please open an issue on Github!), but it's not a 
drop-in replacement, and it's still a work in progress. 
Documentation for the current version (more or less) is available 
at http://sumtype.dpldocs.info/index.html. If there are any 
particular features you'd like to see, let me know, and I'll do 
my best to add them.


[1] 
https://dlang.org/articles/ctarguments.html#type-seq-instantiation
[2] 
https://github.com/Superstar64/tagged_union/blob/master/source/tagged_union.d


Re: stirling numbers and multidimensional arrays

2018-04-10 Thread popgen via Digitalmars-d-learn

On Sunday, 8 April 2018 at 16:51:14 UTC, ag0aep6g wrote:

On 04/08/2018 06:15 PM, popgen wrote:

[...]

[...]

 [...]

[...]

 [...]


Should it be `q <= k` here? You're using q as an index into an 
array of length k + 1. If you go up to i, you'll exceed that 
and go out of bounds.


That you're seeing a segfault instead of a range error 
indicates that you're compiling with -release. Better not do 
that when debugging.


Thank you for your help! And I learned two things, the error in 
the code and not to use -release while debugging.


trouble building dlang.org

2018-04-10 Thread Zach Tollen via Digitalmars-d-learn
I'm trying to update the language spec. I have the standard dmd 
installed on my Mac in `~/dlang/dmd` using the install script 
from the website "curl -fsS https://dlang.org/install.sh | bash 
-s dmd". Okay, good, done.


Now, according to: dlang.org/CONTRIBUTING.md:
"git clone https://github.com/dlang/dlang.org
cd dlang.org"

Okay, done. Now:
"make -f posix.mak html"

This first errored out with "No package file found in 
/Users/zach/dlang/dmd/, expected one of 
dub.json/dub.sdl/package.json

make: *** [.generated/ddoc_preprocessor] Error 2"

I didn't know why the dub.sdl wasn't already installed, so I 
manually copied it from github. But now the error for "make -f 
posix.mak html" is:


".generated/stable_dmd-2.078.2/dmd2/osx/bin/dub build 
--compiler=.generated/stable_dmd-2.078.2/dmd2/osx/bin/dmd 
--root=ddoc && \

mv ddoc/ddoc_preprocessor .generated/ddoc_preprocessor
Invalid source/import path: /Users/zach/dlang/dmd/src/dmd
Invalid source/import path: /Users/zach/dlang/dmd/generated/dub"

So I'm here wondering wuzzup? The basic instructions in 
CONTRIBUTING.md aren't working. Anyone?







Re: SMTP Mail

2018-04-10 Thread Adam D. Ruppe via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 15:10:44 UTC, Vino wrote:
The variable "to" is of type string[] but we need it as 
Array!string

The variable "Subject" but we need it as Array!string.


You'll have to convert them yourself if that is a must, but why 
would you need that?


Re: SMTP Mail

2018-04-10 Thread Vino via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 13:51:02 UTC, Adam D. Ruppe wrote:

On Tuesday, 10 April 2018 at 11:09:56 UTC, Vino wrote:
 Now the program works, but the attachment does not work as 
expected,


message.addAttachment("text/plain", 
"C:\\Temp\\Test\Test1.txt", "Test");


What did you expect that "Test" argument to do if it was going 
to read the file as the content? I guess I should change the 
documents on this. The way it works is the filename argument is 
just what is seen in the email as a suggestion name for the 
user to download the attachment, and the content argument is 
what is what's inside that attachment.


Since the attachment name just suggests a name, and the user 
decides where to put it, it should NOT have a path name.


So try this instead:


addAttachment("text/plain", "Test1.txt", 
std.file.read("C:\Temp\Test\Test1.txt"));



so the name argument is JUST the name to suggest to the user, 
then the content argument gives the content of your file to 
attach - which here is read from the file on disk via the 
phobos std.file read function.


Hi Adam,

  Thank you very much, the program now works, but i need to make 
some adjustment, if possible can you please help me on this.


The variable "to" is of type string[] but we need it as 
Array!string

The variable "Subject" but we need it as Array!string.

From,
Vino.B




Re: Range length property

2018-04-10 Thread Adam D. Ruppe via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 14:25:52 UTC, Nordlöw wrote:

Should ranges always provide a length property?


No.

If so, in which cases is a length property an advantage or a 
requirement?


Just provide it whenever it is cheap to do so. If you need to do 
complex calculations or especially loop over contents to figure 
out the length, do NOT provide it.


But if it is as simple as returning some value, provide it and 
algorithms can take advantage of it for optimizations etc. as 
needed.


Range length property

2018-04-10 Thread Nordlöw via Digitalmars-d-learn

Should ranges always provide a length property?

If so, in which cases is a length property an advantage or a 
requirement?


Re: How to destruct class instances allocated by a Region-allocator over a single GC block

2018-04-10 Thread rikki cattermole via Digitalmars-d-learn

On 11/04/2018 1:56 AM, Eduard Staniloiu wrote:

On Monday, 9 April 2018 at 14:51:24 UTC, Per Nordlöw wrote:

On Monday, 9 April 2018 at 13:51:47 UTC, Steven Schveighoffer wrote:
Well, you know the type, because make returned it no? The contract 
is, you call obj = make!X(args), then you have to call dispose(obj), 
where obj is of the type X. That's how it knows.


If you are thinking you want to destroy the whole block at once 
(typed as void[]), that's not how it works.


stdx.allocator is not going to help you with GC collection, it's not 
geared towards that purpose.


Ok, thanks!


If you are using a custom allocator to allocate memory then you also
have to manually dispose of the memory when it is no longer needed.

You can't have a custom allocator to supply you with the memory and
then have the GC track and dispose of it. I get the feeling that this
is what you were looking for?


As long as you can use libc's free, sure you can :)


Re: How to destruct class instances allocated by a Region-allocator over a single GC block

2018-04-10 Thread Eduard Staniloiu via Digitalmars-d-learn

On Monday, 9 April 2018 at 14:51:24 UTC, Per Nordlöw wrote:
On Monday, 9 April 2018 at 13:51:47 UTC, Steven Schveighoffer 
wrote:
Well, you know the type, because make returned it no? The 
contract is, you call obj = make!X(args), then you have to 
call dispose(obj), where obj is of the type X. That's how it 
knows.


If you are thinking you want to destroy the whole block at 
once (typed as void[]), that's not how it works.


stdx.allocator is not going to help you with GC collection, 
it's not geared towards that purpose.


Ok, thanks!


If you are using a custom allocator to allocate memory then you 
also
have to manually dispose of the memory when it is no longer 
needed.


You can't have a custom allocator to supply you with the memory 
and
then have the GC track and dispose of it. I get the feeling that 
this

is what you were looking for?


Re: SMTP Mail

2018-04-10 Thread Adam D. Ruppe via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 11:09:56 UTC, Vino wrote:
 Now the program works, but the attachment does not work as 
expected,


message.addAttachment("text/plain", "C:\\Temp\\Test\Test1.txt", 
"Test");


What did you expect that "Test" argument to do if it was going to 
read the file as the content? I guess I should change the 
documents on this. The way it works is the filename argument is 
just what is seen in the email as a suggestion name for the user 
to download the attachment, and the content argument is what is 
what's inside that attachment.


Since the attachment name just suggests a name, and the user 
decides where to put it, it should NOT have a path name.


So try this instead:


addAttachment("text/plain", "Test1.txt", 
std.file.read("C:\Temp\Test\Test1.txt"));



so the name argument is JUST the name to suggest to the user, 
then the content argument gives the content of your file to 
attach - which here is read from the file on disk via the phobos 
std.file read function.


Re: Is std.variant.visit not @nogc?

2018-04-10 Thread aliak via Digitalmars-d-learn

On Tuesday, 10 April 2018 at 03:48:25 UTC, Paul Backus wrote:
Nope! It's just a tagged union, almost exactly the same as what 
you'd write by hand in C. You can take a look at the source 
yourself, if you're curious---it's actually pretty simple:


https://github.com/pbackus/sumtype/blob/master/src/sumtype.d#L27


Awesome!

this is a neat trick:

union
{
  AliasSeq!(T0, T1) values;
}

Is that usage documented somewhere, or is it somewhere in phobos 
maybe?


Also, can Algebraic be fully replaced with this version then or 
is there some functionality that would stop it going through?


Re: SMTP Mail

2018-04-10 Thread Vino via Digitalmars-d-learn

On Monday, 9 April 2018 at 19:19:53 UTC, Adam D. Ruppe wrote:

On Monday, 9 April 2018 at 15:38:55 UTC, Vino.B wrote:
Thank you very much, I copied your folder arsd under the 
phobes folder in c:\D\... and the program was placed on my 
desktop and tried to execute it from the desktop via rdmd.



I don't think rdmd is seeing the dependency on htmltotext.d. 
Try importing it explicitly from your main:


import arsd.email;
import arsd.htmltotext;

/* the rest of your code */


Just that way rdmd will find it easier.


Hi Adam,

 Now the program works, but the attachment does not work as 
expected,


message.addAttachment("text/plain", "C:\\Temp\\Test\Test1.txt", 
"Test");



It takes the full path as file name eg: If the attachment file 
resides on the path C:\Temp\Test\Test1.txt" the attachment name 
file name that we receive is as "CTempTestTest1.txt" and also it 
does not attached the real file, instead the content of the file 
is "Test"


We Tried the below

message.addAttachment("text/plain", "Test1.txt", 
"C:\\Temp\\Test\Test1.txt");


After the above change the attachment file name is "Test1.txt" 
with the content "C:\Temp\Test\Test1.txt"


The orignal content of the file is "Hi This is Test Attachment".

From,
Vino.B