Re: Read a unicode character from the terminal

2012-04-05 Thread Jacob Carlborg

On 2012-04-05 01:21, Stewart Gordon wrote:

On 04/04/2012 17:37, Jacob Carlborg wrote:
snip

Sure I can help you with testing. I have a lot on my own table so I
don't have any time
for implementing things (maybe some small things). If I may ask, what
is the point of this
library?


Just to hold some miscellaneous utility classes/structs/functions.


Doesn't it duplicate functionally that's already available in Phobos
and/or Tango?

snip

It certainly does in places. But what matters is that it contains
functionality that isn't present in Phobos (or wasn't present in Phobos
at the time I wrote it).

Stewart.


Ok, I see. The functions that need a Posix implementation are mostly in 
datetime and commandline, if I recall correctly. These are already 
present in Phobos?


--
/Jacob Carlborg


Remove dir contents?

2012-04-05 Thread Andrej Mitrovic
There's rmdirRecurse in std.file, but it removes the folder itself as
well as its contents. I'm looking for a function that removes only the
contents of the dir. Is this in Phobos, and if not can we add it?

Otherwise I have to use platform-specific calls to system() like del *.*.


Re: Remove dir contents?

2012-04-05 Thread Andrej Mitrovic
On 4/5/12, Andrej Mitrovic andrej.mitrov...@gmail.com wrote:
 Otherwise I have to use platform-specific calls to system() like del *.*.

Actually nevermind that, I can just remove the dir entirely and then
re-create it.


Re: SUL for Posix

2012-04-05 Thread Jacob Carlborg

On 2012-04-05 12:55, Stewart Gordon wrote:

On 05/04/2012 07:18, Jacob Carlborg wrote:
snip

Ok, I see. The functions that need a Posix implementation are mostly
in datetime and
commandline, if I recall correctly. These are already present in Phobos?


Maybe it contains the code I need to finish datetime off. Though I can't
really just copy someone else's code, I suppose I can at least see what
functions it uses.

I haven't noticed much along the lines of command line manipulation in
Phobos - only the code (now in druntime) to populate the args argument
to main (which under Posix it just uses argc/argv from the C main). Or
is there something I haven't found?

Stewart.


http://dlang.org/phobos/std_getopt.html

But it might not do what you want.

--
/Jacob Carlborg


Re: Questions about the slice operator

2012-04-05 Thread Christophe
Jonathan M Davis , dans le message (digitalmars.D.learn:34243), a
 Except that opSlice already works with ... What would this buy you?

Having a specific range for a .. operator allows you to have them as 
parameters of any function.

For example, this could be nice for multidimensional slicing:
Matrix!(double, 6, 6) A;
auto partOfA = A[1..3, 4..6];

Operations on several items of a container:
Container B;
B.remove(4..9); // remove 5 contiguous elements.

etc.



Re: Up to date documentation on D implementation.

2012-04-05 Thread bearophile

ReneSac:

My hand will be full with my own bugs, and I would like to 
suppose an correctly working language...


If you use more than the basic C features, you will find DMD
compiler bugs (and probably the same is true for any D compiler,
because most bugs are in the front-end, that is shared). Lately I
hit new bugs less often, but they happen still.

Bye,
bearophile


Re: Questions about the slice operator

2012-04-05 Thread Timon Gehr

On 04/04/2012 12:06 PM, Jacob Carlborg wrote:

On 2012-04-04 04:11, Jonathan M Davis wrote:


foreach(i; 0 .. 5)

is more efficient only because it has _nothing_ to do with arrays.
Generalizing
the syntax wouldn't help at all, and if it were generalized, it would
arguably
have to be consistent in all of its uses, in which case

foreach(i; 0 .. 5)

would become identical to

foreach(i; [0, 1, 2, 3, 4])

and therefore less efficient. Generalizing .. just doesn't make sense.


Why couldn't the .. syntax be syntax sugar for some kind of library
implement range type, just as what is done with associative arrays.

...

I think this would be completely backwards compatible as well.



It would be awkward to introduce it in a backwards compatible way, 
because currently '..' binds weaker than any operator.


auto x = 0..10; // ok
auto y = 0..10, z = 2; // error, z not defined
x = 0..11; // error: expression '11' has no effect


Re: Up to date documentation on D implementation.

2012-04-05 Thread David

Am 05.04.2012 17:56, schrieb bearophile:

ReneSac:


My hand will be full with my own bugs, and I would like to suppose an
correctly working language...


If you use more than the basic C features, you will find DMD
compiler bugs (and probably the same is true for any D compiler,
because most bugs are in the front-end, that is shared). Lately I
hit new bugs less often, but they happen still.

Bye,
bearophile


Well, that's true, sometimes you hit a compiler or phobos-bug, but it's 
not like:


uhm, today I wanna code something, let's begin … 5 minutes later … uh 
tha fuq another compiler bug 


It has gotten pretty rare that you hit them and when you do, you 
normally realize it very soon that this is a bug from the compiler (e.g. 
cod2.c shows up in the error message).
And if you hit one, ppl in the IRC or here will help you out, with a 
bugfix or a workaround!


Re: D slower ~1s from C ?!

2012-04-05 Thread q66

On Thursday, 5 April 2012 at 17:22:38 UTC, Minas wrote:
Many of you should know the website projecteuler.net, where 
there are mathematical problems to solve with computers.


I am doing those in D, and after I finished one today, I 
decided to compile it in C as well to compare the results.


The problem was:

The number 3797 has an interesting property. Being prime 
itself, it is possible to continuously remove digits from left 
to right, and remain prime at each stage: 3797, 797, 97, and 7. 
Similarly we can work from right to left: 3797, 379, 37, and 3.


Find the sum of the only eleven primes that are both 
truncatable from left to right and right to left.


NOTE: 2, 3, 5, and 7 are not considered to be truncatable 
primes.


My solution in D:

[source]
import std.stdio;
import std.math;
import std.conv;

void main()
{
int count, i = 10, sum;

while( count  11 )
{
		if( isPrime(i)  isPrimeRightToLeft(i)  
isPrimeLeftToRight(i) )

{
//writeln(i);
++count;
sum += i;
}

++i;
}

writeln(sum);
}

/// returns true if n is a prime number
bool isPrime(ulong n)
{
n = abs(n);

// 0 and 1 aren't primes
if( n  2 ) return false;

if( n % 2 == 0  n != 2)
return false; // an even number can't be a prime (except 2)

// check only if it's odd
for(ulong i = 2; i = cast (ulong)sqrt(cast(double)n+1); ++i)
if( n % i == 0 )
return false;

return true;
}

/**
 * returns true if n is a prime* truncatable from right to left.
 * Note: n must have been tested to be prime with a separate 
function

 */
bool isPrimeRightToLeft(ulong n)
{
if( n  10 )
return false;

	n /= 10; // assuming that n has already been tested to be 
prime, we can skip checking it


while( n  0 )
{
if( !isPrime(n) )
return false;

n /= 10;
}

return true;
}

/**
 * returns true if n is a prime* truncatable from left to right.
 * Note: n must have been tested to be prime with a separate 
function

 */
bool isPrimeLeftToRight(ulong n)
{
if( n  10 )
return false;

ulong power = cast(ulong)pow(10, cast(ulong)log10(n));
ulong firstDigit = n / power;
n -= firstDigit * power;

while( n  0 )
{
if( !isPrime(n) )
return false;

power = cast(ulong)pow(10, cast(ulong)log10(n));
firstDigit = n / power;

n -= firstDigit * power;
}

return true;
}
[/source]


In C:
[source]
#include stdio.h
#include stdlib.h
#include math.h

typedef unsigned long ulong;

int isPrime(ulong n);
int isPrimeRightToLeft(ulong n);
int isPrimeLeftToRight(ulong n);

int main()
{
int count = 0, i = 10, sum = 0;

while( count  11 )
{
		if( isPrime(i)  isPrimeRightToLeft(i)  
isPrimeLeftToRight(i) )

{
//writeln(i);
++count;
sum += i;
}

++i;
}

printf(%d\n, sum);

return 0;
}

/// returns true if n is a prime number
int isPrime(ulong n)
{
n = abs(n);

// 0 and 1 aren't primes
if( n  2 ) return 0;

if( n % 2 == 0  n != 2)
return 0; // an even number can't be a prime (except 2)

// check only if it's odd
for(ulong i = 2; i = (ulong)sqrt((double)n+1); ++i)
if( n % i == 0 )
return 0;

return 1;
}

/**
 * returns 1 if n is a prime* truncatable from right to left.
 * Note: n must have been tested to be prime with a separate 
function

 */
int isPrimeRightToLeft(ulong n)
{
if( n  10 )
return 0;

	n /= 10; // assuming that n has already been tested to be 
prime, we can skip checking it


while( n  0 )
{
if( !isPrime(n) )
return 0;

n /= 10;
}

return 1;
}

/**
 * returns 1 if n is a prime* truncatable from left to right.
 * Note: n must have been tested to be prime with a separate 
function

 */
int isPrimeLeftToRight(ulong n)
{
if( n  10 )
return 0;

ulong power = (ulong)pow(10, (ulong)log10(n));
ulong firstDigit = n / power;
n -= firstDigit * power;

while( n  0 )
{
if( !isPrime(n) )
return 0;

power = 

Re: Remove dir contents?

2012-04-05 Thread Jonathan M Davis
On Thursday, April 05, 2012 12:55:23 Andrej Mitrovic wrote:
 On 4/5/12, Andrej Mitrovic andrej.mitrov...@gmail.com wrote:
  Otherwise I have to use platform-specific calls to system() like del
  *.*.
 
 Actually nevermind that, I can just remove the dir entirely and then
 re-create it.

I don't believe that there's any system call or command-line program on any of 
the platforms that D supports which specifically deletes the _contents_ of a 
directory - as your del *.* demonstrates for Windows, so I wouldn't expect 
such a thing in Phobos - especially when what's there makes it quite possible 
to do what you want, even if it's not one command.

The normal way to do it would probably be to iterate over the contents and 
delete everything one by one. Your proposed solution or removing the dir and 
then creating it again is arguably cleaner, but it does have the downside of 
the new directory possibly not matching the original one with regards to 
permissions or ownership (it may even be that you don't have permission to 
remove it or create it even if you have permission to edit to its contents, 
since you could have write permission for the directory but not for its parent 
directory). I don't think that that's really an issue in Windows (which you're 
presumably using given your suggestion of del *.*), since it's pretty limited 
when it comes to permissions, but it definitely would be on Posix systems.

- Jonathan M Davis


Re: Questions about the slice operator

2012-04-05 Thread Jonathan M Davis
On Thursday, April 05, 2012 14:58:41 Christophe wrote:
 Jonathan M Davis , dans le message (digitalmars.D.learn:34243), a
 
  Except that opSlice already works with ... What would this buy you?

As I said, all it does is give you syntactic sugar for iota which can't even 
do as much as iota can (since it lacks a step parameter).

But my point that you're quoting has nothing to do with using .. with 
functions in general. It specifically has to do with creating a new overload 
for opSlice as Jacob suggestios - i.e. when you do a[0 .. 5] where a is an 
instance of a user-defined type. That works just fine with auto opSlice (size_t 
start, size_t end). The range type buys you nothing for that, and in fact 
would be _more_ expensive, since it would have to allocate a struct rather 
than simply passing the two indices.

- Jonathan M Davis


Re: D slower ~1s from C ?!

2012-04-05 Thread Andrej Mitrovic
On 4/5/12, Minas minas_mina1...@hotmail.co.uk wrote:
 And this is the time execution of the programs

C via GCC (gcc -m32 test.c -o testgcc.exe -std=c99 -lm -O5)
Elapsed Time: 0:00:02.015

D via DMD (dmd test.d -oftestdmd.exe -release -inline -O -noboundscheck)
Elapsed Time: 0:00:08.312

D via GDC (gdmd -m32 -release -inline -O -noboundscheck test.d -oftestgdc.exe)
Elapsed Time: 0:00:01.015

These results are fairly consistent on my machine.


Re: Remove dir contents?

2012-04-05 Thread Andrej Mitrovic
On 4/5/12, Jonathan M Davis jmdavisp...@gmx.com wrote:
 But it does have the downside of
 the new directory possibly not matching the original one with regards to
 permissions or ownership

That's a very good point. Since I run all of my code locally I never
run into these issues and so I've never given thought about
permissions.


Re: Up to date documentation on D implementation.

2012-04-05 Thread Jesse Phillips

On Thursday, 5 April 2012 at 15:01:53 UTC, ReneSac wrote:

Hi.

I'm totally new to D, and would like to use it to prototype 
some compression software ideas.


You'll be pretty safe using features you know for C, but you can 
venture out pretty far from it.


While, the page isn't specific to the questions you have at hand, 
this does cover much of the current state. Remember, recently 
implemented features are more likely to have bugs.


http://www.prowiki.org/wiki4d/wiki.cgi?LanguageDevel


Re: Questions about the slice operator

2012-04-05 Thread bearophile
Christophe:

 Having a specific range for a .. operator allows you to have them as 
 parameters of any function.

Such functions are also able to accept a Iota struct and then read its fields 
to find its bounds.


For Jonathan M Davis: the first class intervals seem nice to have, but they 
aren't near the top of the list of my enhancement requests :-) 

Bye,
bearophile


Re: Up to date documentation on D implementation.

2012-04-05 Thread ReneSac

On Thursday, 5 April 2012 at 18:34:05 UTC, Jesse Phillips wrote:


You'll be pretty safe using features you know for C, but you 
can venture out pretty far from it.


While, the page isn't specific to the questions you have at 
hand, this does cover much of the current state. Remember, 
recently implemented features are more likely to have bugs.


I will probably program close to C/Lua style (the languages I'm 
most proficient with), but pretty far is vague. And I haven't 
been following the time line of the feature additions, like old 
users do, and I'm not sure if I should read the entire changelog 
for some vague indication of the stability of a feature...



http://www.prowiki.org/wiki4d/wiki.cgi?LanguageDevel


Ok, that page gives some pointers. Seems like I shouldn't use 
std.stream. So, std.cstream or std.stdio are safe?


Dynamic Arrays, Slicing, Unittest, conditional compilation and 
compile time function execution should be working well, right? 
What about std.paralelism and message passing, non-shared 
multithreading?


And I still don't know how to generate windows executables.. If 
it is really impossible to compile D in Windows 64 bits, then 
what is the best compiler for Linux?


Re: Up to date documentation on D implementation.

2012-04-05 Thread David

Am 05.04.2012 23:10, schrieb ReneSac:

Ok, that page gives some pointers. Seems like I shouldn't use
std.stream. So, std.cstream or std.stdio are safe?


I also heared that, but actually std.stream works pretty well, 
especially the EndianStream. So I can recommend you to use it.


Re: Up to date documentation on D implementation.

2012-04-05 Thread Jesse Phillips

On Thursday, 5 April 2012 at 21:10:41 UTC, ReneSac wrote:

I will probably program close to C/Lua style (the languages I'm 
most proficient with), but pretty far is vague. And I haven't 
been following the time line of the feature additions, like old 
users do, and I'm not sure if I should read the entire 
changelog for some vague indication of the stability of a 
feature...


The page I liked does have compiler versions for some of the 
implemented features, as you appear to have noticed.



http://www.prowiki.org/wiki4d/wiki.cgi?LanguageDevel


Ok, that page gives some pointers. Seems like I shouldn't use 
std.stream. So, std.cstream or std.stdio are safe?


Hmm, bring up a good point, I think someone is working on 
revamping stdio, though I would think it would mostly remain 
compatible. Who's doing that? Could you write the details here:


http://www.prowiki.org/wiki4d/wiki.cgi?ReviewQueue

Dynamic Arrays, Slicing, Unittest, conditional compilation and 
compile time function execution should be working well, right?


Yep, there are some requested improvements but, things are stable.

What about std.paralelism and message passing, non-shared 
multithreading?


I'm not sure how much use they have been getting, so it is hard 
to say. I know there have been questions about how to use them, 
but they seem solid.


If you get into using shared though, you'll probably walk into 
areas that will require casting to get things done. I don't know 
what if any changes are planned, but likely it needs a closer 
look.


And I still don't know how to generate windows executables.. If 
it is really impossible to compile D in Windows 64 bits, then 
what is the best compiler for Linux?


Sorry, forgot to cover that. I believe GDC will compile 64bit 
Windows applications, but otherwise you can still compile and run 
32bit applications.


Most people use DMD, but GDC, I hear, should be on par.


Re: Up to date documentation on D implementation.

2012-04-05 Thread ReneSac

On Thursday, 5 April 2012 at 22:07:05 UTC, Jesse Phillips wrote:

On Thursday, 5 April 2012 at 21:10:41 UTC, ReneSac wrote:

I will probably program close to C/Lua style (the languages 
I'm most proficient with), but pretty far is vague. And I 
haven't been following the time line of the feature additions, 
like old users do, and I'm not sure if I should read the 
entire changelog for some vague indication of the stability of 
a feature...


The page I liked does have compiler versions for some of the 
implemented features, as you appear to have noticed.


Ah, I saw The following list of major issues dates from July 
2009. So I supposed it was old, but now I see that I understood 
wrong.



http://www.prowiki.org/wiki4d/wiki.cgi?LanguageDevel


Ok, that page gives some pointers. Seems like I shouldn't use 
std.stream. So, std.cstream or std.stdio are safe?


Hmm, bring up a good point, I think someone is working on 
revamping stdio, though I would think it would mostly remain 
compatible. Who's doing that? Could you write the details here:



So, what I should use?


http://www.prowiki.org/wiki4d/wiki.cgi?ReviewQueue

Dynamic Arrays, Slicing, Unittest, conditional compilation and 
compile time function execution should be working well, right?


Yep, there are some requested improvements but, things are 
stable.

Good! Thanks.



What about std.paralelism and message passing, non-shared 
multithreading?


I'm not sure how much use they have been getting, so it is hard 
to say. I know there have been questions about how to use them, 
but they seem solid.


If you get into using shared though, you'll probably walk into 
areas that will require casting to get things done. I don't 
know what if any changes are planned, but likely it needs a 
closer look.


I would try to avoid anything shared anyway. It is hard to 
program if a++ isn't deterministic...




Sorry, forgot to cover that. I believe GDC will compile 64bit 
Windows applications, but otherwise you can still compile and 
run 32bit applications.


Most people use DMD, but GDC, I hear, should be on par.


I don't need a 64bit binary right now. Actually, I would even 
prefer a 32bit one for development because then I can't run too 
wild in memory usage. The problem is that DMD seems to require 32 
bit windows, according to the page I linked... Is it not true?


Anyway, GDC seems to have quite better performance/optimization, 
so I may end up using it... But I also heard bad things about it 
in old posts... so...


Re: Up to date documentation on D implementation.

2012-04-05 Thread H. S. Teoh
On Fri, Apr 06, 2012 at 12:42:57AM +0200, ReneSac wrote:
 On Thursday, 5 April 2012 at 22:07:05 UTC, Jesse Phillips wrote:
[...]
 Anyway, GDC seems to have quite better performance/optimization, so
 I may end up using it... But I also heard bad things about it in old
 posts... so...

I use GDC for some of my D projects. I didn't find anything wrong with
it. Plus, GCC's backend optimizer is a LOT better than dmd. Something to
consider if you're writing performance-critical code.


T

-- 
Right now I'm having amnesia and deja vu at the same time. I think I've
forgotten this before.


Re: Up to date documentation on D implementation.

2012-04-05 Thread Jonathan M Davis
On Friday, April 06, 2012 00:07:03 Jesse Phillips wrote:
 Hmm, bring up a good point, I think someone is working on
 revamping stdio, though I would think it would mostly remain
 compatible. Who's doing that? Could you write the details here:

It's Steven Schveighoffer, but it's far from ready, since he hasn't had a lot 
of time to work on it of late. He put up an initial version for feedback a few 
weeks back, and one of the main points of feedback (which Walter felt very 
strongly about) was that it needed to be compatible with the current std.stdio 
rather than having a whole new API, so while it may do new stuff and have a 
better implementation, most (all?) of the stuff using the current std.stdio 
will continue to work with the new one whenever it's finished.

- Jonathan M Davis


Re: Up to date documentation on D implementation.

2012-04-05 Thread Jonathan M Davis
On Thursday, April 05, 2012 23:47:52 David wrote:
 Am 05.04.2012 23:10, schrieb ReneSac:
  Ok, that page gives some pointers. Seems like I shouldn't use
  std.stream. So, std.cstream or std.stdio are safe?
 
 I also heared that, but actually std.stream works pretty well,
 especially the EndianStream. So I can recommend you to use it.

Regardless of how well it works, it's going to be replaced with a range-based 
API. So, it's not going to be around in the long run. You can use it. You just 
have to be aware that it's going to go away. Unfortunately, its replacement is 
far from ready, so we really don't know when it's actually going to be 
replaced.

- Jonathan M Davis


Re: D slower ~1s from C ?!

2012-04-05 Thread Kapps

On Thursday, 5 April 2012 at 17:22:38 UTC, Minas wrote:
Many of you should know the website projecteuler.net, where 
there are mathematical problems to solve with computers.


I am doing those in D, and after I finished one today, I 
decided to compile it in C as well to compare the results.


The problem was:

The number 3797 has an interesting property. Being prime 
itself, it is possible to continuously remove digits from left 
to right, and remain prime at each stage: 3797, 797, 97, and 7. 
Similarly we can work from right to left: 3797, 379, 37, and 3.


Find the sum of the only eleven primes that are both 
truncatable from left to right and right to left.


NOTE: 2, 3, 5, and 7 are not considered to be truncatable 
primes.


My solution in D:



First, you should compile with -O -release -inline and, in this 
case, -noboundscheck.


The main issue here seems to be the for loop.
Changing:
for(ulong i = 2; i = cast (ulong)sqrt(cast(double)n+1); ++i)
if( n % i == 0 )
return false;
To:
ulong End = cast (ulong)sqrt(cast(double)n+1);
for(ulong i = 2; i = End; ++i)
if( n % i == 0 )
return false;

Results in a 26 times performance increase for me, based off of 
using a StopWatch at start of main and stopping it at end of 
main. It's possible that the C compiler can recognize that this 
is a constant expression (sqrt might be an intrinsic). D should 
be able to do this even better; sqrt is strongly pure and takes 
in arguments that do not change, thus it should be able to 
automatically make the change I did above. It (at least DMD) does 
not seem to however.


I did not try the C version, and the D version was compiled with 
DMD on Windows.


Re: Up to date documentation on D implementation.

2012-04-05 Thread Mike Parker

On 4/6/2012 7:42 AM, ReneSac wrote:


Most people use DMD, but GDC, I hear, should be on par.


I don't need a 64bit binary right now. Actually, I would even prefer a
32bit one for development because then I can't run too wild in memory
usage. The problem is that DMD seems to require 32 bit windows,
according to the page I linked... Is it not true?


DMD runs just fine on 64-bit Windows.


Re: Insert an element into an Associative Array ?

2012-04-05 Thread Ary Manzana

On 4/5/12 2:57 AM, Chris Pons wrote:

I'm playing around with associative arrays right now and I can't
seem to figure out how to add additional objects to the array. I
tried insert but it doesn't recognize both arguments.

Also, if I do this it produces an error:

Node[bool] test;

Node node;

Node[bool] temp = [ false:node ];

test ~= temp;


Error 1 Error: cannot append type Node[bool] to type
Node[bool] C:\Users\CP\Documents\Visual Studio
2010\Projects\D\STDS\NPC.d 256

Does this mean you can't use the append operator on associative
arrays ? ( this one ~= ) ?


By the way, why is it called associative array? A name like Hash or 
Map would be much better. Everyone knows what a Hash means. I don't see 
anyone using associative array to refer to a Hash. And I think this is 
the source of the confusion Chris has...


I mean, you can't append to an associate array. What part of it makes it 
an array?


Re: Insert an element into an Associative Array ?

2012-04-05 Thread Jonathan M Davis
On Friday, April 06, 2012 11:46:24 Ary Manzana wrote:
 By the way, why is it called associative array? A name like Hash or
 Map would be much better. Everyone knows what a Hash means. I don't see
 anyone using associative array to refer to a Hash. And I think this is
 the source of the confusion Chris has...
 
 I mean, you can't append to an associate array. What part of it makes it
 an array?

The term associative array is quite correct: 
http://en.wikipedia.org/wiki/Associative_array

Also, static arrays are arrays, but you can't append to them. And most 
programming languages with arrays don't have any form of array concatenation 
(certainly, among C-based languages, D is the only one that I'm aware of). 
They do with strings, but strings generally aren't arrays in such languages. 
So, the fact that something is an array says _nothing_ about whether you can 
append to it. The fact that you can with D's dynamic arrays is a fantastic 
feature, but it is by no means guaranteed simply because they're arrays.

And the very nature of an associative array pretty clearly doesn't make any 
sense with appending, since appending doesn't involve a key-value pair at all, 
so I'm honestly very surprised to see that anyone would make that mistake.

- Jonathan M Davis