## digitalmars.D - Positive

Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

The implementation would accept conversion from its base type, e.g.
Positive.(real) can be constructed from a real. The constructor enforces
dynamically the condition. Also, Positive.(real) accepts implicit
conversion to real (no checking necessary).

There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

These specifications are also efficient because checking for positivity
is no cascading checking necessary so there's one test less to do.

However, there is also the risk that Positive has the same fate the many
SafeInt implementation have had in C++: many defined them, nobody used
them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

In order to get things really started, there's already been an exchange
with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to Positive
in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more checks
are necessary.

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean something.
==============

I'm interesting in further arguments. This feature is a numbers issue
(pun not intended), meaning it will be any good only if enough people
find it useful enough to actually use it in their own code and
libraries, therefore building momentum behind it.

Andrei

Oct 04 2008
"Steven Schveighoffer" <schveiguy yahoo.com> writes:
"Andrei Alexandrescu" wrote
(Background: Walter has kindly allowed ".()" as an alternative to the ugly
"!()" for template argument specifications.)

:(

Another case of multiple syntax possibilities.  What was wrong with !() ?
I didn't consider it ugly at all.  In fact, I prefer it.

It's very alarming to me that something like this just has no problem
getting in the language without community feedback.

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

I wouldn't use it, if that helps at all.  Even if it was in Tango (i.e. not
just because I don't use Phobos).

-Steve

Oct 04 2008
=?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes:
Steven Schveighoffer wrote:
"Andrei Alexandrescu" wrote
(Background: Walter has kindly allowed ".()" as an alternative to the ugly
"!()" for template argument specifications.)

:(

Another case of multiple syntax possibilities.  What was wrong with !() ?
I didn't consider it ugly at all.  In fact, I prefer it.

It's very alarming to me that something like this just has no problem
getting in the language without community feedback.

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

I wouldn't use it, if that helps at all.  Even if it was in Tango (i.e. not
just because I don't use Phobos).

Seconded.

Oct 04 2008
"Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Sat, Oct 4, 2008 at 10:55 PM, Steven Schveighoffer
<schveiguy yahoo.com> wrote:
"Andrei Alexandrescu" wrote
(Background: Walter has kindly allowed ".()" as an alternative to the ugly
"!()" for template argument specifications.)

:(

Another case of multiple syntax possibilities.  What was wrong with !() ?
I didn't consider it ugly at all.  In fact, I prefer it.

It's very alarming to me that something like this just has no problem
getting in the language without community feedback.

Heartily agree.  Not that it means anything.

Oct 04 2008
Walter Bright <newshound1 digitalmars.com> writes:
Steven Schveighoffer wrote:
It's very alarming to me that something like this just has no problem
getting in the language without community feedback.

It's there at the moment so we can look at it and see if we like it. I
know Andrei likes it. Anyhow, this is the opportunity for community
feedback.

Oct 04 2008
Sean Kelly <sean invisibleduck.org> writes:
Walter Bright wrote:
Steven Schveighoffer wrote:
It's very alarming to me that something like this just has no problem
getting in the language without community feedback.

It's there at the moment so we can look at it and see if we like it. I
know Andrei likes it. Anyhow, this is the opportunity for community
feedback.

To me, the !() syntax has always clearly communicated what's happening.
The exclamation mark signifies an assertion of sorts (using the
English meaning of 'assertion', not the programming meaning).  With the
dot syntax I'd always be wondering whether there was a function call
taking place that I didn't know about.  Is there anything this change in
syntax gives us over what we currently have?  If not, I don't want it.

Sean

Oct 04 2008
Walter Bright <newshound1 digitalmars.com> writes:
Sean Kelly wrote:
Is there anything this change in syntax
gives us over what we currently have?  If not, I don't want it.

It's purely aesthetic. There are no technical advantages of one over the
other.

Oct 04 2008
=?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes:
Walter Bright wrote:
Sean Kelly wrote:
Is there anything this change in syntax gives us over what we
currently have?  If not, I don't want it.

It's purely aesthetic. There are no technical advantages of one over the
other.

“T!()” just works. There’s no other meaning to it than template
instantiation, whereas ”.” is heavily used as member accessor. I don’t
see any technical or even aesthetical advantages here that might help
understanding code. I just don’t get it.

Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
The problem I see with "!" as a template instantiation is not technical.
I write a fair amount of templated code and over years the "!" did not
grow on me at all. I was time and again consoled by Walter than one day
that will happen, but it never did. I also realized that Walter didn't
see a problem with it because he writes only little template code.

I didn't have much beef with other oddities unique to D. For example, I
found no problem accommodating binary "~" and I was wondering what makes
"!" different. I was just looking at a page full of templates and it
looked like crap.

One morning I woke up with the sudden realization of what the problem
was: the shouting.

In C, "!" is used as a unary operator. That may seem odd at first, but
it nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word, a name,
something coming from natural language. So the conotation with
exclamation jumps at you.

That's why I find the choice of "!" poor. I believe it can impede to
some extent acquisition of templates by newcomers, and conversely I
believe that using .() can make templates more palatable. I tried using
".()" in my code and in only a couple of days it looked and felt way
better to me. Based on that experience, I suggest that "!()" is dropped
in favor of ".()" for template instantiation for D2.

Sean's argument that "The exclamation mark signifies an assertion of
sorts" is exactly where I'd want templates not to be: they should be
blended in, not a hiccup from normal code. Serious effort has been, and
still is, made in D to avoid shell-shocking people about use of
templates, and I think ".()" would be a good step in that direction.

Andrei

Oct 04 2008
dsimcha <dsimcha yahoo.com> writes:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
The problem I see with "!" as a template instantiation is not technical.
I write a fair amount of templated code and over years the "!" did not
grow on me at all. I was time and again consoled by Walter than one day
that will happen, but it never did. I also realized that Walter didn't
see a problem with it because he writes only little template code.
I didn't have much beef with other oddities unique to D. For example, I
found no problem accommodating binary "~" and I was wondering what makes
"!" different. I was just looking at a page full of templates and it
looked like crap.
One morning I woke up with the sudden realization of what the problem
was: the shouting.
In C, "!" is used as a unary operator. That may seem odd at first, but
it nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word, a name,
something coming from natural language. So the conotation with
exclamation jumps at you.
That's why I find the choice of "!" poor. I believe it can impede to
some extent acquisition of templates by newcomers, and conversely I
believe that using .() can make templates more palatable. I tried using
".()" in my code and in only a couple of days it looked and felt way
better to me. Based on that experience, I suggest that "!()" is dropped
in favor of ".()" for template instantiation for D2.
Sean's argument that "The exclamation mark signifies an assertion of
sorts" is exactly where I'd want templates not to be: they should be
blended in, not a hiccup from normal code. Serious effort has been, and
still is, made in D to avoid shell-shocking people about use of
templates, and I think ".()" would be a good step in that direction.
Andrei

Personally, I think that ".()" looks a little too much like a normal
function/method call.  The "!()" syntax looks just different enough to make it
easy to keep straight in my head that stuff with the "!" is a compile-time
construct and stuff without it can be evaluated at runtime.

Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
The problem I see with "!" as a template instantiation is not technical.
I write a fair amount of templated code and over years the "!" did not
grow on me at all. I was time and again consoled by Walter than one day
that will happen, but it never did. I also realized that Walter didn't
see a problem with it because he writes only little template code.
I didn't have much beef with other oddities unique to D. For example, I
found no problem accommodating binary "~" and I was wondering what makes
"!" different. I was just looking at a page full of templates and it
looked like crap.
One morning I woke up with the sudden realization of what the problem
was: the shouting.
In C, "!" is used as a unary operator. That may seem odd at first, but
it nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word, a name,
something coming from natural language. So the conotation with
exclamation jumps at you.
That's why I find the choice of "!" poor. I believe it can impede to
some extent acquisition of templates by newcomers, and conversely I
believe that using .() can make templates more palatable. I tried using
".()" in my code and in only a couple of days it looked and felt way
better to me. Based on that experience, I suggest that "!()" is dropped
in favor of ".()" for template instantiation for D2.
Sean's argument that "The exclamation mark signifies an assertion of
sorts" is exactly where I'd want templates not to be: they should be
blended in, not a hiccup from normal code. Serious effort has been, and
still is, made in D to avoid shell-shocking people about use of
templates, and I think ".()" would be a good step in that direction.
Andrei

Personally, I think that ".()" looks a little too much like a normal
function/method call.  The "!()" syntax looks just different enough to make it
easy to keep straight in my head that stuff with the "!" is a compile-time
construct and stuff without it can be evaluated at runtime.

I'm arguing we _should_ make template code look like "normal" code,
whatever "normal" is :o). We _should_ strive for "quiet" templates.

You know what annoys the living heebiejeebies out of me? Nested template
instantiations.

This!(That!(TheOther!(crap)))

I have a ton + change of those. In superdan's words: intercourse that.

Andrei

Oct 04 2008
superdan <super dan.org> writes:
Andrei Alexandrescu Wrote:

dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
The problem I see with "!" as a template instantiation is not technical.
I write a fair amount of templated code and over years the "!" did not
grow on me at all. I was time and again consoled by Walter than one day
that will happen, but it never did. I also realized that Walter didn't
see a problem with it because he writes only little template code.
I didn't have much beef with other oddities unique to D. For example, I
found no problem accommodating binary "~" and I was wondering what makes
"!" different. I was just looking at a page full of templates and it
looked like crap.
One morning I woke up with the sudden realization of what the problem
was: the shouting.
In C, "!" is used as a unary operator. That may seem odd at first, but
it nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word, a name,
something coming from natural language. So the conotation with
exclamation jumps at you.
That's why I find the choice of "!" poor. I believe it can impede to
some extent acquisition of templates by newcomers, and conversely I
believe that using .() can make templates more palatable. I tried using
".()" in my code and in only a couple of days it looked and felt way
better to me. Based on that experience, I suggest that "!()" is dropped
in favor of ".()" for template instantiation for D2.
Sean's argument that "The exclamation mark signifies an assertion of
sorts" is exactly where I'd want templates not to be: they should be
blended in, not a hiccup from normal code. Serious effort has been, and
still is, made in D to avoid shell-shocking people about use of
templates, and I think ".()" would be a good step in that direction.
Andrei

Personally, I think that ".()" looks a little too much like a normal
function/method call.  The "!()" syntax looks just different enough to make it
easy to keep straight in my head that stuff with the "!" is a compile-time
construct and stuff without it can be evaluated at runtime.

I'm arguing we _should_ make template code look like "normal" code,
whatever "normal" is :o). We _should_ strive for "quiet" templates.

You know what annoys the living heebiejeebies out of me? Nested template
instantiations.

This!(That!(TheOther!(crap)))

I have a ton + change of those. In superdan's words: intercourse that.

Andrei

im a bit drunk. but im much obliged since my name was mentioned n all.

! pisses me off too. i have an opinion. walter looked at unary ops that can be
binary ops. first tilde. pulled tat off. ten he wanted the template thing. only
1 left was !. so he put that at work. right walt?
now i never like ! because of nother reason. i always forget to put it. and yes
it's not needed. i look   code its unambig. then wtf do i need that crap !

anyhoo would be great if ! goes away. to hell with it. need to try
asdad.(asdasd) to see how it feels. and yeah they all jump andreis neck whever
he posts any. or walts. its funny. hold them guns folks. can i delete this
later i wonder.

Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
superdan wrote:
Andrei Alexandrescu Wrote:

dsimcha wrote:
== Quote from Andrei Alexandrescu
(SeeWebsiteForEmail erdani.org)'s article
The problem I see with "!" as a template instantiation is not
technical. I write a fair amount of templated code and over
years the "!" did not grow on me at all. I was time and again
consoled by Walter than one day that will happen, but it never
did. I also realized that Walter didn't see a problem with it
because he writes only little template code. I didn't have much
beef with other oddities unique to D. For example, I found no
problem accommodating binary "~" and I was wondering what makes
"!" different. I was just looking at a page full of templates
and it looked like crap. One morning I woke up with the sudden
realization of what the problem was: the shouting. In C, "!" is
used as a unary operator. That may seem odd at first, but it
nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word,
a name, something coming from natural language. So the
conotation with exclamation jumps at you. That's why I find the
choice of "!" poor. I believe it can impede to some extent
acquisition of templates by newcomers, and conversely I believe
that using .() can make templates more palatable. I tried using
".()" in my code and in only a couple of days it looked and
felt way better to me. Based on that experience, I suggest that
"!()" is dropped in favor of ".()" for template instantiation
for D2. Sean's argument that "The exclamation mark signifies an
assertion of sorts" is exactly where I'd want templates not to
be: they should be blended in, not a hiccup from normal code.
Serious effort has been, and still is, made in D to avoid
shell-shocking people about use of templates, and I think ".()"
would be a good step in that direction. Andrei

normal function/method call.  The "!()" syntax looks just
different enough to make it easy to keep straight in my head that
stuff with the "!" is a compile-time construct and stuff without
it can be evaluated at runtime.

whatever "normal" is :o). We _should_ strive for "quiet"
templates.

You know what annoys the living heebiejeebies out of me? Nested
template instantiations.

This!(That!(TheOther!(crap)))

I have a ton + change of those. In superdan's words: intercourse
that.

Andrei

im a bit drunk. but im much obliged since my name was mentioned n
all.

! pisses me off too. i have an opinion. walter looked at unary ops
that can be binary ops. first tilde. pulled tat off. ten he wanted
the template thing. only 1 left was !. so he put that at work. right
walt? now i never like ! because of nother reason. i always forget to
put it. and yes it's not needed. i look   code its unambig. then wtf
do i need that crap !

anyhoo would be great if ! goes away. to hell with it. need to try
asdad.(asdasd) to see how it feels. and yeah they all jump andreis
neck whever he posts any. or walts. its funny. hold them guns folks.
can i delete this later i wonder.

I guess this still counts as a vote! No? :o)

Andrei

Oct 04 2008
"Chris R. Miller" <lordsauronthegreat gmail.com> writes:
superdan wrote:
Andrei Alexandrescu Wrote:

dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
The problem I see with "!" as a template instantiation is not technical.
I write a fair amount of templated code and over years the "!" did not
grow on me at all. I was time and again consoled by Walter than one day
that will happen, but it never did. I also realized that Walter didn't
see a problem with it because he writes only little template code.
I didn't have much beef with other oddities unique to D. For example, I
found no problem accommodating binary "~" and I was wondering what makes
"!" different. I was just looking at a page full of templates and it
looked like crap.
One morning I woke up with the sudden realization of what the problem
was: the shouting.
In C, "!" is used as a unary operator. That may seem odd at first, but
it nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word, a name,
something coming from natural language. So the conotation with
exclamation jumps at you.
That's why I find the choice of "!" poor. I believe it can impede to
some extent acquisition of templates by newcomers, and conversely I
believe that using .() can make templates more palatable. I tried using
".()" in my code and in only a couple of days it looked and felt way
better to me. Based on that experience, I suggest that "!()" is dropped
in favor of ".()" for template instantiation for D2.
Sean's argument that "The exclamation mark signifies an assertion of
sorts" is exactly where I'd want templates not to be: they should be
blended in, not a hiccup from normal code. Serious effort has been, and
still is, made in D to avoid shell-shocking people about use of
templates, and I think ".()" would be a good step in that direction.
Andrei

function/method call.  The "!()" syntax looks just different enough to make it
easy to keep straight in my head that stuff with the "!" is a compile-time
construct and stuff without it can be evaluated at runtime.

whatever "normal" is :o). We _should_ strive for "quiet" templates.

You know what annoys the living heebiejeebies out of me? Nested template
instantiations.

This!(That!(TheOther!(crap)))

I have a ton + change of those. In superdan's words: intercourse that.

Andrei

im a bit drunk. but im much obliged since my name was mentioned n all.

! pisses me off too. i have an opinion. walter looked at unary ops that can be
binary ops. first tilde. pulled tat off. ten he wanted the template thing. only
1 left was !. so he put that at work. right walt?
now i never like ! because of nother reason. i always forget to put it. and
yes it's not needed. i look   code its unambig. then wtf do i need that crap !

anyhoo would be great if ! goes away. to hell with it. need to try
asdad.(asdasd) to see how it feels. and yeah they all jump andreis neck whever
he posts any. or walts. its funny. hold them guns folks. can i delete this
later i wonder.

I live in California.  Legally I cannot own any gun that could
conceivably hurt someone when misused under the proper situations.  =/

I was never particularly annoyed by the !() syntax, but then again I
have not written much template code.  I can count the number of template
classes I have written on one hand.

I am deeply concerned about the proposed .() syntax, however, since (to
me) it's too similar to a function call.  This lack of finding some kind
of counterproposal left me studying my keyboard for any unused
characters that could become a symbol.  I saw these symbols that I could
remember no existing use for:

, #, $,  I'm favorable to the # symbol. So a template would look like foo#(int)(bar). To me the # symbol looks like it could be two Latin 't' characters (not to be confused with the Greek Tau 'T', which is different). Thus one could remember the mnemonic "template" with two t's for the # symbol. Just a countersuggestion, I haven't really looked through specifications or anything to verify the unused status of any of those symbols.  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Chris R. Miller wrote: superdan wrote: Andrei Alexandrescu Wrote: dsimcha wrote: == Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Andrei function/method call. The "!()" syntax looks just different enough to make it easy to keep straight in my head that stuff with the "!" is a compile-time construct and stuff without it can be evaluated at runtime. whatever "normal" is :o). We _should_ strive for "quiet" templates. You know what annoys the living heebiejeebies out of me? Nested template instantiations. This!(That!(TheOther!(crap))) I have a ton + change of those. In superdan's words: intercourse that. Andrei im a bit drunk. but im much obliged since my name was mentioned n all. ! pisses me off too. i have an opinion. walter looked at unary ops that can be binary ops. first tilde. pulled tat off. ten he wanted the template thing. only 1 left was !. so he put that at work. right walt? now i never like ! because of nother reason. i always forget to put it. and yes it's not needed. i look code its unambig. then wtf do i need that crap ! anyhoo would be great if ! goes away. to hell with it. need to try asdad.(asdasd) to see how it feels. and yeah they all jump andreis neck whever he posts any. or walts. its funny. hold them guns folks. can i delete this later i wonder. I live in California. Legally I cannot own any gun that could conceivably hurt someone when misused under the proper situations. =/ I was never particularly annoyed by the !() syntax, but then again I have not written much template code. I can count the number of template classes I have written on one hand. I am deeply concerned about the proposed .() syntax, however, since (to me) it's too similar to a function call. This lack of finding some kind of counterproposal left me studying my keyboard for any unused characters that could become a symbol. I saw these symbols that I could remember no existing use for: , #,$, 

I'm favorable to the # symbol.  So a template would look like
foo#(int)(bar).

To me the # symbol looks like it could be two Latin 't' characters (not
to be confused with the Greek Tau 'T', which is different).  Thus one
could remember the mnemonic "template" with two t's for the # symbol.

Just a countersuggestion, I haven't really looked through specifications
or anything to verify the unused status of any of those symbols.

No go due to #line. :o(

Andrei

Oct 05 2008
Lutger <lutger.blijdestijn gmail.com> writes:
Andrei Alexandrescu wrote:

...
No go due to #line. :o(

Andrei

Perhaps this is silly, but if #line is the sole blocker, then why not change
#line? That feature seems so small in comparison to template instantiation,
it isn't fair to get the nicer symbol.

Oct 06 2008
KennyTM~ <kennytm gmail.com> writes:
Chris R. Miller wrote:
superdan wrote:
Andrei Alexandrescu Wrote:

dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s
article
The problem I see with "!" as a template instantiation is not
technical.
I write a fair amount of templated code and over years the "!" did not
grow on me at all. I was time and again consoled by Walter than one
day
that will happen, but it never did. I also realized that Walter didn't
see a problem with it because he writes only little template code.
I didn't have much beef with other oddities unique to D. For
example, I
found no problem accommodating binary "~" and I was wondering what
makes
"!" different. I was just looking at a page full of templates and it
looked like crap.
One morning I woke up with the sudden realization of what the problem
was: the shouting.
In C, "!" is used as a unary operator. That may seem odd at first, but
it nevers follows a word so it's tenuous to associate it with the
natural language "!". In D, binary "!" _always_ follows a word, a
name,
something coming from natural language. So the conotation with
exclamation jumps at you.
That's why I find the choice of "!" poor. I believe it can impede to
some extent acquisition of templates by newcomers, and conversely I
believe that using .() can make templates more palatable. I tried
using
".()" in my code and in only a couple of days it looked and felt way
better to me. Based on that experience, I suggest that "!()" is
dropped
in favor of ".()" for template instantiation for D2.
Sean's argument that "The exclamation mark signifies an assertion of
sorts" is exactly where I'd want templates not to be: they should be
blended in, not a hiccup from normal code. Serious effort has been,
and
still is, made in D to avoid shell-shocking people about use of
templates, and I think ".()" would be a good step in that direction.
Andrei

function/method call.  The "!()" syntax looks just different enough
to make it
easy to keep straight in my head that stuff with the "!" is a
compile-time
construct and stuff without it can be evaluated at runtime.

whatever "normal" is :o). We _should_ strive for "quiet" templates.

You know what annoys the living heebiejeebies out of me? Nested
template instantiations.

This!(That!(TheOther!(crap)))

I have a ton + change of those. In superdan's words: intercourse that.

Andrei

im a bit drunk. but im much obliged since my name was mentioned n all.

! pisses me off too. i have an opinion. walter looked at unary ops
that can be binary ops. first tilde. pulled tat off. ten he wanted the
template thing. only 1 left was !. so he put that at work. right walt?
now i never like ! because of nother reason. i always forget to put
it. and yes it's not needed. i look   code its unambig. then wtf do i
need that crap !

anyhoo would be great if ! goes away. to hell with it. need to try
asdad.(asdasd) to see how it feels. and yeah they all jump andreis
neck whever he posts any. or walts. its funny. hold them guns folks.
can i delete this later i wonder.

I live in California.  Legally I cannot own any gun that could
conceivably hurt someone when misused under the proper situations.  =/

I was never particularly annoyed by the !() syntax, but then again I
have not written much template code.  I can count the number of template
classes I have written on one hand.

I am deeply concerned about the proposed .() syntax, however, since (to
me) it's too similar to a function call.  This lack of finding some kind
of counterproposal left me studying my keyboard for any unused
characters that could become a symbol.  I saw these symbols that I could
remember no existing use for:

, #, $,  I'm favorable to the # symbol. So a template would look like foo#(int)(bar). To me the # symbol looks like it could be two Latin 't' characters (not to be confused with the Greek Tau 'T', which is different). Thus one could remember the mnemonic "template" with two t's for the # symbol. Just a countersuggestion, I haven't really looked through specifications or anything to verify the unused status of any of those symbols. Sorry,  is not possible because of string like = this.toString();.  Oct 05 2008 Janderson <ask me.com> writes: Andrei Alexandrescu wrote: dsimcha wrote: == Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Andrei Personally, I think that ".()" looks a little too much like a normal function/method call. The "!()" syntax looks just different enough to make it easy to keep straight in my head that stuff with the "!" is a compile-time construct and stuff without it can be evaluated at runtime. I'm arguing we _should_ make template code look like "normal" code, whatever "normal" is :o). We _should_ strive for "quiet" templates. You know what annoys the living heebiejeebies out of me? Nested template instantiations. This!(That!(TheOther!(crap))) I have a ton + change of those. In superdan's words: intercourse that. Andrei I guess if you want to make template look like normal code your could look at extending that static syntax to accept things like alias: void FooTemplate(alias T, alias T2, static T x, T2 f) { ... } //call int value; FooTemplate(int, int, 10, value); //And with induction T2 can be solved so (Note: I'm considering induction either all that can be solved, or nothing) FooTemplate(int, 10, value); -Joel  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Janderson wrote: Andrei Alexandrescu wrote: dsimcha wrote: == Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Andrei Personally, I think that ".()" looks a little too much like a normal function/method call. The "!()" syntax looks just different enough to make it easy to keep straight in my head that stuff with the "!" is a compile-time construct and stuff without it can be evaluated at runtime. I'm arguing we _should_ make template code look like "normal" code, whatever "normal" is :o). We _should_ strive for "quiet" templates. You know what annoys the living heebiejeebies out of me? Nested template instantiations. This!(That!(TheOther!(crap))) I have a ton + change of those. In superdan's words: intercourse that. Andrei I guess if you want to make template look like normal code your could look at extending that static syntax to accept things like alias: void FooTemplate(alias T, alias T2, static T x, T2 f) { ... } //call int value; FooTemplate(int, int, 10, value); //And with induction T2 can be solved so (Note: I'm considering induction either all that can be solved, or nothing) FooTemplate(int, 10, value); -Joel Walter actually went out implementing this for days and reached irreconcilable issues. Andrei  Oct 05 2008 Janderson <ask me.com> writes: Andrei Alexandrescu wrote: Janderson wrote: Andrei Alexandrescu wrote: dsimcha wrote: == Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Andrei Personally, I think that ".()" looks a little too much like a normal function/method call. The "!()" syntax looks just different enough to make it easy to keep straight in my head that stuff with the "!" is a compile-time construct and stuff without it can be evaluated at runtime. I'm arguing we _should_ make template code look like "normal" code, whatever "normal" is :o). We _should_ strive for "quiet" templates. You know what annoys the living heebiejeebies out of me? Nested template instantiations. This!(That!(TheOther!(crap))) I have a ton + change of those. In superdan's words: intercourse that. Andrei I guess if you want to make template look like normal code your could look at extending that static syntax to accept things like alias: void FooTemplate(alias T, alias T2, static T x, T2 f) { ... } //call int value; FooTemplate(int, int, 10, value); //And with induction T2 can be solved so (Note: I'm considering induction either all that can be solved, or nothing) FooTemplate(int, 10, value); -Joel Walter actually went out implementing this for days and reached irreconcilable issues. Andrei That's a shame :(  Oct 05 2008 Ary Borenszweig <ary esperanto.org.ar> writes: Andrei Alexandrescu escribió: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. I was thinking about in which other way templates could be specified... Most of the other symbols already have a meaning as binary operator. And it also would be nice to have an opening and closing symbols, like <> in Java, C++, etc. Can't {} be used for that? For example: List{int} someList; void foo{T}(T val) { } It seems more quiet. :-) The only thing is, I don't know if this can lead to ambiguos parsing. I thought about it a little, and it seems it's ok. Another thing is that maybe { and ( look alike, so it can lead to confusion... Oh, mmm... does it conflict with struct initializers?  Oct 04 2008 "Chris R. Miller" <lordsauronthegreat gmail.com> writes: Ary Borenszweig wrote: Andrei Alexandrescu escribió: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. I was thinking about in which other way templates could be specified... Most of the other symbols already have a meaning as binary operator. And it also would be nice to have an opening and closing symbols, like <> in Java, C++, etc. I remember reading that Walter specifically rejected that idea because it became ambiguous with bitshift operations. In my time with Java, I saw many of these: public class Foo<Bar<o extends ArrayList>> { ... } When instantiated in code the >> at the end of the template declaration does become very ambiguous with a bitshift. Can't {} be used for that? For example: List{int} someList; void foo{T}(T val) { } It seems more quiet. :-) I rejected that idea when I was searching for counterproposals because it conflicts with the code-block syntax. The existing () is much less ambiguous, since when you encounter two sets of parenthesis it must be a template. If it were multiplication it would require the explicit * binary operator. The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz).  Oct 05 2008 Michel Fortin <michel.fortin michelf.com> writes: On 2008-10-05 20:57:31 -0400, "Chris R. Miller" <lordsauronthegreat gmail.com> said: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). Well, not so sure about that: I'm pretty sure it's needed for disambiguation too. Let's say you have: void foo(int x)(); void foo(T)(T x); foo(5); Is foo(5) a the same as foo!(5), or does it call foo!(int).foo(5) ? Under the current rules, it's the second (you can write foo!(5) to call the first). If you allow templates to be instanciated without the "!", then I guess both will match and you'll have ambiguity. If you could avoid having sets of parameters, one for the function and one for the template, then you could get rid of the "!" in a snap... Well, maybe not. You'll still have to resolve the same issues for constructors: class A(int x) { this() {} } class A() { this(int x) {} } auto a = new A(5); Perhaps this is not a problem however: the only two valid ways to create an instance of one or the other are "new A!(5)" or "new A!()(5)", which would translate in non-"!" syntax as: "new A(5)" and "new A()(5)". Unfortunately, we don't have this "luck" with functions. -- Michel Fortin michel.fortin michelf.com http://michelf.com/  Oct 05 2008 Vincent Richomme <forumer smartmobili.com> writes: Michel Fortin a crit : On 2008-10-05 20:57:31 -0400, "Chris R. Miller" <lordsauronthegreat gmail.com> said: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). What about the ^ ? I think it's not worst than ! foo^(int)(bar) but maybe this symbol is already used by D ? Personally I would prefer to keep the C++, Java, C# syntax with <> because people are used to it even if in some cases it looks like a bit shift op.  Oct 05 2008 Robert Fraser <fraserofthenight gmail.com> writes: Vincent Richomme wrote: Michel Fortin a crit : On 2008-10-05 20:57:31 -0400, "Chris R. Miller" <lordsauronthegreat gmail.com> said: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). What about the ^ ? I think it's not worst than ! foo^(int)(bar) but maybe this symbol is already used by D ? Personally I would prefer to keep the C++, Java, C# syntax with <> because people are used to it even if in some cases it looks like a bit shift op. The problem isn't what it looks like to people -- people will generally be able to discern a template instantiation/declaration from a bitshift. The problem is what it looks like to the compiler. If we had this in the compiler, the compiler would need to resolve symbols before it was able to produce a full parse tree, which leads to slower compilation times, more difficult tool creation, and a whole slew of other problems.  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Vincent Richomme wrote: Michel Fortin a écrit : On 2008-10-05 20:57:31 -0400, "Chris R. Miller" <lordsauronthegreat gmail.com> said: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). What about the ^ ? I think it's not worst than ! foo^(int)(bar) but maybe this symbol is already used by D ? Personally I would prefer to keep the C++, Java, C# syntax with <> because people are used to it even if in some cases it looks like a bit shift op. ^ is for bitwise XOR! Unless you use ^^ foo^^(int)(bar) Not my cup of tea though.  Oct 05 2008 Vincent Richomme <forumer smartmobili.com> writes: KennyTM~ a écrit : Vincent Richomme wrote: Michel Fortin a écrit : On 2008-10-05 20:57:31 -0400, "Chris R. Miller" <lordsauronthegreat gmail.com> said: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). What about the ^ ? I think it's not worst than ! foo^(int)(bar) but maybe this symbol is already used by D ? Personally I would prefer to keep the C++, Java, C# syntax with <> because people are used to it even if in some cases it looks like a bit shift op. ^ is for bitwise XOR! Just look at managed c++ in .NET and tell me if ^ is always a bitwise XOR. Unless you use ^^ foo^^(int)(bar) Not my cup of tea though.  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Vincent Richomme wrote: KennyTM~ a écrit : Vincent Richomme wrote: Michel Fortin a écrit : On 2008-10-05 20:57:31 -0400, "Chris R. Miller" <lordsauronthegreat gmail.com> said: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). What about the ^ ? I think it's not worst than ! foo^(int)(bar) but maybe this symbol is already used by D ? Personally I would prefer to keep the C++, Java, C# syntax with <> because people are used to it even if in some cases it looks like a bit shift op. ^ is for bitwise XOR! Just look at managed c++ in .NET and tell me if ^ is always a bitwise XOR. OK. The *binary* operator ^ is for bitwise XOR! And the ^ in foo^(int) acts as a *binary* operator also. And in C++/CLI the ^ in int^ and ^x acts as a *unary* operator, so no problem in this case. AFAIK one of the reason ! was chosen because a!b doesn't make sense in C, so D is free to use ! as a *binary* operator. Unless you use ^^ foo^^(int)(bar) Not my cup of tea though.  Oct 05 2008 Michel Fortin <michel.fortin michelf.com> writes: On 2008-10-05 22:23:16 -0400, Michel Fortin <michel.fortin michelf.com> said: Well, not so sure about that: I'm pretty sure it's needed for disambiguation too. Let's say you have: void foo(int x)(); void foo(T)(T x); foo(5); Is foo(5) a the same as foo!(5), or does it call foo!(int).foo(5) ? Under the current rules, it's the second (you can write foo!(5) to call the first). If you allow templates to be instanciated without the "!", then I guess both will match and you'll have ambiguity. If you could avoid having sets of parameters, one for the function and one for the template, then you could get rid of the "!" in a snap... Or... we could just disallow having both at the same time, just like you can't have two functions with the same arguments. A call to foo(5) would be ambigous in the above situation, plain and simple. Is this reasonable? We could still disambiguate using: foo!(5); and: foo(int)(5); In this context, the ! becomes the "force this to be template arguments" operator, or the "do not deduce template arguments, I'll provide them" operator. Or we could just forget ! completely and leave the first one impossible to disambiguate. Which makes me think that it's sad we can't write the second as: foo(int, 5); I'd be much nicer to the eye. -- Michel Fortin michel.fortin michelf.com http://michelf.com/  Oct 06 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Jarrett Billingsley wrote: On Mon, Oct 6, 2008 at 9:16 AM, Denis Koroskin <2korden gmail.com> wrote: On Mon, 06 Oct 2008 16:42:51 +0400, Jarrett Billingsley <jarrett.billingsley gmail.com> wrote: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() Stdout("foo")("bar!").newline; paranthesises. The point is that something like "foo()(5)" could then be either a template instantiation or a chained call. I think there is ambiguity, and another problem is that we wanted to make things "better"; under these circumstances, terser would be better. Andrei  Oct 06 2008 Benji Smith <dlanguage benjismith.net> writes: Jarrett Billingsley wrote: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() No it doesn't. Stdout("foo")("bar!").newline; This is one of the main reasons I dislike opCall. Combined with optional-parentheses for function invocation, opCall is a poison-pill that creates a lot of potential ambiguities and prevents the implementation of more compelling features. --benji  Oct 07 2008 Benji Smith <dlanguage benjismith.net> writes: Simen Kjaeraas wrote: On Tue, 07 Oct 2008 16:27:00 +0200, Benji Smith <dlanguage benjismith.net> wrote: Jarrett Billingsley wrote: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() Stdout("foo")("bar!").newline; This is one of the main reasons I dislike opCall. Combined with optional-parentheses for function invocation, opCall is a poison-pill that creates a lot of potential ambiguities and prevents the implementation of more compelling features. --benji void delegate() foo() { return delegate void() {);}; } ? Is that supposed to be legal code? I'll assume this is what you meant to write: void delegate() foo() { return delegate void() { }; } ...and that you're making the point that opCall introduces no more ambiguities than delegate-call syntax. And I suppose you're right. But people use opCall *everywhere* for all sorts of crazy crap, and I think it makes the code far less readable. When the call syntax is used for actual delegates, I don't really mind. But I think call-chaining with opCall is a huge eye-sore: object(x)("hello")(); I guess my ambiguity argument is invalidated by wanting to keep the delegate-call syntax. I just hate when it's applied to non-delegates. --benji  Oct 08 2008 Benji Smith <dlanguage benjismith.net> writes: Jarrett Billingsley wrote: On Sun, Oct 5, 2008 at 8:57 PM, Chris R. Miller <lordsauronthegreat gmail.com> wrote: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). Unambiguous grammar, you fail it. foo(bar)(baz); // template instantiation or a chained call? This _can_ be _made_ to work, but it would mean that the parse tree would be dependent upon semantic analysis, and that just makes things slow and awful. I.e. C++. I'd be happy to get rid of OpCall, which I've always found confusing and pointless. --benji  Oct 06 2008 KennyTM~ <kennytm gmail.com> writes: Benji Smith wrote: Jarrett Billingsley wrote: On Sun, Oct 5, 2008 at 8:57 PM, Chris R. Miller <lordsauronthegreat gmail.com> wrote: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). Unambiguous grammar, you fail it. foo(bar)(baz); // template instantiation or a chained call? This _can_ be _made_ to work, but it would mean that the parse tree would be dependent upon semantic analysis, and that just makes things slow and awful. I.e. C++. I'd be happy to get rid of OpCall, which I've always found confusing and pointless. --benji That's going to break a lot of struct constructors using static opCalls.  Oct 06 2008 Benji Smith <dlanguage benjismith.net> writes: KennyTM~ wrote: Benji Smith wrote: Jarrett Billingsley wrote: On Sun, Oct 5, 2008 at 8:57 PM, Chris R. Miller <lordsauronthegreat gmail.com> wrote: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). Unambiguous grammar, you fail it. foo(bar)(baz); // template instantiation or a chained call? This _can_ be _made_ to work, but it would mean that the parse tree would be dependent upon semantic analysis, and that just makes things slow and awful. I.e. C++. I'd be happy to get rid of OpCall, which I've always found confusing and pointless. --benji That's going to break a lot of struct constructors using static opCalls. Only because structs should have had constructors from the start. Using opCall was always a hack around the lack of constructors on structs. opCall is a source of numerous language ambiguities that make other features more difficult to implement. For example, template instantiation could be done with bare parentheses ("Template(args)" instead of "Template!(args)" or "Template{args}") if opCall was eliminated. --benji  Oct 07 2008 KennyTM~ <kennytm gmail.com> writes: Benji Smith wrote: KennyTM~ wrote: Benji Smith wrote: Jarrett Billingsley wrote: On Sun, Oct 5, 2008 at 8:57 PM, Chris R. Miller <lordsauronthegreat gmail.com> wrote: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). Unambiguous grammar, you fail it. foo(bar)(baz); // template instantiation or a chained call? This _can_ be _made_ to work, but it would mean that the parse tree would be dependent upon semantic analysis, and that just makes things slow and awful. I.e. C++. I'd be happy to get rid of OpCall, which I've always found confusing and pointless. --benji That's going to break a lot of struct constructors using static opCalls. Only because structs should have had constructors from the start. Using opCall was always a hack around the lack of constructors on structs. opCall is a source of numerous language ambiguities that make other features more difficult to implement. For example, template instantiation could be done with bare parentheses ("Template(args)" instead of "Template!(args)" or "Template{args}") if opCall was eliminated. --benji But what about a method that returns a delegate?  Oct 07 2008 Benji Smith <dlanguage benjismith.net> writes: KennyTM~ wrote: Benji Smith wrote: KennyTM~ wrote: Benji Smith wrote: Jarrett Billingsley wrote: On Sun, Oct 5, 2008 at 8:57 PM, Chris R. Miller <lordsauronthegreat gmail.com> wrote: The !() syntax seems to serve only as a heads up that it's a template. Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work just as well as foo!(int)(bar, baaz). Unambiguous grammar, you fail it. foo(bar)(baz); // template instantiation or a chained call? This _can_ be _made_ to work, but it would mean that the parse tree would be dependent upon semantic analysis, and that just makes things slow and awful. I.e. C++. I'd be happy to get rid of OpCall, which I've always found confusing and pointless. --benji That's going to break a lot of struct constructors using static opCalls. Only because structs should have had constructors from the start. Using opCall was always a hack around the lack of constructors on structs. opCall is a source of numerous language ambiguities that make other features more difficult to implement. For example, template instantiation could be done with bare parentheses ("Template(args)" instead of "Template!(args)" or "Template{args}") if opCall was eliminated. --benji But what about a method that returns a delegate? Damn. You win. Hmmmmmm... I still hate opCall, though :) --benji  Oct 07 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Benji Smith wrote: Hmmmmmm... I still hate opCall, though :) One context in which I found opCall very valuable is parameterized functions: functions that take, say, 1 argument but are parameterized by another. An example is a Gaussian kernel of parameterized bandwidth: double gaussianKernel(double d) { return exp(-d * d / alpha * alpha); } We'd like to be able to configure alpha properly (not via a global, because there could be several Gaussian kernels around). A solution would be to use delegates, but that's inefficient and a kernel is evaluated so often it's not even funny. So a good solution is to make the function a struct with state: struct GaussianKernel { private double alpha2InvNeg = -1; double opCall(double d) const { return exp(d * d * alpha2InvNeg); } void alpha(double a) { enforce(a > 0); alpha2InvNeg = -1 / (a * a); } double alpha() const { return sqrt(-1 / alpha2InvNeg); } } Andrei  Oct 07 2008 Benji Smith <dlanguage benjismith.net> writes: Andrei Alexandrescu wrote: Benji Smith wrote: Hmmmmmm... I still hate opCall, though :) One context in which I found opCall very valuable is parameterized functions: functions that take, say, 1 argument but are parameterized by another. An example is a Gaussian kernel of parameterized bandwidth: double gaussianKernel(double d) { return exp(-d * d / alpha * alpha); } We'd like to be able to configure alpha properly (not via a global, because there could be several Gaussian kernels around). A solution would be to use delegates, but that's inefficient and a kernel is evaluated so often it's not even funny. So a good solution is to make the function a struct with state: struct GaussianKernel { private double alpha2InvNeg = -1; double opCall(double d) const { return exp(d * d * alpha2InvNeg); } void alpha(double a) { enforce(a > 0); alpha2InvNeg = -1 / (a * a); } double alpha() const { return sqrt(-1 / alpha2InvNeg); } } Andrei Great example! I've actually implemented the same thing (in Java). I have a KernelDensityEstimator class, for estimating the shape of a distribution, based on sample values from that distribution. The KDE constructor takes a Function object to define the kernel. (Rather than defining a "Kernel" as an interface or an abstract class, I define a more general "Function" interface, and let the caller make his own choice about whether his function makes an appropriate kernel.) So the code looks like this: interface Function { public double project(double value); } class GaussianFunction implements Function { private double height; private double mean; private double stdev; private double denominator; public GaussianFunction(double height, double mean, double stdev) { enforce(height > 0); enforce(!Double.isInfinite(height)); enforce(!Double.isNaN(height)); enforce(!Double.isInfinite(mean)); enforce(!Double.isNaN(mean)); enforce(stdev > 0); enforce(!Double.isInfinite(stdev)); enforce(!Double.isNaN(stdev)); this.height = height; this.mean = mean; this.stdev = stdev; // Pre-calculate the denominator of the exponent // (since it won't vary from call to call). this.denominator = 2 * stdev * stdev; } public double project(double value) { double difference = x - mean; double numerator = difference * difference; return height * Math.exp(- (numerator / denominator)); } } class KernelDensityEstimator { private Function kernel; private List<Double> samples; public KernelDensityEstimator(Function kernel) { this.kernel = kernel; this.samples = new ArrayList<Double>(); } public double addSample(double sample) { samples.add(sample); } public estimatedProbabilityOf(double value) { double sum = 0; for (double sample : samples) { sum += kernel.project(sample); } return sum / samples.size(); } } Anyhoo... maybe that's a little too much code to dump, but I wanted to show the definition of the concept of a "Function", separated from the definition of a particular function class, separated from the instantiation of that class, and separated from the invocation of the function. In my mind, opCall would encourage code like this: foreach (double x; values) { GaussianKernel(alpha)(x); } In this code, the alpha gets set... over and over and over again. If the construction of the parametric function is distinct from the calling of it, the user is encouraged to write code more like this: auto kernel = new GuassianKernel(alpha); foreach (double x; values) { auto result = kernel.valueOf(x); } It can be convincingly argued that a Function object shouldn't have a *named* method. Or at least, if it does have a named method, the name should be the same at the name of the function. But then that makes it hard to use functions polymorphically. What you and I are doing is pretty much the same, except that I call my function "project" (since a function is a projection from an x value to a corresponding y value), whereas you use opCall. The nice thing about using a named function, though, is that it allows me to pass functions around polymorphically, and since Java doesn't have function pointers, this is the best solution to the problem. I totally agree with you, though, that this is the best possible use for opCall. --benji  Oct 07 2008 =?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Sean has a point. Templates are not runtime constructs. So a clear distinction between instantiating a function with a given type and just calling a function that has fixed argument types and a fixed return type is necessary. The exclamation mark gives us this clear distinction and has served well in terms of readability for me, especially because it jumps out — not because it’s an exclamation mark, thus having a meaning in natural language, but rather just because of its form. A straight vertical line with a dot underneath it. That just works perfectly well as seperator between identifier/type and type argument. Also, you might want to consider changing your font if exclamation marks jump at you so intensively. ;)  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Alexander Pánek wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Sean has a point. Templates are not runtime constructs. So a clear distinction between instantiating a function with a given type and just calling a function that has fixed argument types and a fixed return type is necessary. Why? This sounds objective, so you better back it up. Au contraire, I see absolutely, but absolutely no need for a distinction. If it weren't for syntactic difficulties, to me using straight parentheses for template instantiation would have been the perfect choice. (How many times did you just forget the "!"? I know I often do. Why? Because most of the time it's not even needed.) The exclamation mark gives us this clear distinction and has served well in terms of readability for me, especially because it jumps out — not because it’s an exclamation mark, thus having a meaning in natural language, but rather just because of its form. A straight vertical line with a dot underneath it. That just works perfectly well as seperator between identifier/type and type argument. I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. Also, you might want to consider changing your font if exclamation marks jump at you so intensively. ;) I use Vera, probably the best code font I've ever had. Andrei  Oct 04 2008 =?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes: Andrei Alexandrescu wrote: Alexander Pánek wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Sean has a point. Templates are not runtime constructs. So a clear distinction between instantiating a function with a given type and just calling a function that has fixed argument types and a fixed return type is necessary. Why? This sounds objective, so you better back it up. Au contraire, I see absolutely, but absolutely no need for a distinction. If it weren't for syntactic difficulties, to me using straight parentheses for template instantiation would have been the perfect choice. (How many times did you just forget the "!"? I know I often do. Why? Because most of the time it's not even needed.) The exclamation mark gives us this clear distinction and has served well in terms of readability for me, especially because it jumps out — not because it’s an exclamation mark, thus having a meaning in natural language, but rather just because of its form. A straight vertical line with a dot underneath it. That just works perfectly well as seperator between identifier/type and type argument. I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. IMHO — I forgot that before, so that’s why it might have sounded a bit too objective —, the clear distinction is important to keep the code self-documenting. It might not be so important in terms of freestanding templated functions that might even be simple enough that the argument types can be infered, but as soon as something heavily alters the way the code and the binary looks like afterwards (CTFE, multiple templated class/struct/function instantiates, string mixins created by CTFE functions, etc.), it (again, in my truly subjective opinion) deserves to be marked as such. I see this distinction as feature, not as flaw.  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Alexander Pánek wrote: Andrei Alexandrescu wrote: Alexander Pánek wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Sean has a point. Templates are not runtime constructs. So a clear distinction between instantiating a function with a given type and just calling a function that has fixed argument types and a fixed return type is necessary. Why? This sounds objective, so you better back it up. Au contraire, I see absolutely, but absolutely no need for a distinction. If it weren't for syntactic difficulties, to me using straight parentheses for template instantiation would have been the perfect choice. (How many times did you just forget the "!"? I know I often do. Why? Because most of the time it's not even needed.) The exclamation mark gives us this clear distinction and has served well in terms of readability for me, especially because it jumps out — not because it’s an exclamation mark, thus having a meaning in natural language, but rather just because of its form. A straight vertical line with a dot underneath it. That just works perfectly well as seperator between identifier/type and type argument. I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. IMHO — I forgot that before, so that’s why it might have sounded a bit too objective —, the clear distinction is important to keep the code self-documenting. It might not be so important in terms of freestanding templated functions that might even be simple enough that the argument types can be infered, but as soon as something heavily alters the way the code and the binary looks like afterwards (CTFE, multiple templated class/struct/function instantiates, string mixins created by CTFE functions, etc.), it (again, in my truly subjective opinion) deserves to be marked as such. I see this distinction as feature, not as flaw. I don't understand this argument. For one thing, argument type deduction for template functions is not simple at all and we're glad that it's taken care of. Andrei  Oct 04 2008 Sean Kelly <sean invisibleduck.org> writes: Andrei Alexandrescu wrote: Alexander Pánek wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Sean has a point. Templates are not runtime constructs. So a clear distinction between instantiating a function with a given type and just calling a function that has fixed argument types and a fixed return type is necessary. Why? This sounds objective, so you better back it up. I like being able to distinguish between the function signature and the parameter list and to tell at a glance what's actually happening. Since the dot already has a function in this context, I don't think it should be given another. Also, if we get the option to override opDot, things could get really weird if it's also a template signifier. The exclamation mark gives us this clear distinction and has served well in terms of readability for me, especially because it jumps out — not because it’s an exclamation mark, thus having a meaning in natural language, but rather just because of its form. A straight vertical line with a dot underneath it. That just works perfectly well as seperator between identifier/type and type argument. I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. Why is it undesirable? I like the idea of static parameters as described at the conference last year, but I don't think that has any bearing on this particular issue. Sean  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Sean Kelly wrote: Andrei Alexandrescu wrote: I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. Why is it undesirable? I like the idea of static parameters as described at the conference last year, but I don't think that has any bearing on this particular issue. Time and again, both Walter and myself have met people who experience a mental block whenever templates come within a mile. The fact that they come with the sign Here! This! Is! A! Template! doesn't help any. Andrei  Oct 05 2008 "Chris R. Miller" <lordsauronthegreat gmail.com> writes: Andrei Alexandrescu wrote: Sean Kelly wrote: Andrei Alexandrescu wrote: I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. Why is it undesirable? I like the idea of static parameters as described at the conference last year, but I don't think that has any bearing on this particular issue. Time and again, both Walter and myself have met people who experience a mental block whenever templates come within a mile. The fact that they come with the sign Here! This! Is! A! Template! doesn't help any. Are we discussing better template syntax of a magical injection that will cure the common fear of template code? ;-)  Oct 05 2008 Sergey Gromov <snake.scaly gmail.com> writes: Sat, 04 Oct 2008 23:50:47 -0500, Andrei Alexandrescu wrote: Alexander Panek wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not=20 technical. I write a fair amount of templated code and over years the= "!" did not grow on me at all. I was time and again consoled by Walter= than one day that will happen, but it never did. I also realized that= Walter didn't see a problem with it because he writes only little=20 template code. I didn't have much beef with other oddities unique to D. For example,= I found no problem accommodating binary "~" and I was wondering what= makes "!" different. I was just looking at a page full of templates=20 and it looked like crap. One morning I woke up with the sudden realization of what the problem= was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but= it nevers follows a word so it's tenuous to associate it with the=20 natural language "!". In D, binary "!" _always_ follows a word, a=20 name, something coming from natural language. So the conotation with= exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to= some extent acquisition of templates by newcomers, and conversely I=20 believe that using .() can make templates more palatable. I tried=20 using ".()" in my code and in only a couple of days it looked and felt= way better to me. Based on that experience, I suggest that "!()" is=20 dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of= sorts" is exactly where I'd want templates not to be: they should be= blended in, not a hiccup from normal code. Serious effort has been,=20 and still is, made in D to avoid shell-shocking people about use of=20 templates, and I think ".()" would be a good step in that direction. Sean has a point. Templates are not runtime constructs. So a clear=20 distinction between instantiating a function with a given type and just= calling a function that has fixed argument types and a fixed return typ= is necessary. Why? This sounds objective, so you better back it up. Au contraire, I=20 see absolutely, but absolutely no need for a distinction. If it weren't= for syntactic difficulties, to me using straight parentheses for=20 template instantiation would have been the perfect choice. (How many=20 times did you just forget the "!"? I know I often do. Why? Because most= of the time it's not even needed.) =20 The exclamation mark gives us this clear distinction and=20 has served well in terms of readability for me, especially because it= jumps out ? not because it?s an exclamation mark, thus having a meaning= in natural language, but rather just because of its form. A straight=20 vertical line with a dot underneath it. That just works perfectly well= as seperator between identifier/type and type argument. I believe the clear distinction is not only unnecessary, but=20 undesirable. We should actively fight against it. You have a problem with shouting. Not everyone has. The distinction is important IMHO because the choice between template=20 and runtime is a speed/size tradeoff choice. It's better to make it=20 explicitly.  Oct 06 2008 Christopher Wright <dhasenan gmail.com> writes: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used.  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Christopher Wright wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Andrei!  Oct 04 2008 Michel Fortin <michel.fortin michelf.com> writes: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive$$real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". - - - The ".(" syntax makes me think more of something like this: void func(T, alias methodOfT, A...)(T obj, A args) { obj.(methodOfT)(args); } which I which I could do. If methodOfT was a string, I suppose I could use string mixins, but it pushes diagnostics about misnamed methods further in the template and requires adding quotes to the template parameter when instanciating. -- Michel Fortin michel.fortin michelf.com http://michelf.com/  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". - - - The ".(" syntax makes me think more of something like this: void func(T, alias methodOfT, A...)(T obj, A args) { obj.(methodOfT)(args); } which I which I could do. If methodOfT was a string, I suppose I could use string mixins, but it pushes diagnostics about misnamed methods further in the template and requires adding quotes to the template parameter when instanciating. Argh, actually I once have a strong desire making f«T»(x); a valid construct, and to workaround that « and » can't be easily typed you could substitute it with f\<T\>(x); --- Anyway, I think the .() syntax is not as good as !() because the . is pretty hideous before another punctuation mark (which may be a good thing, I don't know), and one could easily miss it. And even if .() is allowed, please don't remove !() -- it will break significantly many code, and it doesn't cause any ambiguity either (unlike .func() vs .prop).  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: KennyTM~ wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". - - - The ".(" syntax makes me think more of something like this: void func(T, alias methodOfT, A...)(T obj, A args) { obj.(methodOfT)(args); } which I which I could do. If methodOfT was a string, I suppose I could use string mixins, but it pushes diagnostics about misnamed methods further in the template and requires adding quotes to the template parameter when instanciating. Argh, actually I once have a strong desire making f«T»(x); a valid construct, and to workaround that « and » can't be easily typed you could substitute it with f\<T\>(x); --- Yah I would've like French quotes too. Anyway, I think the .() syntax is not as good as !() because the . is pretty hideous before another punctuation mark (which may be a good thing, I don't know), and one could easily miss it. And even if .() is allowed, please don't remove !() -- it will break significantly many code, and it doesn't cause any ambiguity either (unlike .func() vs .prop). Many languages have successfully dealt with similar situations by simply allowing both but promoting only one in books and other documentation. Speaking of which, I'm on verge of signing with Addison Wesley Longman for delivering TDPL in April. Andrei  Oct 05 2008 Gregor Richards <Richards codu.org> writes: KennyTM~ wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". - - - The ".(" syntax makes me think more of something like this: void func(T, alias methodOfT, A...)(T obj, A args) { obj.(methodOfT)(args); } which I which I could do. If methodOfT was a string, I suppose I could use string mixins, but it pushes diagnostics about misnamed methods further in the template and requires adding quotes to the template parameter when instanciating. Argh, actually I once have a strong desire making f«T»(x); a valid construct, and to workaround that « and » can't be easily typed you could substitute it with f\<T\>(x); Yes. Trigraphs were such a good idea in C, let's bring them to D X_X - Gregor Richards  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Gregor Richards wrote: KennyTM~ wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". - - - The ".(" syntax makes me think more of something like this: void func(T, alias methodOfT, A...)(T obj, A args) { obj.(methodOfT)(args); } which I which I could do. If methodOfT was a string, I suppose I could use string mixins, but it pushes diagnostics about misnamed methods further in the template and requires adding quotes to the template parameter when instanciating. Argh, actually I once have a strong desire making f«T»(x); a valid construct, and to workaround that « and » can't be easily typed you could substitute it with f\<T\>(x); Yes. Trigraphs were such a good idea in C, let's bring them to D X_X - Gregor Richards It has been done with Pascal ( {comment} = (*comment*) } already. And the \ character is used to escape stuffs already, so no problem like writing "what??!" in C. And technically it's just a digraph, so at most it is only 67% as evil as trigraphs <g>. OK I'm just joking :p.  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. - - - The ".(" syntax makes me think more of something like this: void func(T, alias methodOfT, A...)(T obj, A args) { obj.(methodOfT)(args); } which I which I could do. If methodOfT was a string, I suppose I could use string mixins, but it pushes diagnostics about misnamed methods further in the template and requires adding quotes to the template parameter when instanciating. Given that methodOfT is an alias, there is no need for the parens. Andrei  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) -- snip --  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: KennyTM~ wrote: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) I believe it should be considered. At some point there was discussion on accepting a last parameter of delegate type outside the function parens. The idea was to allow user-defined code to define constructs similar to e.g. if and foreach. But I think that has many other problems (one of which is that the delegate can't reasonably specify parameters), so we can safely discount that as a problem. I'd want to give it a try. How do others feel about Template{arguments}? Andrei  Oct 05 2008 =?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes: Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? I’m not sure. It looks somehow better when nesting template arguments, but {} doesn’t quite fit in as some kind of argument in a C-style language like D, I think. Template{int}(); // Looks awkward.  Oct 05 2008 "Steven Schveighoffer" <schveiguy yahoo.com> writes: "Andrei Alexandrescu" wrote KennyTM~ wrote: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive"real"(joke); Positivereal(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) I believe it should be considered. At some point there was discussion on accepting a last parameter of delegate type outside the function parens. The idea was to allow user-defined code to define constructs similar to e.g. if and foreach. But I think that has many other problems (one of which is that the delegate can't reasonably specify parameters), so we can safely discount that as a problem. I'd want to give it a try. How do others feel about Template{arguments}? I like it much better than .() But I'd still vote for keeping !(), as I have no problems with it. -Steve  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Andrei Alexandrescu wrote: KennyTM~ wrote: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) I believe it should be considered. At some point there was discussion on accepting a last parameter of delegate type outside the function parens. The idea was to allow user-defined code to define constructs similar to e.g. if and foreach. Probably use func () { // some delegates } ? Just like what has been done to class invariants. But this may cause ambiguity if the 1st parameter of func is optional... But I think that has many other problems (one of which is that the delegate can't reasonably specify parameters), so we can safely discount that as a problem. I'd want to give it a try. How do others feel about Template{arguments}? Andrei  Oct 05 2008 Ary Borenszweig <ary esperanto.org.ar> writes: Andrei Alexandrescu escribió: KennyTM~ wrote: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) I believe it should be considered. At some point there was discussion on accepting a last parameter of delegate type outside the function parens. The idea was to allow user-defined code to define constructs similar to e.g. if and foreach. But I think that has many other problems (one of which is that the delegate can't reasonably specify parameters), so we can safely discount that as a problem. I'd want to give it a try. How do others feel about Template{arguments}? I thought no one read my post, now I see you are discussing it in another thread. :-P After I posted, I also remembered the possibility of allowing delegate invocation in a nicer way, and that conflicts with Foo{T}. :-(  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Ary Borenszweig wrote: Andrei Alexandrescu escribió: KennyTM~ wrote: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) I believe it should be considered. At some point there was discussion on accepting a last parameter of delegate type outside the function parens. The idea was to allow user-defined code to define constructs similar to e.g. if and foreach. But I think that has many other problems (one of which is that the delegate can't reasonably specify parameters), so we can safely discount that as a problem. I'd want to give it a try. How do others feel about Template{arguments}? I thought no one read my post, now I see you are discussing it in another thread. :-P After I posted, I also remembered the possibility of allowing delegate invocation in a nicer way, and that conflicts with Foo{T}. :-( I think we can drop that. Even if we allow that, there will be parens needed before the delegate body, at least for passing it arguments. Andrei  Oct 05 2008 Derek Parnell <derek psych.ward> writes: On Sun, 05 Oct 2008 09:41:28 -0500, Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? Not too shabby at all, really. -- Derek Parnell Melbourne, Australia skype: derek.j.parnell  Oct 05 2008 Leandro Lucarella <llucax gmail.com> writes: Andrei Alexandrescu, el 5 de octubre a las 09:41 me escribiste: I'd want to give it a try. How do others feel about Template{arguments}? I feel is unnecessary to change the template instantiation syntax. -- Leandro Lucarella (luca) | Blog colectivo: http://www.mazziblog.com.ar/blog/ ---------------------------------------------------------------------------- GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145 104C 949E BFB6 5F5A 8D05) ---------------------------------------------------------------------------- "CIRILO" Y "SIRACUSA" DE "SEÑORITA MAESTRA": UNO MUERTO Y OTRO PRESO -- Crónica TV  Oct 05 2008 "Chris R. Miller" <lordsauronthegreat gmail.com> writes: Andrei Alexandrescu wrote: KennyTM~ wrote: Andrei Alexandrescu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: -- snip -- Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". There was also Positive{real}(joke), with which I couldn't find an ambiguity. Ohhhh. Why isn't it considered then? (Suppose we already knew Positive is not a keyword and not preceded by the keywords struct, class, etc.) I believe it should be considered. At some point there was discussion on accepting a last parameter of delegate type outside the function parens. The idea was to allow user-defined code to define constructs similar to e.g. if and foreach. But I think that has many other problems (one of which is that the delegate can't reasonably specify parameters), so we can safely discount that as a problem. I'd want to give it a try. How do others feel about Template{arguments}? I distrust it greatly. Too similar to a code block. I still have a lot of contact with kids still being educated in programming, and that'd probably just confuse the heck out of 'em. No on {}! Keep the code block sacred! ;-)  Oct 05 2008 Benji Smith <dlanguage benjismith.net> writes: Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? At first glance, I like it better than !(), especially since it saves a character, making nested templates much nicer: auto map = new Map{T[], List{MyType}}(); // not too bad auto map = new Map!(T[], List!(MyType))(); // not too good auto map = new Map<T[], List<MyType>>(); // still my favorite It's too bad the shift operators can't be changed. Personally, I think the angle brackets are more valuable as a matched pair of enclosures. We could redefine the shift operators to be: --> RIGHT SHIFT <-- LEFT SHIFT -->> SIGNED RIGHT SHIFT And then the angle brackets could be coopted for templates. Of course, like I said before, I think it'd be especially cool if templates, as such, didn't exist. Instead, what if an ordinary function could return a Type, which could be used in a Type Constructor? Templates would vanish! It'd be CTFE, but for types instead of just for values. --benji  Oct 06 2008 KennyTM~ <kennytm gmail.com> writes: Benji Smith wrote: Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? At first glance, I like it better than !(), especially since it saves a character, making nested templates much nicer: auto map = new Map{T[], List{MyType}}(); // not too bad auto map = new Map!(T[], List!(MyType))(); // not too good auto map = new Map<T[], List<MyType>>(); // still my favorite It's too bad the shift operators can't be changed. Personally, I think the angle brackets are more valuable as a matched pair of enclosures. We could redefine the shift operators to be: --> RIGHT SHIFT <-- LEFT SHIFT -->> SIGNED RIGHT SHIFT And then the angle brackets could be coopted for templates. Of course, like I said before, I think it'd be especially cool if templates, as such, didn't exist. Instead, what if an ordinary function could return a Type, which could be used in a Type Constructor? Templates would vanish! It'd be CTFE, but for types instead of just for values. --benji Another problem with < is that, if you're not confident that Map is really a template identifier, you'll have the ambiguity whether < is an open bracket or a less than sign. int x, y, w, z; writefln(x<y,w>(z)); // currently compiles.  Oct 06 2008 =?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes: Benji Smith wrote: Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? At first glance, I like it better than !(), especially since it saves a character, making nested templates much nicer: auto map = new Map{T[], List{MyType}}(); // not too bad auto map = new Map!(T[], List!(MyType))(); // not too good auto map = new Map<T[], List<MyType>>(); // still my favorite It's too bad the shift operators can't be changed. Personally, I think the angle brackets are more valuable as a matched pair of enclosures. We could redefine the shift operators to be: --> RIGHT SHIFT <-- LEFT SHIFT -->> SIGNED RIGHT SHIFT And then the angle brackets could be coopted for templates. No way! :( ’em pointed brackets are way too pointy. I like having parenthesis for templates.  Oct 06 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Alexander Pnek wrote: Benji Smith wrote: Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? At first glance, I like it better than !(), especially since it saves a character, making nested templates much nicer: auto map = new Map{T[], List{MyType}}(); // not too bad auto map = new Map!(T[], List!(MyType))(); // not too good auto map = new Map<T[], List<MyType>>(); // still my favorite It's too bad the shift operators can't be changed. Personally, I think the angle brackets are more valuable as a matched pair of enclosures. We could redefine the shift operators to be: --> RIGHT SHIFT <-- LEFT SHIFT -->> SIGNED RIGHT SHIFT And then the angle brackets could be coopted for templates. No way! :( em pointed brackets are way too pointy. I like having parenthesis for templates. Well another problem is we'd need to redefine the less-than and greater-than operators too. Andrei  Oct 06 2008 Benji Smith <dlanguage benjismith.net> writes: Andrei Alexandrescu wrote: Alexander Pnek wrote: Benji Smith wrote: Andrei Alexandrescu wrote: I'd want to give it a try. How do others feel about Template{arguments}? At first glance, I like it better than !(), especially since it saves a character, making nested templates much nicer: auto map = new Map{T[], List{MyType}}(); // not too bad auto map = new Map!(T[], List!(MyType))(); // not too good auto map = new Map<T[], List<MyType>>(); // still my favorite It's too bad the shift operators can't be changed. Personally, I think the angle brackets are more valuable as a matched pair of enclosures. We could redefine the shift operators to be: --> RIGHT SHIFT <-- LEFT SHIFT -->> SIGNED RIGHT SHIFT And then the angle brackets could be coopted for templates. No way! :( em pointed brackets are way too pointy. I like having parenthesis for templates. Well another problem is we'd need to redefine the less-than and greater-than operators too. Andrei Oh yeah. I don't know how I missed that. <smacks forehead> --benji  Oct 07 2008 Lionello Lunesu <lio lunesu.remove.com> writes: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Positive(real)(joke); Does D have a use for # at the moment? I'm surprised it wasn't used for array length instead of . L.  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Lionello Lunesu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Positive(real)(joke); Does D have a use for # at the moment? I'm surprised it wasn't used for array length instead of . L. Yes. #line. I think makes sense because in RegExp matches the end of string (or end of line).  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Lionello Lunesu wrote: Michel Fortin wrote: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Positive(real)(joke); Does D have a use for # at the moment? I'm surprised it wasn't used for array length instead of . I considered # too. It's a bit "fat", but you know what, I'd rather deal with a fella with a slight weight problem than one who's shouting all the time. Andrei  Oct 05 2008 Leandro Lucarella <llucax gmail.com> writes: Michel Fortin, el 5 de octubre a las 03:53 me escribiste: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Hum, I don't think we have much choice, it'll have to be something in this lot: Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". I think this is exactly the point. ".(" don't look that much better than "!(" (if better at all), so why should a new syntax variation should be introduced to the language with that small (and arguable) benefit? "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. And if it's introduced, you'll have to read a lot of "!(" anyways, is not that you will be solving any problems, because all D1-ported code (and code of people who like "!(" better) will use it instead of ".(" (unless "!(" stops working, in which case it's really dumb to make D1 incompatible with D2 for this such a small aesthetic issue). So you'll just make things whorse. -1 for ".(" PS: I wont use Positive!() either ;) -- Leandro Lucarella (luca) | Blog colectivo: http://www.mazziblog.com.ar/blog/ ---------------------------------------------------------------------------- GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145 104C 949E BFB6 5F5A 8D05) ---------------------------------------------------------------------------- Es mas posible, que un elefante maneje un cero km a que un camello habite un departamento de un ambiente. -- Peperino Pómoro  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Leandro Lucarella wrote: Michel Fortin, el 5 de octubre a las 03:53 me escribiste: On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> said: I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Positive!(real)(joke); Positive.(real)(joke); Positive#(real)(joke); Positive (real)(joke); Positive&(real)(joke); Positive(real)(joke); Positive´(real)(joke); Positive^(real)(joke); Positive¨(real)(joke); Positive\(real)(joke); Anything else I forgot? Or we could use special delimiter characters: Positive<real>(joke); Positive“real”(joke); Positive«real»(joke); Positive#real (joke); Each having its own problem though. My preference still goes to "!(". I think this is exactly the point. ".(" don't look that much better than "!(" (if better at all), so why should a new syntax variation should be introduced to the language with that small (and arguable) benefit? I think it's reasonable to say that The Sad Pirate won't make it. I hope a different fate awaits for unparenthesized instantiations. "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. Ugly or not, enumerated symbols were manifest constants to begin with. That's kinda hard to argue against because it's a sheer fact. And if it's introduced, you'll have to read a lot of "!(" anyways, is not that you will be solving any problems, because all D1-ported code (and code of people who like "!(" better) will use it instead of ".(" (unless "!(" stops working, in which case it's really dumb to make D1 incompatible with D2 for this such a small aesthetic issue). So you'll just make things whorse. -1 for ".(" PS: I wont use Positive!() either ;) Would you use Bounded? It takes a type, a minimum, and a maximum. Andrei  Oct 05 2008 Jason House <jason.james.house gmail.com> writes: Andrei Alexandrescu wrote: Leandro Lucarella wrote: "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. Ugly or not, enumerated symbols were manifest constants to begin with. That's kinda hard to argue against because it's a sheer fact. Even before we expanded enums, I hated how there was no toString() for enum types. Walter explained this was because bit masks made it difficult. I like using enums for a restricted set of options. That'd allow the compiler to provide toString and catch misuse in switch statements... Including when I add or remove allowed values.  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Jason House wrote: Andrei Alexandrescu wrote: Leandro Lucarella wrote: "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. That's kinda hard to argue against because it's a sheer fact. Even before we expanded enums, I hated how there was no toString() for enum types. defineEnum in std.typecons provides that (and parsing too). Walter explained this was because bit masks made it difficult. I like using enums for a restricted set of options. That'd allow the compiler to provide toString and catch misuse in switch statements... Including when I add or remove allowed values. Walter hasn't gotten around to implementing the final switch statement, which does exactly as you mention. For the interested I paste the relevant section in TDPL - hot off the oven: \section{The \protect\cc{final switch} Statement} It is often the case that switch is meant to handle all possible cases, such as all values of a small integer or of an enumerated type. If, during maintenance, the number of cases is changing, all of the dependent switch statements suddenly fall out of sync and must be manually searched for and modified. For such situations, the \cc{final switch} statement comes in handy: \begin{D} enum deviceStatusMask = 3; ... void Handle(uint x) { final switch (x & deviceStatusMask) { case 0: ... case 1: ... case 2: ... case 3: ... } } \end{D} Should the value of mask change later to, say, 7, attempting to recompile Handle is met with refusal on the following grounds: \begin{lstlisting}[language=sys] Error: final switch statement must handle all values \end{lstlisting} The \cc{final switch} statement looks at the shape of its controlling expression to figure out the bounds, as follows: \begin{itemize*} \item If \meta{expression} is \metai{e} & \metaii{e} and one of \metai{e} and \metaii{e} evaluates to a positive compile-time value c , then the range is determined as 0 up to (and including) c . \item If \meta{expression} is \metai{e} \cc{\%} \metaii{e} and \metaii{e} evaluates to a positive compile-time value c , then the range is determined as 0 up to (and not including) \cc{c}. \item If \meta{expression} is an unsigned right shift (either \metai{e} \cc{>>} \metaii{e} operating on unsigned numbers, or \metai{e} \cc{>>>} \metaii{e}), and if \metaii{e} evaluates to a compile-time value c , then the range is determined as 0 up to (and not including) \cc{1 << (8 *} \metai{e}\cc{.sizeof - c)}.%>> \item If \meta{expression} is the assignment variant of one of the above ( &= , \cc{\%=} etc.) then the range the same as for the non-assignment variant. \item If \meta{expression} is an enumerated type, the range is the entire set of values of the enumerated type. \item Otherwise, the range is e.min up to and including e.max . (The min and max constants are defined for all numeric types.) \end{itemize*} There are quite a few other cases in which the range of an expression could be effectively determined, but \cc{final switch} only handles the usual ones. A default label is allowed inside a \cc{final switch} statement and practically turns off all checks because it ensures \emph{de facto} that all values are handled. Andrei  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Denis Koroskin wrote: On Mon, 06 Oct 2008 04:03:08 +0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: Jason House wrote: Andrei Alexandrescu wrote: Leandro Lucarella wrote: "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. That's kinda hard to argue against because it's a sheer fact. for enum types. defineEnum in std.typecons provides that (and parsing too). Walter explained this was because bit masks made it difficult. I like using enums for a restricted set of options. That'd allow the compiler to provide toString and catch misuse in switch statements... Including when I add or remove allowed values. Walter hasn't gotten around to implementing the final switch statement, which does exactly as you mention. For the interested I paste the relevant section in TDPL - hot off the oven: \section{The \protect\cc{final switch} Statement} It is often the case that switch is meant to handle all possible cases, such as all values of a small integer or of an enumerated type. If, during maintenance, the number of cases is changing, all of the dependent switch statements suddenly fall out of sync and must be manually searched for and modified. For such situations, the \cc{final switch} statement comes in handy: \begin{D} enum deviceStatusMask = 3; ... void Handle(uint x) { final switch (x & deviceStatusMask) { case 0: ... case 1: ... case 2: ... case 3: ... } } \end{D} Should the value of mask change later to, say, 7, attempting to recompile Handle is met with refusal on the following grounds: \begin{lstlisting}[language=sys] Error: final switch statement must handle all values \end{lstlisting} The \cc{final switch} statement looks at the shape of its controlling expression to figure out the bounds, as follows: \begin{itemize*} \item If \meta{expression} is \metai{e} & \metaii{e} and one of \metai{e} and \metaii{e} evaluates to a positive compile-time value c , then the range is determined as 0 up to (and including) c . \item If \meta{expression} is \metai{e} \cc{\%} \metaii{e} and \metaii{e} evaluates to a positive compile-time value c , then the range is determined as 0 up to (and not including) \cc{c}. \item If \meta{expression} is an unsigned right shift (either \metai{e} \cc{>>} \metaii{e} operating on unsigned numbers, or \metai{e} \cc{>>>} \metaii{e}), and if \metaii{e} evaluates to a compile-time value c , then the range is determined as 0 up to (and not including) \cc{1 << (8 *} \metai{e}\cc{.sizeof - c)}.%>> \item If \meta{expression} is the assignment variant of one of the above ( &= , \cc{\%=} etc.) then the range the same as for the non-assignment variant. \item If \meta{expression} is an enumerated type, the range is the entire set of values of the enumerated type. \item Otherwise, the range is e.min up to and including e.max . (The min and max constants are defined for all numeric types.) \end{itemize*} There are quite a few other cases in which the range of an expression could be effectively determined, but \cc{final switch} only handles the usual ones. A default label is allowed inside a \cc{final switch} statement and practically turns off all checks because it ensures \emph{de facto} that all values are handled. Andrei Final switch is great, but why allow default case in it? Putting the default case into the final switch effectively transforms it into a regular one discarding all of its benefits. What's the point? Good point. I was thinking of making maintenance easier: sometimes you decide to insert a default. Then you'd need to wipe the "final" too. Then you comment out the default. You'd need to add the "final" back (and you may forget). And so on. Andrei  Oct 05 2008 Leandro Lucarella <llucax gmail.com> writes: Andrei Alexandrescu, el 5 de octubre a las 17:45 me escribiste: "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. Ugly or not [...] But this thread started about uglyness, and enum SOMETHING = 1 is plain ugly =) And if it's introduced, you'll have to read a lot of "!(" anyways, is not that you will be solving any problems, because all D1-ported code (and code of people who like "!(" better) will use it instead of ".(" (unless "!(" stops working, in which case it's really dumb to make D1 incompatible with D2 for this such a small aesthetic issue). So you'll just make things whorse. -1 for ".(" PS: I wont use Positive!() either ;) Would you use Bounded? It takes a type, a minimum, and a maximum. I don't make much numeric/math programming, but it sounds much more useful than Positive. -- Leandro Lucarella (luca) | Blog colectivo: http://www.mazziblog.com.ar/blog/ ---------------------------------------------------------------------------- GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145 104C 949E BFB6 5F5A 8D05) ---------------------------------------------------------------------------- You look so tired-unhappy, bring down the government, they don't, they don't speak for us.  Oct 06 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Simen Kjaeraas wrote: Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: Leandro Lucarella wrote: "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. Ugly or not, enumerated symbols were manifest constants to begin with. That's kinda hard to argue against because it's a sheer fact. All bears are animals, so lets call all animals bears. See where this is wrong? The correct reasoning to apply is, if you see a white bear, would you call it a different way? Andrei  Oct 08 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Simen Kjaeraas wrote: Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: Simen Kjaeraas wrote: Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: Leandro Lucarella wrote: "enum" as the way to declare manifest constants were much more ugly than "!(", and most of the people were against it. I don't see why ".(" should be introduced. Ugly or not, enumerated symbols were manifest constants to begin with. That's kinda hard to argue against because it's a sheer fact. All bears are animals, so lets call all animals bears. See where this is wrong? The correct reasoning to apply is, if you see a white bear, would you call it a different way? Andrei Mayhaps. But to me, a manifest constant is not just a bear of a different color, but possibly one with six legs, a prehensile tail, bat wings, and riding a helicopter. And I'm pretty sure I would not classify that as a bear, even if it still had fur and powerful jaws, and would make for a fun teddy. But you just agreed that enum is a manifest constant. Andrei  Oct 08 2008 Christopher Wright <dhasenan gmail.com> writes: Andrei Alexandrescu wrote: Christopher Wright wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Andrei! I agree with Mr. Martin II: colon might be an unambiguous option, and for qwerty keyboards, you don't have to switch shift keys. (I use dvorak, so it'd be slightly more awkward, but still a fair bit more easier than a bang.) Also, colon's taller than dot, so it's easier to see.  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Christopher Wright wrote: Andrei Alexandrescu wrote: Christopher Wright wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Andrei! I agree with Mr. Martin II: colon might be an unambiguous option, and for qwerty keyboards, you don't have to switch shift keys. (I use dvorak, so it'd be slightly more awkward, but still a fair bit more easier than a bang.) Also, colon's taller than dot, so it's easier to see. How to distinguish a label from a template then? Should I print X or Y in the following code? import std.stdio; class X { static void print () { writeln("Y"); } } template T (x) { void print () { writeln("X"); } } void main () { T:(X).print(); }  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: KennyTM~ wrote: Christopher Wright wrote: Andrei Alexandrescu wrote: Christopher Wright wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Andrei! I agree with Mr. Martin II: colon might be an unambiguous option, and for qwerty keyboards, you don't have to switch shift keys. (I use dvorak, so it'd be slightly more awkward, but still a fair bit more easier than a bang.) Also, colon's taller than dot, so it's easier to see. How to distinguish a label from a template then? Should I print X or Y in the following code? import std.stdio; class X { static void print () { writeln("Y"); } } template T (x) { void print () { writeln("X"); } } void main () { T:(X).print(); } Heh. So this change should come together with abolishing goto :o). Andrei  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Adam D. Ruppe wrote: On Sun, Oct 05, 2008 at 09:29:37AM -0500, Andrei Alexandrescu wrote: Heh. So this change should come together with abolishing goto :o). Noooooooooooooooooooooooooo! No worries. Goto to Walter is what money is to Swiss banks. :o) Andrei P.S. I have one goto in my code too.  Oct 05 2008 Sergey Gromov <snake.scaly gmail.com> writes: Sun, 05 Oct 2008 09:44:39 -0500, Andrei Alexandrescu wrote: Adam D. Ruppe wrote: On Sun, Oct 05, 2008 at 09:29:37AM -0500, Andrei Alexandrescu wrote: Heh. So this change should come together with abolishing goto :o). Noooooooooooooooooooooooooo! No worries. Goto to Walter is what money is to Swiss banks. :o) Andrei P.S. I have one goto in my code too. Maybe not gotos, but labelled breaks and continues might come in very handy sometimes.  Oct 06 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Christopher Wright wrote: Andrei Alexandrescu wrote: Christopher Wright wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't favor "." any more than the next guy, but I am glad there is awareness of how unfit a choice "!" is. If you have any ideas, please post them! Ah! I! Exclaimed! Again! Andrei! I agree with Mr. Martin II: colon might be an unambiguous option, and for qwerty keyboards, you don't have to switch shift keys. (I use dvorak, so it'd be slightly more awkward, but still a fair bit more easier than a bang.) Also, colon's taller than dot, so it's easier to see. I love the colon. It would be my first preference in fact. Walter wants to do parsing without symbol tables, and I think that's a worthy goal. How to parse this? a = b?c?d:(e):f:(g); Hmmmm... Andrei  Oct 05 2008 Lester L. Martin II <lestermartin92 gmail.com> writes: Christopher Wright Wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. Not only that, but typing it is annoying. First you need to put the right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't like the idea of '.' either. I currently like the '!'. I am not the best at templates and making templates similar to function call (looks like each other) would make templating so much harder. It should have something that lets you know right off that it's a template. Do you really want a template looking like a function. That has potential to get confusing as your brain argues just at a glance over if a function is called and supplied parameters most functions wouldn't accept or is it a template and the list afterwards is the stuff supplied to the function (I don't remember ever passing to a function (real, real) so looking at that and having my brain think about "OH!" that's why the function call isn't working and the code won't compile, it's because you were dumb enough to supply types instead of values is not very intuitive). I like the '!' and don't look forward to seeing it changed but if it was to be changed, I'd prefer it not to be a '.' but maybe something along the line of a colon (':') because it doesn't show a function call. I can't remember ever using a ':' in my code except for that import this : function2 type stuff so I think this would be a good idea versus the '.' Lester L. Martin II  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Lester L. Martin II wrote: Christopher Wright Wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. right pinky on the shift key, which is a long reach; then you need to put the left pinky on the 1 key, which is a long reach. Then you need to move your left pinky all the way back to the left shift key, which is a short reach, and move your right ring finger up to the 9 key. It's a lot of reaching and back and forth. But I don't favor '.' since it's already used. I don't like the idea of '.' either. I currently like the '!'. I am not the best at templates and making templates similar to function call (looks like each other) would make templating so much harder. It should have something that lets you know right off that it's a template. Do you really want a template looking like a function. You already have a template looking like a function. It works so well you don't even care, and consequently are not put off by it. That has potential to get confusing as your brain argues just at a glance over if a function is called and supplied parameters most functions wouldn't accept or is it a template and the list afterwards is the stuff supplied to the function (I don't remember ever passing to a function (real, real) so looking at that and having my brain think about "OH!" that's why the function call isn't working and the code won't compile, it's because you were dumb enough to supply types instead of values is not very intuitive). I like the '!' and don't look forward to seeing it changed but if it was to be changed, I'd prefer it not to be a '.' but maybe something along the line of a colon (':') because it doesn't show a function call. I can't remember ever using a ':' in my code except for that import this : function2 type stuff so I think this would be a good idea versus the '.' I prefer the colon too, if ambiguity with ?: can be taken care of. Andrei  Oct 05 2008 Walter Bright <newshound1 digitalmars.com> writes: Andrei Alexandrescu wrote: I prefer the colon too, if ambiguity with ?: can be taken care of. There's also an ambiguity with statement labels: L1: (*foo)();  Oct 05 2008 Tom S <h3r3tic remove.mat.uni.torun.pl> writes: I don't like using "." for template instantiation. The tokenizer in my eyes clearly separates constructs at ".". On the other hand, "!" as a graphical character is more 'filled', thus doesn't separate the identifier and arguments that much visually. foo.bar <- obviously member access foo.(bar, baz) <- multiple member access? ... It looks like it should yield a tuple containing bar and baz :P foo!(bar, baz) <- distinct, no issue. As for the other queries, I like how template instantiation stands out right now with the exclamation mark. I would not like to have compile-time and run-time merged visually in code. And I don't forget to put the exclamation mark there when programming templates. Let's also keep in mind what Ary said, that using "." will cause problems for IDEs. What's the point in pretending that run-time is the same as compile-time? You can't instantiate compile-time constructs with run-time arguments, the costs are very different, too. Heck, when I see too many "!" in the code, it indicates that there may be a design issue and some massive bloat involved. I would not like this additional insight into the code removed from my eyes. -- Tomasz Stachowiak http://h3.team0xf.com/ h3/h3r3tic on #D freenode  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Tom S wrote: I don't like using "." for template instantiation. The tokenizer in my eyes clearly separates constructs at ".". On the other hand, "!" as a graphical character is more 'filled', thus doesn't separate the identifier and arguments that much visually. foo.bar <- obviously member access foo.(bar, baz) <- multiple member access? I hear you. I would have chosen the colon if it wasn't ambiguous. ... It looks like it should yield a tuple containing bar and baz :P foo!(bar, baz) <- distinct, no issue. Looks great until you have twenty or thirty of these on a code screen. Then you're like, boy this is one ugly language. Believe me, I *tried* to put up with it. As for the other queries, I like how template instantiation stands out right now with the exclamation mark. I wouldn't mind it either if I only had few of those. I would not like to have compile-time and run-time merged visually in code. You already do in template argument deduction. Compile-time evaluation erodes the distinction further. The times go against the style of coding that separates compile-time stuff from run-time stuff. And I don't forget to put the exclamation mark there when programming templates. Ok. Let's also keep in mind what Ary said, that using "." will cause problems for IDEs. No it won't. What's the point in pretending that run-time is the same as compile-time? Because you shouldn't care. You can't instantiate compile-time constructs with run-time arguments, the costs are very different, too. Heck, when I see too many "!" in the code, it indicates that there may be a design issue and some massive bloat involved. I would not like this additional insight into the code removed from my eyes. Conversely, if you have too few of those, I come and say you're doing too much manual work. Andrei  Oct 05 2008 Tom S <h3r3tic remove.mat.uni.torun.pl> writes: Andrei Alexandrescu wrote: ... It looks like it should yield a tuple containing bar and baz :P foo!(bar, baz) <- distinct, no issue. Looks great until you have twenty or thirty of these on a code screen. Then you're like, boy this is one ugly language. Believe me, I *tried* to put up with it. Hm, I didn't think so when working on ctrace or Bind... I could similarly say that parentheses look bad and we should change them to something else because a screenful of them looks ugly when calling lots of functions. I would not like to have compile-time and run-time merged visually in code. a bad thing that some functions will be running at compile-time 'behind my back'. I just wouldn't like the visual distinction between normal function calls and template evaluations to go away as long as they are fundamentally different. You already do in template argument deduction. Point. But for a different purpose - eliminating a lot of redundant code and making some meta programming feasible. It's a bit different from pretending template evaluation is like function calls. The times go against the style of coding that separates compile-time stuff from run-time stuff. The times? I'd say that these times have already been ;) You may not have this distinction e.g. in Lisp. But if you consider that D only has one 'compile time', while you could freely operate on anything at any time in Lisp, it makes more sense to have the compile-time phase stand out a bit. Especially because template code is still very different than normal D code (it's functional and memoized, after all). I'd be tempted to change my mind here if D had more meta-facilities, but at the current state of things, I'd say that the 'times' are pretty stagnant for D. Let's also keep in mind what Ary said, that using "." will cause problems for IDEs. No it won't. Would you elaborate on this? I'd rather believe Ary if nothing else is provided to your point. Ary is the creator of the most advanced IDE for D as far as I know. What's the point in pretending that run-time is the same as compile-time? Because you shouldn't care. I wish I could! But then, I can't process types at run-time. You can't instantiate compile-time constructs with run-time arguments, the costs are very different, too. Heck, when I see too many "!" in the code, it indicates that there may be a design issue and some massive bloat involved. I would not like this additional insight into the code removed from my eyes. Conversely, if you have too few of those, I come and say you're doing too much manual work. Or the code is a 'normal' module that mixes some meta constructs and standard non-parametrized stuff. The "!" may be very common in modules such as std.algorithm, but you won't see as many in the usual stuff, like, most of Tango. -- Tomasz Stachowiak http://h3.team0xf.com/ h3/h3r3tic on #D freenode  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Tom S wrote: Andrei Alexandrescu wrote: ... It looks like it should yield a tuple containing bar and baz :P foo!(bar, baz) <- distinct, no issue. Looks great until you have twenty or thirty of these on a code screen. Then you're like, boy this is one ugly language. Believe me, I *tried* to put up with it. Hm, I didn't think so when working on ctrace or Bind... I could similarly say that parentheses look bad and we should change them to something else because a screenful of them looks ugly when calling lots of functions. You couldn't because f(a, b) is already used in math for function invocation. "Word!" is already used. For shouting that is. I would not like to have compile-time and run-time merged visually in code. a bad thing that some functions will be running at compile-time 'behind my back'. I just wouldn't like the visual distinction between normal function calls and template evaluations to go away as long as they are fundamentally different. They are and they stay different. One oughtn't be shouting at you though. You already do in template argument deduction. Point. But for a different purpose - eliminating a lot of redundant code and making some meta programming feasible. It's a bit different from pretending template evaluation is like function calls. Well parens are already used for more than function calls and nobody seems to mind. The times go against the style of coding that separates compile-time stuff from run-time stuff. The times? I'd say that these times have already been ;) You may not have this distinction e.g. in Lisp. But if you consider that D only has one 'compile time', while you could freely operate on anything at any time in Lisp, it makes more sense to have the compile-time phase stand out a bit. Especially because template code is still very different than normal D code (it's functional and memoized, after all). I'd be tempted to change my mind here if D had more meta-facilities, but at the current state of things, I'd say that the 'times' are pretty stagnant for D. More meta-facilities are coming D's way, not less. As far as Lisp is concerned, at least in Scheme (I forgot how you do it in Lisp) macro invocation isn't distinguished in any way. For example "and" in (and a b c) is a macro. Let's also keep in mind what Ary said, that using "." will cause problems for IDEs. No it won't. Would you elaborate on this? I'd rather believe Ary if nothing else is provided to your point. Ary is the creator of the most advanced IDE for D as far as I know. A template name without arguments has no members, except inside the very template definition, when you'd rarely use it. What's the point in pretending that run-time is the same as compile-time? Because you shouldn't care. I wish I could! But then, I can't process types at run-time. Well then here's the distinction that you wanted :o). You can't instantiate compile-time constructs with run-time arguments, the costs are very different, too. Heck, when I see too many "!" in the code, it indicates that there may be a design issue and some massive bloat involved. I would not like this additional insight into the code removed from my eyes. Conversely, if you have too few of those, I come and say you're doing too much manual work. Or the code is a 'normal' module that mixes some meta constructs and standard non-parametrized stuff. The "!" may be very common in modules such as std.algorithm, but you won't see as many in the usual stuff, like, most of Tango. By and large we'd want seamless and smooth integration of various styles and techniques, wouldn't we? Shouting doesn't fit into this. Andrei  Oct 05 2008 Ary Borenszweig <ary esperanto.org.ar> writes: Andrei Alexandrescu escribió: Tom S wrote: Andrei Alexandrescu wrote: ... It looks like it should yield a tuple containing bar and baz :P foo!(bar, baz) <- distinct, no issue. Looks great until you have twenty or thirty of these on a code screen. Then you're like, boy this is one ugly language. Believe me, I *tried* to put up with it. Hm, I didn't think so when working on ctrace or Bind... I could similarly say that parentheses look bad and we should change them to something else because a screenful of them looks ugly when calling lots of functions. You couldn't because f(a, b) is already used in math for function invocation. "Word!" is already used. For shouting that is. I would not like to have compile-time and run-time merged visually in code. as a bad thing that some functions will be running at compile-time 'behind my back'. I just wouldn't like the visual distinction between normal function calls and template evaluations to go away as long as they are fundamentally different. They are and they stay different. One oughtn't be shouting at you though. You already do in template argument deduction. Point. But for a different purpose - eliminating a lot of redundant code and making some meta programming feasible. It's a bit different from pretending template evaluation is like function calls. Well parens are already used for more than function calls and nobody seems to mind. The times go against the style of coding that separates compile-time stuff from run-time stuff. The times? I'd say that these times have already been ;) You may not have this distinction e.g. in Lisp. But if you consider that D only has one 'compile time', while you could freely operate on anything at any time in Lisp, it makes more sense to have the compile-time phase stand out a bit. Especially because template code is still very different than normal D code (it's functional and memoized, after all). I'd be tempted to change my mind here if D had more meta-facilities, but at the current state of things, I'd say that the 'times' are pretty stagnant for D. More meta-facilities are coming D's way, not less. As far as Lisp is concerned, at least in Scheme (I forgot how you do it in Lisp) macro invocation isn't distinguished in any way. For example "and" in (and a b c) is a macro. Let's also keep in mind what Ary said, that using "." will cause problems for IDEs. No it won't. Would you elaborate on this? I'd rather believe Ary if nothing else is provided to your point. Ary is the creator of the most advanced IDE for D as far as I know. A template name without arguments has no members, except inside the very template definition, when you'd rarely use it. I don't think it's because of that, but the IDE could check that if what's before the "." is a template, suggest instantiation. So after thinking about it again, I agree with you that it won't be problematic. Anyway, I don't like the .() syntax. :-P  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Ary Borenszweig wrote: Andrei Alexandrescu escribió: Tom S wrote: Andrei Alexandrescu wrote: ... It looks like it should yield a tuple containing bar and baz :P foo!(bar, baz) <- distinct, no issue. Looks great until you have twenty or thirty of these on a code screen. Then you're like, boy this is one ugly language. Believe me, I *tried* to put up with it. Hm, I didn't think so when working on ctrace or Bind... I could similarly say that parentheses look bad and we should change them to something else because a screenful of them looks ugly when calling lots of functions. You couldn't because f(a, b) is already used in math for function invocation. "Word!" is already used. For shouting that is. I would not like to have compile-time and run-time merged visually in code. as a bad thing that some functions will be running at compile-time 'behind my back'. I just wouldn't like the visual distinction between normal function calls and template evaluations to go away as long as they are fundamentally different. They are and they stay different. One oughtn't be shouting at you though. You already do in template argument deduction. Point. But for a different purpose - eliminating a lot of redundant code and making some meta programming feasible. It's a bit different from pretending template evaluation is like function calls. Well parens are already used for more than function calls and nobody seems to mind. The times go against the style of coding that separates compile-time stuff from run-time stuff. The times? I'd say that these times have already been ;) You may not have this distinction e.g. in Lisp. But if you consider that D only has one 'compile time', while you could freely operate on anything at any time in Lisp, it makes more sense to have the compile-time phase stand out a bit. Especially because template code is still very different than normal D code (it's functional and memoized, after all). I'd be tempted to change my mind here if D had more meta-facilities, but at the current state of things, I'd say that the 'times' are pretty stagnant for D. More meta-facilities are coming D's way, not less. As far as Lisp is concerned, at least in Scheme (I forgot how you do it in Lisp) macro invocation isn't distinguished in any way. For example "and" in (and a b c) is a macro. Let's also keep in mind what Ary said, that using "." will cause problems for IDEs. No it won't. Would you elaborate on this? I'd rather believe Ary if nothing else is provided to your point. Ary is the creator of the most advanced IDE for D as far as I know. A template name without arguments has no members, except inside the very template definition, when you'd rarely use it. I don't think it's because of that, but the IDE could check that if what's before the "." is a template, suggest instantiation. So after thinking about it again, I agree with you that it won't be problematic. Anyway, I don't like the .() syntax. :-P And why should I care? I got superdan's drunken vote! :oD Andrei  Oct 05 2008 Tom S <h3r3tic remove.mat.uni.torun.pl> writes: Andrei Alexandrescu wrote: By and large we'd want seamless and smooth integration of various styles and techniques, wouldn't we? Shouting doesn't fit into this. Is that a phobia? :P -- Tomasz Stachowiak http://h3.team0xf.com/ h3/h3r3tic on #D freenode  Oct 05 2008 Benji Smith <dlanguage benjismith.net> writes: Tom S wrote: The "!" may be very common in modules such as std.algorithm, but you won't see as many in the usual stuff, like, most of Tango. Unfortunately, any code that uses strings (and wants to correctly handle all three character types) is required to use templates. So there's a lot more template code out there than there ought to be. --benji  Oct 06 2008 downs <default_357-line yahoo.de> writes: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. FWIW: I write large volumes of template code and I like the ! just fine. Andrei  Oct 05 2008 Peter Modzelewski <peter.modzelewski gmail.com> writes: downs pisze: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. FWIW: I write large volumes of template code and I like the ! just fine. Same here! Piotr Modzelewski keyer team0xf.com  Oct 05 2008 Gregor Richards <Richards codu.org> writes: downs wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. FWIW: I write large volumes of template code and I like the ! just fine. Don't take this endorsement lightly. When downs says he writes large volumes of template code, he means volumes in the literary sense: You could fill a fairly-large bookshelf with his tomes of template code. - Gregor Richards  Oct 05 2008 Lars Ivar Igesund <larsivar igesund.net> writes: Gregor Richards wrote: downs wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. FWIW: I write large volumes of template code and I like the ! just fine. Don't take this endorsement lightly. When downs says he writes large volumes of template code, he means volumes in the literary sense: You could fill a fairly-large bookshelf with his tomes of template code. I'm sure you mean not so large tomes, but with very long lines? -- Lars Ivar Igesund blog at http://larsivi.net DSource, #d.tango & #D: larsivi Dancing the Tango  Oct 05 2008 downs <default_357-line yahoo.de> writes: Lars Ivar Igesund wrote: Gregor Richards wrote: downs wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. volumes of template code, he means volumes in the literary sense: You could fill a fairly-large bookshelf with his tomes of template code. I'm sure you mean not so large tomes, but with very long lines? That's why you need the bookshelf. It's not so much the length of the tomes, it's the width :)  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Lars Ivar Igesund wrote: Gregor Richards wrote: downs wrote: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. volumes of template code, he means volumes in the literary sense: You could fill a fairly-large bookshelf with his tomes of template code. I'm sure you mean not so large tomes, but with very long lines? If you strip all the \n's you'll get a very long line. /joke (unless you've used a #line)  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Jarrett Billingsley wrote: On Sun, Oct 5, 2008 at 12:06 AM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Long argument short: I don't mind !() at all, and changing it to .() seems like a pointless pedanticism. But since you're the one suggesting it, there's a very good chance of it getting into the language (if it hasn't already), so there's not much use arguing against it. It won't make it unless others try it and find it palatable too. But please let's try it first. Also, I'm much less keen on introducing .() than on ousting !(), which I believe was a very poor choice. So I suggest we all explore other syntax choices until we find something that we can show to the world with a straight face. Andrei  Oct 05 2008 Lars Ivar Igesund <larsivar igesund.net> writes: Andrei Alexandrescu wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. I don't dislike !() and don't want .() -- Lars Ivar Igesund blog at http://larsivi.net DSource, #d.tango & #D: larsivi Dancing the Tango  Oct 05 2008 "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes: On Sun, Oct 5, 2008 at 8:13 PM, Denis Koroskin <2korden gmail.com> wrote: Final switch is great, but why allow default case in it? Putting the default case into the final switch effectively transforms it into a regular one discarding all of its benefits. What's the point? I was going to ask the same thing.  Oct 05 2008 Benji Smith <dlanguage benjismith.net> writes: Andrei Alexandrescu wrote: One morning I woke up with the sudden realization of what the problem was: the shouting. Here's my (nutty) opinion: Neither the "!" nor the "." really want to be there. I think the language really *wants* to be using a bare set of parens for templates. Because the language actually wants templates and functions to converge. Instead of a special-case syntax for templates, and a set of special rules for CTFE, and a whole set of parallel "static" statements (if, else, foreach) and a special compile-type-only type construct (tuples), just let D be D, either at runtime or compile type. If a function could return a Type, and if that type could be used in a Type Constructor, then you'd have all the magic template sauce you'd need, and templates could happily converge themselves with regular functions. Hey! I told you it was going to be nutty!!! <g> --benji  Oct 06 2008 Benji Smith <dlanguage benjismith.net> writes: Simen Kjaeraas wrote: On Wed, 08 Oct 2008 22:02:18 +0200, Simen Kjaeraas <simen.kjaras gmail.com> wrote: On Mon, 06 Oct 2008 12:39:29 +0200, Benji Smith <dlanguage benjismith.net> wrote: Andrei Alexandrescu wrote: One morning I woke up with the sudden realization of what the problem was: the shouting. Here's my (nutty) opinion: Neither the "!" nor the "." really want to be there. I think the language really *wants* to be using a bare set of parens for templates. Because the language actually wants templates and functions to converge. Instead of a special-case syntax for templates, and a set of special rules for CTFE, and a whole set of parallel "static" statements (if, else, foreach) and a special compile-type-only type construct (tuples), just let D be D, either at runtime or compile type. If a function could return a Type, and if that type could be used in a Type Constructor, then you'd have all the magic template sauce you'd need, and templates could happily converge themselves with regular functions. Hey! I told you it was going to be nutty!!! <g> --benji That would only work for templated functions, though. What about templated types? Forget I ever let my ass do the thinking. I'd really like to see how this would look, but I feel it'd make for uglier syntax. I don't really know how it would work, but the syntax is easy to imagine: Type Dictionary = HashMap(char[], char[]); Dictionary d = new Dictionary(); In this case, HashMap is just a function (executable at compile-time through CTFE), which returns a type. Once the type has been returned, objects of that type can be instantiated. This idea first occurred to me when CTFE was introduced. I thought to myself "if we can have compile-time function exectuion", why can't we also have "runtime template instantiation"? Why is it only possible to define a new type (or to choose which type) at compile time? In languages like Ruby, you can attach new methods to an object at runtime. In .NET, you can generate, compile, and load new bytecode instructions on the fly. It's hard to think of cases where you'd really want to construct a new type at runtime. But maybe....automatically generating a library of types by querying a database schema? --benji  Oct 08 2008 Benji Smith <dlanguage benjismith.net> writes: Simen Kjaeraas wrote: Benji Smith <dlanguage benjismith.net> wrote: This idea first occurred to me when CTFE was introduced. I thought to myself "if we can have compile-time function exectuion", why can't we also have "runtime template instantiation"? Why is it only possible to define a new type (or to choose which type) at compile time? In languages like Ruby, you can attach new methods to an object at runtime. In .NET, you can generate, compile, and load new bytecode instructions on the fly. It's hard to think of cases where you'd really want to construct a new type at runtime. But maybe....automatically generating a library of types by querying a database schema? --benji The reasons for such things are to be found in the compiler. Optimizing an expression whose types you do not know, and allocating space for a type that may change its size under your feet - sounds to me like tricky business. Yep. I totally understand why it's not currently possible. You'd have to have an instance of the compiler always available at runtime; compiling, loading, and linking on the fly. Tricky stuff. But it'd be cool. It wasn't a real suggestion. Just a musing. --benji  Oct 08 2008 Don <nospam nospam.com.au> writes: Benji Smith wrote: Simen Kjaeraas wrote: On Wed, 08 Oct 2008 22:02:18 +0200, Simen Kjaeraas <simen.kjaras gmail.com> wrote: On Mon, 06 Oct 2008 12:39:29 +0200, Benji Smith <dlanguage benjismith.net> wrote: Andrei Alexandrescu wrote: One morning I woke up with the sudden realization of what the problem was: the shouting. Here's my (nutty) opinion: Neither the "!" nor the "." really want to be there. I think the language really *wants* to be using a bare set of parens for templates. Because the language actually wants templates and functions to converge. Instead of a special-case syntax for templates, and a set of special rules for CTFE, and a whole set of parallel "static" statements (if, else, foreach) and a special compile-type-only type construct (tuples), just let D be D, either at runtime or compile type. If a function could return a Type, and if that type could be used in a Type Constructor, then you'd have all the magic template sauce you'd need, and templates could happily converge themselves with regular functions. Hey! I told you it was going to be nutty!!! <g> --benji That would only work for templated functions, though. What about templated types? Forget I ever let my ass do the thinking. I'd really like to see how this would look, but I feel it'd make for uglier syntax. I don't really know how it would work, but the syntax is easy to imagine: Type Dictionary = HashMap(char[], char[]); Dictionary d = new Dictionary(); In this case, HashMap is just a function (executable at compile-time through CTFE), which returns a type. Once the type has been returned, objects of that type can be instantiated. This idea first occurred to me when CTFE was introduced. I thought to myself "if we can have compile-time function exectuion", why can't we also have "runtime template instantiation"? Why is it only possible to define a new type (or to choose which type) at compile time? In languages like Ruby, you can attach new methods to an object at runtime. In .NET, you can generate, compile, and load new bytecode instructions on the fly. It's hard to think of cases where you'd really want to construct a new type at runtime. But maybe....automatically generating a library of types by querying a database schema? It makes sense to construct a new type in CTFE code, though. That would allow a template to be instantiated inside a CTFE function. Currently, a template can pass its arguments into a CTFE function, but a CTFE function cannot pass its arguments to a template.  Oct 09 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I'm joining this discussion late, but I just wanted to say the !() doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? Well part of the problem is that many people made up their mind just by imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. Andrei  Oct 06 2008 Ary Borenszweig <ary esperanto.org.ar> writes: Andrei Alexandrescu wrote: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I'm joining this discussion late, but I just wanted to say the !() doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? Well part of the problem is that many people made up their mind just by imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. So let's have them written down to be able to compare them easier: The sad pirate ---------------- alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; The curly braces ---------------- alias DenseMatrix{num} PulType; alias SparseRowsMatrix{num, HashSparseVector} PuuType; alias BiMap{uint, Tuple{uint, uint}, BiMapOptions.lhDense} DicType; The at ---------------- alias DenseMatrix num PulType; alias SparseRowsMatrix (num, HashSparseVector) PuuType; alias BiMap (uint, Tuple (uint, uint), BiMapOptions.lhDense) DicType; --- Personally, I find the {} easier to understand, and it's less typing, but it doesn't allow to omit the closing } for one argument. Andrei  Oct 06 2008 "Steven Schveighoffer" <schveiguy yahoo.com> writes: "Ary Borenszweig" wrote Andrei Alexandrescu wrote: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I'm joining this discussion late, but I just wanted to say the !() doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? Well part of the problem is that many people made up their mind just by imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. So let's have them written down to be able to compare them easier: The sad pirate ---------------- alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; The curly braces ---------------- alias DenseMatrix{num} PulType; alias SparseRowsMatrix{num, HashSparseVector} PuuType; alias BiMap{uint, Tuple{uint, uint}, BiMapOptions.lhDense} DicType; The at ---------------- alias DenseMatrix num PulType; alias SparseRowsMatrix (num, HashSparseVector) PuuType; alias BiMap (uint, Tuple (uint, uint), BiMapOptions.lhDense) DicType; --- Personally, I find the {} easier to understand, and it's less typing, but it doesn't allow to omit the closing } for one argument. I find the {} much easier to read than the . syntax. The omitting of the braces is not a huge savings. You are sacrificing a couple characters, actually only one if you are comparing with {}, at the expense of clarity. I think it's a special case that is not really worth the trouble. Besides, it's not hard to type {} when you are so used to it anyways, and if you are interested in saving characters, aliasing is a much better approach. One thing I should mention, since this is all about asthetics, my news reader keeps treating the name param as a linked email address. Somthing that will be very annoying if we adopt the syntax and end up discussing templates on the NG. I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) -Steve  Oct 06 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Steven Schveighoffer wrote: "Ary Borenszweig" wrote Andrei Alexandrescu wrote: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. The sad pirate ---------------- alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; The curly braces ---------------- alias DenseMatrix{num} PulType; alias SparseRowsMatrix{num, HashSparseVector} PuuType; alias BiMap{uint, Tuple{uint, uint}, BiMapOptions.lhDense} DicType; The at ---------------- alias DenseMatrix num PulType; alias SparseRowsMatrix (num, HashSparseVector) PuuType; alias BiMap (uint, Tuple (uint, uint), BiMapOptions.lhDense) DicType; --- Personally, I find the {} easier to understand, and it's less typing, but it doesn't allow to omit the closing } for one argument. I find the {} much easier to read than the . syntax. To me too. The omitting of the braces is not a huge savings. You are sacrificing a couple characters, actually only one if you are comparing with {}, at the expense of clarity. I think it's a special case that is not really worth the trouble. Besides, it's not hard to type {} when you are so used to it anyways, and if you are interested in saving characters, aliasing is a much better approach. One thing I kinda dislike about Template Arg is that adding a second arg also asks for the parens. This is a problem present with single- vs. multi-statement blocks as well: if (a) b; If you want to add another statement, you need to add the curls as well: if (a) { b; c; } But then if you want to remove one of the statement you'd want to remove the curls too to stay consistent: if (a) c; This becomes tenuous enough that many people and some coding standards actually prefer to use full block statements to start with, even when they only contain one statement. One thing I should mention, since this is all about asthetics, my news reader keeps treating the name param as a linked email address. Somthing that will be very annoying if we adopt the syntax and end up discussing templates on the NG. Walter made another point, namely that " " has "a lot of ink" in it. I know what he means. I guess people who wanted templates to be distinguished will find that an advantage :o). I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) Well would you go on a strike if there was a little experimentation with the curls? Andrei  Oct 06 2008 "Steven Schveighoffer" <schveiguy yahoo.com> writes: "Andrei Alexandrescu" wrote Steven Schveighoffer wrote: I find the {} much easier to read than the . syntax. To me too. The omitting of the braces is not a huge savings. You are sacrificing a couple characters, actually only one if you are comparing with {}, at the expense of clarity. I think it's a special case that is not really worth the trouble. Besides, it's not hard to type {} when you are so used to it anyways, and if you are interested in saving characters, aliasing is a much better approach. One thing I kinda dislike about Template Arg is that adding a second arg also asks for the parens. This is a problem present with single- vs. multi-statement blocks as well: if (a) b; If you want to add another statement, you need to add the curls as well: if (a) { b; c; } But then if you want to remove one of the statement you'd want to remove the curls too to stay consistent: if (a) c; This becomes tenuous enough that many people and some coding standards actually prefer to use full block statements to start with, even when they only contain one statement. Yeah, I find myself doing that also, removing the {} braces when possible, but that can't apply here for technical reasons. Conversely, I don't think anyone is complaining that they always have to use braces for one-line functions. One thing I should mention, since this is all about asthetics, my news reader keeps treating the name param as a linked email address. Somthing that will be very annoying if we adopt the syntax and end up discussing templates on the NG. Walter made another point, namely that " " has "a lot of ink" in it. I know what he means. I guess people who wanted templates to be distinguished will find that an advantage :o). Yeah, but ! is just as good then, and we don't have to change thousands of lines of code ;) I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) Well would you go on a strike if there was a little experimentation with the curls? I like D too much to give it up based on this one thing. But I would be cursing you profusely as I changed all my existing D code when I move to support D2. I don't think I'd ever feel that it was an improvement, but if it means so much to everyone to abolish the ! syntax, I'd just do the updates and move on. Like I said, it's a bicycle shed color. BTW, this would be another notch in the D1/D2 incompatibility belt (perhaps an insurmountable one), but that ship may have already sailed. -Steve  Oct 06 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Steven Schveighoffer wrote: "Andrei Alexandrescu" wrote Well would you go on a strike if there was a little experimentation with the curls? I like D too much to give it up based on this one thing. But I would be cursing you profusely as I changed all my existing D code when I move to support D2. I don't think I'd ever feel that it was an improvement, but if it means so much to everyone to abolish the ! syntax, I'd just do the updates and move on. Like I said, it's a bicycle shed color. BTW, this would be another notch in the D1/D2 incompatibility belt (perhaps an insurmountable one), but that ship may have already sailed. There's no need to worry about it at all. The !() syntax can stay for a long time in vigor as an alternative that gets used less and less, then mentioned less and less, until essentially disabling it becomes a non-event. PL history has many examples of such changes that were successful, and I'll give a few: 1. The K&R function declaration syntax: int foo(a) int a; { return a; } Before trying: do you believe gcc would accept it? How many of us wrote one like that? 2. C++'s member function definition: class A { void foo(); } void A.foo() {} 3. Perl, having a very experimental attitude towards syntax, has effectively "forgot" quite a few syntaxes that weren't successful, but remained harmless. For example, "?pattern?" is equivalent with the well-known "/pattern/", and still accepted - yet hardly anyone uses it anymore. (There was IIRC an odd operator for accessing a package member that also fell into obsolescence, incidentally it might have been "!", does anyone know?) Of course it's ineffective to allow a lot of things and then leave them hanging around, but it is possible to operate a syntax change without too much disruption. Andrei  Oct 06 2008 KennyTM~ <kennytm gmail.com> writes: Andrei Alexandrescu wrote: Steven Schveighoffer wrote: "Ary Borenszweig" wrote Andrei Alexandrescu wrote: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? by imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. The sad pirate ---------------- alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; The curly braces ---------------- alias DenseMatrix{num} PulType; alias SparseRowsMatrix{num, HashSparseVector} PuuType; alias BiMap{uint, Tuple{uint, uint}, BiMapOptions.lhDense} DicType; The at ---------------- alias DenseMatrix num PulType; alias SparseRowsMatrix (num, HashSparseVector) PuuType; alias BiMap (uint, Tuple (uint, uint), BiMapOptions.lhDense) DicType; --- Personally, I find the {} easier to understand, and it's less typing, but it doesn't allow to omit the closing } for one argument. I find the {} much easier to read than the . syntax. To me too. The omitting of the braces is not a huge savings. You are sacrificing a couple characters, actually only one if you are comparing with {}, at the expense of clarity. I think it's a special case that is not really worth the trouble. Besides, it's not hard to type {} when you are so used to it anyways, and if you are interested in saving characters, aliasing is a much better approach. One thing I kinda dislike about Template Arg is that adding a second arg also asks for the parens. This is a problem present with single- vs. multi-statement blocks as well: if (a) b; If you want to add another statement, you need to add the curls as well: if (a) { b; c; } But then if you want to remove one of the statement you'd want to remove the curls too to stay consistent: if (a) c; This becomes tenuous enough that many people and some coding standards actually prefer to use full block statements to start with, even when they only contain one statement. One thing I should mention, since this is all about asthetics, my news reader keeps treating the name param as a linked email address. Somthing that will be very annoying if we adopt the syntax and end up discussing templates on the NG. Walter made another point, namely that " " has "a lot of ink" in it. I know what he means. I guess people who wanted templates to be distinguished will find that an advantage :o). I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) Well would you go on a strike if there was a little experimentation with the curls? Andrei Frankly speaking one disadvantage of {} is that it is more difficult to refactor it (unlike .() where you just do a s/!\(/.(/g.) If this is gonna effective, I suggest still keeping !() for a while, but make it deprecated, like what has been done to the === operator (the grace period from 0.72 (introduction of "is") to 0.126 (=== deprecated) to 0.174 (=== illegal)).  Oct 06 2008 superdan <super dan.org> writes: Bill Baxter Wrote: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) Yeh, me too. The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. spoken like a true prodigy. yeah. change yer font. But I still say ! stands out better. it stands out. unsure about the better' part. And honestly, my eyes totally just see !(...) as a symbolic string now, devoid of any meaning beyond "this is a template". Mentions of it looking like shouting or negation or anything else brought back a vague recollection of a time long ago when I still could see that. But I can only make it look like shouting in my mind now if I purposefully pretend the parentheses are part of a different word, or pretend to myself that I'm not looking at D code. i'm sober now eh. thing is that's important. i don't mind !() much myself. like a mole on an otherwise fine piece of ass. got used to it. but like u i also remember in the beginning i was like, what's wrong with walt did he run out of ideas or what. to some1 coming anew to d stuff like what!(the!(hell!())) is freakin' weird. no two ways about it. you just keep starin' at that mole like austin powers. if there's a way to get rid of it then whynot. helps attract newcomerz eh. parallel with perl is good. much stuff i thot and still think is plain weird in perl. but hash access was never one. looks good & works like a charm.  Oct 06 2008 Don <nospam nospam.com.au> writes: Bill Baxter wrote: On Tue, Oct 7, 2008 at 2:25 AM, superdan <super dan.org> wrote: Bill Baxter Wrote: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. Well, I think it's more a matter of the size than the particular font, though. So the remedy would probably be to switch to a font that takes up more screen real-estate, meaning I'll get fewer lines of D to the page. But there *is* a difference between { and ( even with Proggy at 6x10 -- 2 pixels are shifted one position. I suppose it's not any more subtle than the difference between . and , which is seen everywhere. I'm sure I could get used to it if it's what the D community thinks is best. Anyway I think foo{} is more readable than foo.(). thing is that's important. i don't mind !() much myself. like a mole on an otherwise fine piece of ass. got used to it. but like u i also remember in the beginning i was like, what's wrong with walt did he run out of ideas or what. to some1 coming anew to d stuff like what!(the!(hell!())) is freakin' weird. no two ways about it. you just keep starin' at that mole like austin powers. if there's a way to get rid of it then whynot. helps attract newcomerz eh. I thought it was bizarre till I read the justification here http://www.digitalmars.com/d/1.0/templates-revisited.html. Then I thought, OK. Not a bad idea. It's better than parsing ambiguities, and being forced to insert spaces between punctuation to avoid them. But I agree that as an utter newbie to D, foo{bar} would probably have seemed more elegant and obvious as a template syntax than re-purposing the unary NOT operator. The newbie's response to "foo{bar} is a template instantiation" would probably be "ok, sure." instead of "Why??" Still it seems like a big bike shed issue. And it's bizarre coming from the guy who's usually the first one to call "bike shed" anytime anyone else makes a suggestion to improve aesthetics. I agree with all these. There's a lot of other things I wish Andrei were working on instead. I'd hope for a colossal benefit, from something which would break almost all my code... (BTW Putting template parameters inside normal parens would be an adequate benefit).  Oct 07 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Don wrote: Bill Baxter wrote: On Tue, Oct 7, 2008 at 2:25 AM, superdan <super dan.org> wrote: Bill Baxter Wrote: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. Well, I think it's more a matter of the size than the particular font, though. So the remedy would probably be to switch to a font that takes up more screen real-estate, meaning I'll get fewer lines of D to the page. But there *is* a difference between { and ( even with Proggy at 6x10 -- 2 pixels are shifted one position. I suppose it's not any more subtle than the difference between . and , which is seen everywhere. I'm sure I could get used to it if it's what the D community thinks is best. Anyway I think foo{} is more readable than foo.(). thing is that's important. i don't mind !() much myself. like a mole on an otherwise fine piece of ass. got used to it. but like u i also remember in the beginning i was like, what's wrong with walt did he run out of ideas or what. to some1 coming anew to d stuff like what!(the!(hell!())) is freakin' weird. no two ways about it. you just keep starin' at that mole like austin powers. if there's a way to get rid of it then whynot. helps attract newcomerz eh. I thought it was bizarre till I read the justification here http://www.digitalmars.com/d/1.0/templates-revisited.html. Then I thought, OK. Not a bad idea. It's better than parsing ambiguities, and being forced to insert spaces between punctuation to avoid them. But I agree that as an utter newbie to D, foo{bar} would probably have seemed more elegant and obvious as a template syntax than re-purposing the unary NOT operator. The newbie's response to "foo{bar} is a template instantiation" would probably be "ok, sure." instead of "Why??" Still it seems like a big bike shed issue. And it's bizarre coming from the guy who's usually the first one to call "bike shed" anytime anyone else makes a suggestion to improve aesthetics. I agree with all these. There's a lot of other things I wish Andrei were working on instead. I am, I am. Soon as Walter fixes a few bugs, I'll rewrite std.algorithm (and add some more to it) in terms of ranges. Map and reduce will likely be lazyfied. Also std.random will define ranges instead of the current ad-hoc interface that works but is not integrated with anything in particular. But bear with me; I have a paper deadline staring me in the face and a thesis to finish. I'd hope for a colossal benefit, from something which would break almost all my code... Not going to break anything, as I explained. (BTW Putting template parameters inside normal parens would be an adequate benefit). I agree. Andrei  Oct 07 2008 Aarti_pl <aarti interia.pl> writes: Don pisze: Bill Baxter wrote: On Tue, Oct 7, 2008 at 2:25 AM, superdan <super dan.org> wrote: Bill Baxter Wrote: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. Well, I think it's more a matter of the size than the particular font, though. So the remedy would probably be to switch to a font that takes up more screen real-estate, meaning I'll get fewer lines of D to the page. But there *is* a difference between { and ( even with Proggy at 6x10 -- 2 pixels are shifted one position. I suppose it's not any more subtle than the difference between . and , which is seen everywhere. I'm sure I could get used to it if it's what the D community thinks is best. Anyway I think foo{} is more readable than foo.(). thing is that's important. i don't mind !() much myself. like a mole on an otherwise fine piece of ass. got used to it. but like u i also remember in the beginning i was like, what's wrong with walt did he run out of ideas or what. to some1 coming anew to d stuff like what!(the!(hell!())) is freakin' weird. no two ways about it. you just keep starin' at that mole like austin powers. if there's a way to get rid of it then whynot. helps attract newcomerz eh. I thought it was bizarre till I read the justification here http://www.digitalmars.com/d/1.0/templates-revisited.html. Then I thought, OK. Not a bad idea. It's better than parsing ambiguities, and being forced to insert spaces between punctuation to avoid them. But I agree that as an utter newbie to D, foo{bar} would probably have seemed more elegant and obvious as a template syntax than re-purposing the unary NOT operator. The newbie's response to "foo{bar} is a template instantiation" would probably be "ok, sure." instead of "Why??" Still it seems like a big bike shed issue. And it's bizarre coming from the guy who's usually the first one to call "bike shed" anytime anyone else makes a suggestion to improve aesthetics. I agree with all these. There's a lot of other things I wish Andrei were working on instead. I'd hope for a colossal benefit, from something which would break almost all my code... (BTW Putting template parameters inside normal parens would be an adequate benefit). Well, I want just say "I agree" to all written above by Bill, Don and others who like current syntax. I wanted to write a bit more today morning but I stopped myself as I would probably write too much :-P ------ I would be much more happy with implementation of my proposal: http://d.puremagic.com/issues/show_bug.cgi?id=1827 I mean here especially syntax for "is expression" for templates. http://digitalmars.com/d/1.0/expression.html#IsExpression As it occurred on Tango conference in talk of Rafał Bocian (who lead the D course for students) syntax for "is expression" and specification (among few other things) is especially difficult for newbies in D. Unfortunately answer from Walter, why he didn't decide to change current syntax was.... guess what? --- It doesn't look nice in code... Bad luck, said sad pirate .( BR Marcin Kuszczak (aarti_pl)  Oct 07 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Aarti_pl wrote: Don pisze: Bill Baxter wrote: On Tue, Oct 7, 2008 at 2:25 AM, superdan <super dan.org> wrote: Bill Baxter Wrote: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. Well, I think it's more a matter of the size than the particular font, though. So the remedy would probably be to switch to a font that takes up more screen real-estate, meaning I'll get fewer lines of D to the page. But there *is* a difference between { and ( even with Proggy at 6x10 -- 2 pixels are shifted one position. I suppose it's not any more subtle than the difference between . and , which is seen everywhere. I'm sure I could get used to it if it's what the D community thinks is best. Anyway I think foo{} is more readable than foo.(). thing is that's important. i don't mind !() much myself. like a mole on an otherwise fine piece of ass. got used to it. but like u i also remember in the beginning i was like, what's wrong with walt did he run out of ideas or what. to some1 coming anew to d stuff like what!(the!(hell!())) is freakin' weird. no two ways about it. you just keep starin' at that mole like austin powers. if there's a way to get rid of it then whynot. helps attract newcomerz eh. I thought it was bizarre till I read the justification here http://www.digitalmars.com/d/1.0/templates-revisited.html. Then I thought, OK. Not a bad idea. It's better than parsing ambiguities, and being forced to insert spaces between punctuation to avoid them. But I agree that as an utter newbie to D, foo{bar} would probably have seemed more elegant and obvious as a template syntax than re-purposing the unary NOT operator. The newbie's response to "foo{bar} is a template instantiation" would probably be "ok, sure." instead of "Why??" Still it seems like a big bike shed issue. And it's bizarre coming from the guy who's usually the first one to call "bike shed" anytime anyone else makes a suggestion to improve aesthetics. I agree with all these. There's a lot of other things I wish Andrei were working on instead. I'd hope for a colossal benefit, from something which would break almost all my code... (BTW Putting template parameters inside normal parens would be an adequate benefit). Well, I want just say "I agree" to all written above by Bill, Don and others who like current syntax. I wanted to write a bit more today morning but I stopped myself as I would probably write too much :-P ------ I would be much more happy with implementation of my proposal: http://d.puremagic.com/issues/show_bug.cgi?id=1827 I mean here especially syntax for "is expression" for templates. http://digitalmars.com/d/1.0/expression.html#IsExpression As it occurred on Tango conference in talk of Rafał Bocian (who lead the D course for students) syntax for "is expression" and specification (among few other things) is especially difficult for newbies in D. Unfortunately answer from Walter, why he didn't decide to change current syntax was.... guess what? --- It doesn't look nice in code... Bad luck, said sad pirate .( BR Marcin Kuszczak (aarti_pl) Your proposal should be reevaluated in wake of the conditional templates, which Walter has implemented a couple of releases ago. Andrei  Oct 07 2008 Marcin Kuszczak <aarti_please_no spam_interia.pl> writes: Andrei Alexandrescu wrote: Aarti_pl wrote: I would be much more happy with implementation of my proposal: http://d.puremagic.com/issues/show_bug.cgi?id=1827 I mean here especially syntax for "is expression" for templates. http://digitalmars.com/d/1.0/expression.html#IsExpression As it occurred on Tango conference in talk of Rafał Bocian (who lead the D course for students) syntax for "is expression" and specification (among few other things) is especially difficult for newbies in D. Unfortunately answer from Walter, why he didn't decide to change current syntax was.... guess what? --- It doesn't look nice in code... Bad luck, said sad pirate .( BR Marcin Kuszczak (aarti_pl) Your proposal should be reevaluated in wake of the conditional templates, which Walter has implemented a couple of releases ago. Andrei Yes, I am aware of that. They are just small part of the whole proposal, but currently implemented in such a way that it is not possible to use it in e.g. static asserts and aliases like it was proposed. I still think that proposal is good (no one pointed out problems with it). It could be implemented as kind of compile time expression once, and then used in other places. It allows also more expressiveness and predictable syntax e.g. void call(T : class)(T instance) {} I hope that above mentioned issues with current design of IsExpression will be eventually fixed somehow, sometime... The strange think here is how minor issues (as most of community doesn't have problem with it) suddenly emerges from deeps and good ideas (which solve real problems) are sunken in the water... Well, I can give more examples if you want :-) -- Regards Marcin Kuszczak (Aarti_pl) ------------------------------------- Ask me why I believe in Jesus - http://www.zapytajmnie.com (en/pl) Doost (port of few Boost libraries) - http://www.dsource.org/projects/doost/ -------------------------------------  Oct 07 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Marcin Kuszczak wrote: Andrei Alexandrescu wrote: Aarti_pl wrote: I would be much more happy with implementation of my proposal: http://d.puremagic.com/issues/show_bug.cgi?id=1827 I mean here especially syntax for "is expression" for templates. http://digitalmars.com/d/1.0/expression.html#IsExpression As it occurred on Tango conference in talk of Rafał Bocian (who lead the D course for students) syntax for "is expression" and specification (among few other things) is especially difficult for newbies in D. Unfortunately answer from Walter, why he didn't decide to change current syntax was.... guess what? --- It doesn't look nice in code... Bad luck, said sad pirate .( BR Marcin Kuszczak (aarti_pl) templates, which Walter has implemented a couple of releases ago. Andrei Yes, I am aware of that. They are just small part of the whole proposal, but currently implemented in such a way that it is not possible to use it in e.g. static asserts and aliases like it was proposed. I still think that proposal is good (no one pointed out problems with it). It could be implemented as kind of compile time expression once, and then used in other places. It allows also more expressiveness and predictable syntax e.g. void call(T : class)(T instance) {} I hope that above mentioned issues with current design of IsExpression will be eventually fixed somehow, sometime... I agree that pattern matching on type trees will have to make it into the language in one form or another. In fact, syntactically it is already there, but compiler bugs/limitations prevent it from happening. One thing with the notation you suggest is that it doesn't quite look like the rest of the language, and perhaps a few simple steps could be taken to make it more integrated. The strange think here is how minor issues (as most of community doesn't have problem with it) suddenly emerges from deeps and good ideas (which solve real problems) are sunken in the water... Well, I can give more examples if you want :-) This is pointing at some being born into royalty while others' good work is under-compensated. Well in a way I'm glad you bring this up. One thing that has caused and is causing an amount of stir and occasional irritation is the perception that I came out of nowhere and captured Walter's attention effortlessly. The reality is that being neighbors with Walter was part of the mix, but the prosaic bulk of it is that Walter cared only because of my previous and ongoing 99% transpiration. For better or worse, this state of affairs makes it that whatever I say is perceived as much more intense, imposing, controversial, quirky, or arrogant, than it is, and therefore much more scrutinized and criticized. This reaction is entirely understandable, and I'm still thinking of ways to assuage it. In the meantime it's costing me time because I feel obligated to answer the many replies to my posts. That being said, it is always great if you can bring to the fore more outstanding problems that you think have good solutions thought of by you or others. Just please consider the above when you compare and contrast them against the petty issue of "!()". Andrei  Oct 07 2008 Aarti_pl <aarti interia.pl> writes: Andrei Alexandrescu pisze: Marcin Kuszczak wrote: Andrei Alexandrescu wrote: Aarti_pl wrote: I would be much more happy with implementation of my proposal: http://d.puremagic.com/issues/show_bug.cgi?id=1827 I mean here especially syntax for "is expression" for templates. http://digitalmars.com/d/1.0/expression.html#IsExpression As it occurred on Tango conference in talk of Rafał Bocian (who lead the D course for students) syntax for "is expression" and specification (among few other things) is especially difficult for newbies in D. Unfortunately answer from Walter, why he didn't decide to change current syntax was.... guess what? --- It doesn't look nice in code... Bad luck, said sad pirate .( BR Marcin Kuszczak (aarti_pl) templates, which Walter has implemented a couple of releases ago. Andrei Yes, I am aware of that. They are just small part of the whole proposal, but currently implemented in such a way that it is not possible to use it in e.g. static asserts and aliases like it was proposed. I still think that proposal is good (no one pointed out problems with it). It could be implemented as kind of compile time expression once, and then used in other places. It allows also more expressiveness and predictable syntax e.g. void call(T : class)(T instance) {} I hope that above mentioned issues with current design of IsExpression will be eventually fixed somehow, sometime... I agree that pattern matching on type trees will have to make it into the language in one form or another. In fact, syntactically it is already there, but compiler bugs/limitations prevent it from happening. One thing with the notation you suggest is that it doesn't quite look like the rest of the language, Really? I got in my code a lot of similarly looking code. My proposal is in fact generalization and "uniformization" of existing syntaxes of template parameters and is expression. In most common cases you get same syntax as now. and perhaps a few simple steps could be taken to make it more integrated. I have nothing against improving this syntax. But I would be happy to get one uniform syntax for: template parameters, IsExpression, static assert, static if. And to dismiss this ugly: T : T[] creature ;-) With my proposal you got only one universal syntax and few design mistakes fixed. With current implementation state we probably lost opportunity for uniform syntax. The strange think here is how minor issues (as most of community doesn't have problem with it) suddenly emerges from deeps and good ideas (which solve real problems) are sunken in the water... Well, I can give more examples if you want :-) This is pointing at some being born into royalty while others' good work is under-compensated. Well in a way I'm glad you bring this up. One thing that has caused and is causing an amount of stir and occasional irritation is the perception that I came out of nowhere and captured Walter's attention effortlessly. The reality is that being neighbors with Walter was part of the mix, but the prosaic bulk of it is that Walter cared only because of my previous and ongoing 99% transpiration. For better or worse, this state of affairs makes it that whatever I say is perceived as much more intense, imposing, controversial, quirky, or arrogant, than it is, and therefore much more scrutinized and criticized. This reaction is entirely understandable, and I'm still thinking of ways to assuage it. In the meantime it's costing me time because I feel obligated to answer the many replies to my posts. Great that you see this issue. And even greater that you think rationally how to solve it. Currently I think that it would be good to ask community about top 5 problematic issues with D (not features, nor bugs because it would be better to get more general knowledge). And after sorting out final top 5 list, commit to improve situation or solve problem in these areas in reasonable, defined time. I think that people could post here proposed features, most annoying bugs, D design mistakes, problems with processes, problems with web pages etc. Just one restriction: only 5, single, well defined issues in decreasing priority. Well, I think that it might help to know what community really needs. That being said, it is always great if you can bring to the fore more outstanding problems that you think have good solutions thought of by you or others. Just please consider the above when you compare and contrast them against the petty issue of "!()". Andrei I think that asking people about "top 5 issues" (see above) will bring a lot of such a things. I will certainly contribute with my 5 groszy (Polish "cents"). Best Regards Marcin Kuszczak (aarti_pl)  Oct 08 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Aarti_pl wrote: Andrei Alexandrescu pisze: I agree that pattern matching on type trees will have to make it into the language in one form or another. In fact, syntactically it is already there, but compiler bugs/limitations prevent it from happening. One thing with the notation you suggest is that it doesn't quite look like the rest of the language, Really? I got in my code a lot of similarly looking code. My proposal is in fact generalization and "uniformization" of existing syntaxes of template parameters and is expression. In most common cases you get same syntax as now. Probably I misread the samples you posted with that bug report. Could you please point me to a more thorough description? and perhaps a few simple steps could be taken to make it more integrated. I have nothing against improving this syntax. But I would be happy to get one uniform syntax for: template parameters, IsExpression, static assert, static if. And to dismiss this ugly: T : T[] creature ;-) Oh how I wish Walter let that go. With my proposal you got only one universal syntax and few design mistakes fixed. With current implementation state we probably lost opportunity for uniform syntax. Then I guess it's of interest. Again, need to build some more understanding. The strange think here is how minor issues (as most of community doesn't have problem with it) suddenly emerges from deeps and good ideas (which solve real problems) are sunken in the water... Well, I can give more examples if you want :-) This is pointing at some being born into royalty while others' good work is under-compensated. Well in a way I'm glad you bring this up. One thing that has caused and is causing an amount of stir and occasional irritation is the perception that I came out of nowhere and captured Walter's attention effortlessly. The reality is that being neighbors with Walter was part of the mix, but the prosaic bulk of it is that Walter cared only because of my previous and ongoing 99% transpiration. For better or worse, this state of affairs makes it that whatever I say is perceived as much more intense, imposing, controversial, quirky, or arrogant, than it is, and therefore much more scrutinized and criticized. This reaction is entirely understandable, and I'm still thinking of ways to assuage it. In the meantime it's costing me time because I feel obligated to answer the many replies to my posts. Great that you see this issue. And even greater that you think rationally how to solve it. Currently I think that it would be good to ask community about top 5 problematic issues with D (not features, nor bugs because it would be better to get more general knowledge). And after sorting out final top 5 list, commit to improve situation or solve problem in these areas in reasonable, defined time. I think that people could post here proposed features, most annoying bugs, D design mistakes, problems with processes, problems with web pages etc. Just one restriction: only 5, single, well defined issues in decreasing priority. Well, I think that it might help to know what community really needs. I think that's a good idea. For now, I'm waiting on the results of the Tango conference to percolate. I understand there was some discussion about mistakes in D's design. That being said, it is always great if you can bring to the fore more outstanding problems that you think have good solutions thought of by you or others. Just please consider the above when you compare and contrast them against the petty issue of "!()". Andrei I think that asking people about "top 5 issues" (see above) will bring a lot of such a things. I will certainly contribute with my 5 groszy (Polish "cents"). Ok. Andrei  Oct 08 2008 John Reimer <terminal.node gmail.com> writes: Hello Andrei, <snip> This is pointing at some being born into royalty while others' good work is under-compensated. Well in a way I'm glad you bring this up. One thing that has caused and is causing an amount of stir and occasional irritation is the perception that I came out of nowhere and captured Walter's attention effortlessly. The reality is that being neighbors with Walter was part of the mix, but the prosaic bulk of it is that Walter cared only because of my previous and ongoing 99% transpiration. For better or worse, this state of affairs makes it that whatever I say is perceived as much more intense, imposing, controversial, quirky, or arrogant, than it is, and therefore much more scrutinized and criticized. This reaction is entirely understandable, and I'm still thinking of ways to assuage it. In the meantime it's costing me time because I feel obligated to answer the many replies to my posts. Anderi, I think you have a good grasp of the complexity of the situation here, and I think (or is it believe ;) ) you are doing a fine job, if not being a little too accomodating (in terms of trying to respond to everyone): I would have collapsed of exhaustion long ago if I were in your shoes. Anyway, keep up the good work. I think the general D/Walter relationship picture will become clearer the longer your participate. It does seem that D is taking a turn for the better again. -JJR  Oct 08 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: John Reimer wrote: Hello Andrei, <snip> This is pointing at some being born into royalty while others' good work is under-compensated. Well in a way I'm glad you bring this up. One thing that has caused and is causing an amount of stir and occasional irritation is the perception that I came out of nowhere and captured Walter's attention effortlessly. The reality is that being neighbors with Walter was part of the mix, but the prosaic bulk of it is that Walter cared only because of my previous and ongoing 99% transpiration. For better or worse, this state of affairs makes it that whatever I say is perceived as much more intense, imposing, controversial, quirky, or arrogant, than it is, and therefore much more scrutinized and criticized. This reaction is entirely understandable, and I'm still thinking of ways to assuage it. In the meantime it's costing me time because I feel obligated to answer the many replies to my posts. Anderi, I think you have a good grasp of the complexity of the situation here, and I think (or is it believe ;) ) you are doing a fine job, if not being a little too accomodating (in terms of trying to respond to everyone): I would have collapsed of exhaustion long ago if I were in your shoes. Anyway, keep up the good work. I think the general D/Walter relationship picture will become clearer the longer your participate. It does seem that D is taking a turn for the better again. -JJR Thank you! Andrei  Oct 09 2008 "Steven Schveighoffer" <schveiguy yahoo.com> writes: "Andrei Alexandrescu" wrote John Reimer wrote: Hello Andrei, <snip> This is pointing at some being born into royalty while others' good work is under-compensated. Well in a way I'm glad you bring this up. One thing that has caused and is causing an amount of stir and occasional irritation is the perception that I came out of nowhere and captured Walter's attention effortlessly. The reality is that being neighbors with Walter was part of the mix, but the prosaic bulk of it is that Walter cared only because of my previous and ongoing 99% transpiration. For better or worse, this state of affairs makes it that whatever I say is perceived as much more intense, imposing, controversial, quirky, or arrogant, than it is, and therefore much more scrutinized and criticized. This reaction is entirely understandable, and I'm still thinking of ways to assuage it. In the meantime it's costing me time because I feel obligated to answer the many replies to my posts. Anderi, I think you have a good grasp of the complexity of the situation here, and I think (or is it believe ;) ) you are doing a fine job, if not being a little too accomodating (in terms of trying to respond to everyone): I would have collapsed of exhaustion long ago if I were in your shoes. Anyway, keep up the good work. I think the general D/Walter relationship picture will become clearer the longer your participate. It does seem that D is taking a turn for the better again. -JJR Thank you! Andrei I'd also like to thank you Andrei. Although we don't see eye to eye on every issue, I think what you have brought to the table in many areas is very good. That gets overlooked, especially by me, because your ideas are mostly in Phobos, which I don't use. But I agree with most of your ideas. If I disagree with you it's mostly because I really do disagree, not because I perceive that your ideas automatically make it into D without question from Walter. Just some constructive criticism, it would have been a lot less agitating if you had stated in your original post: Background: Walter has allowed ".()" as an alternative to "!()" for template argument specifications in the next version of D2 as a trial to see if people like it better. Your original statement implied that it was a fact everyone hated !(), and implied that Walter had already blessed the change for D2. This was the point I think that set me off at least. -Steve  Oct 09 2008 KennyTM~ <kennytm gmail.com> writes: Ary Borenszweig wrote: Ary Borenszweig wrote: Andrei Alexandrescu wrote: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I'm joining this discussion late, but I just wanted to say the !() doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? Well part of the problem is that many people made up their mind just by imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. So let's have them written down to be able to compare them easier: The sad pirate ---------------- alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; The curly braces ---------------- alias DenseMatrix{num} PulType; alias SparseRowsMatrix{num, HashSparseVector} PuuType; alias BiMap{uint, Tuple{uint, uint}, BiMapOptions.lhDense} DicType; The at ---------------- alias DenseMatrix num PulType; alias SparseRowsMatrix (num, HashSparseVector) PuuType; alias BiMap (uint, Tuple (uint, uint), BiMapOptions.lhDense) DicType; --- Personally, I find the {} easier to understand, and it's less typing, but it doesn't allow to omit the closing } for one argument. Andrei Andrei Alexandrescu wrote: Bill Baxter wrote: On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I'm joining this discussion late, but I just wanted to say the !() doesn't bother me so much. What Walter said to you was pretty much how it went for me. Seemed weird for a while, but I got used to it. I had to do several double-takes reading this thread thinking people were suggesting to use plain "()" because the little dot is just so easy to miss. I find !() to at least be easier on the eyes than greater-than less-than everywhere in C++. I wouldn't be adamantly opposed to a different syntax, but it would have to be better by leaps and bounds for me to think it was worth the headache. And .() doesn't seem leaps and bounds better to me. I suggest, though, that if you think it looks a lot better you should at least post some example code showing "before" and "after" to try to convince us. Seems like not many here see a lot of point in making the change, so rather than pleading with everyone to try it out on their own, why not just save us the effort and show us how it improves the code you're looking at? Well part of the problem is that many people made up their mind just by imagining how it would look like, and it would be hard to sway them. Since you asked, here are some examples copied verbatim from a source file I found handy: alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; For functions: sort.("a._0 == b._0 ? a._1 < b._1 : a._0 < b._0")(all); result.id = std.conv.parse.(uint)(line); I was even more pleased while actually using The Sad Pirate than while imagining how it would be like, probably because typing is also easier (something that's not self-evident when just looking at the code). It looks like The Sad Pirate won't make it. People just don't see it as bringing enough improvement. But I think it is worth pursuing a number of alternatives. The two that to me are the most appealing are: a) Template{Args} Experience with Perl has shown that using {} as parens in addition to blocks is easy to pick up and easy on the eyes. Another argument in favor is that {} are "the right thing" - meaning they are parens that pair properly, as opposed to "<>". Also, they make today's "!()" look like a contraption that creates a new kind of parens from an existing (and ambiguous) kind of parens by prefixing it with a marker. b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. So let's have them written down to be able to compare them easier: The sad pirate ---------------- alias DenseMatrix.(num) PulType; alias SparseRowsMatrix.(num, HashSparseVector) PuuType; alias BiMap.(uint, Tuple.(uint, uint), BiMapOptions.lhDense) DicType; The curly braces ---------------- alias DenseMatrix{num} PulType; alias SparseRowsMatrix{num, HashSparseVector} PuuType; alias BiMap{uint, Tuple{uint, uint}, BiMapOptions.lhDense} DicType; The at ---------------- alias DenseMatrix num PulType; alias SparseRowsMatrix (num, HashSparseVector) PuuType; alias BiMap (uint, Tuple (uint, uint), BiMapOptions.lhDense) DicType; --- Personally, I find the {} easier to understand, and it's less typing, but it doesn't allow to omit the closing } for one argument. Andrei I don't think being able to omit {} is a big problem. Well, we used f(x) in a function with 1 parameter so long without complaining anyway. (Some mathematicians use f1 to indicate f(1) to avoid confusion with multiplication; and many cases the ( ) are even omitted, e.g. sin 1. So f(x) is not "the" norm.)  Oct 06 2008 Benji Smith <dlanguage benjismith.net> writes: Andrei Alexandrescu wrote: b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. Interesting. // If this is possible....... auto myTemplate = Template (1, 2, 3, uint); // ......shouldn't this be possible too? auto args = (1, 2, 3, uint); auto myTemplate = Template args; All other binary operators can operate on either a literal or on an expression, and I'd expect a template instantiation operator to do the same. What do you think? --benji  Oct 07 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Benji Smith wrote: Andrei Alexandrescu wrote: b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. Interesting. // If this is possible....... auto myTemplate = Template (1, 2, 3, uint); // ......shouldn't this be possible too? auto args = (1, 2, 3, uint); auto myTemplate = Template args; All other binary operators can operate on either a literal or on an expression, and I'd expect a template instantiation operator to do the same. What do you think? I think you will have a hard time (re)using parentheses and commas to define literals. Andrei  Oct 07 2008 Benji Smith <dlanguage benjismith.net> writes: Andrei Alexandrescu wrote: Benji Smith wrote: Andrei Alexandrescu wrote: b) Template Arg and Template (Args) This approach not only accepts the need for a contraption, it actually leverages it by allowing you to drop the parens if you only have one argument. That way " " becomes a true operator, the template instantiation operator. Note that this can be done with the current "!" as well, except that Template!Arg does not look to me like anything enticing. Interesting. // If this is possible....... auto myTemplate = Template (1, 2, 3, uint); // ......shouldn't this be possible too? auto args = (1, 2, 3, uint); auto myTemplate = Template args; All other binary operators can operate on either a literal or on an expression, and I'd expect a template instantiation operator to do the same. What do you think? I think you will have a hard time (re)using parentheses and commas to define literals. Andrei The actual syntax I used isn't important. That's not what I was talking about. It was the idea that template instantiation is the result of a binary operator. Which, to me, implies that the operands could be either literals or other types of expressions. I suppose the real syntax would be more like this: auto args = Tuple (1, 2, 3, real); auto myTemplate = Template args; So, if " " is a binary operator, it has two operands: a template name and an argument list. But, currently, there's no way to express either of those constructs symbolically. Only literally. It seems to me that, in your proposal, " " is not really an operator. It might act a little bit like an operator, but since its operands can't exist by themselves, then they're not really operands. And " " is not an operator. It'd be cool if template instantiation really was the result of an operator, with all of the necessary implications regarding the operands. Of course, I'm not actually *proposing* that implementation. I'm just drawing a fine line in the sand delineating what it actually means to be an "operator" rather than "template syntax". --benji  Oct 07 2008 "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes: On Mon, Oct 6, 2008 at 9:16 AM, Denis Koroskin <2korden gmail.com> wrote: On Mon, 06 Oct 2008 16:42:51 +0400, Jarrett Billingsley <jarrett.billingsley gmail.com> wrote: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() No it doesn't. Stdout("foo")("bar!").newline; And what causes ambiguity here? I mean, imagine you can't drop empty paranthesises. The point is that something like "foo()(5)" could then be either a template instantiation or a chained call.  Oct 06 2008 "Bill Baxter" <wbaxter gmail.com> writes: On Tue, Oct 7, 2008 at 2:25 AM, superdan <super dan.org> wrote: Bill Baxter Wrote: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) Yeh, me too. The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. spoken like a true prodigy. yeah. change yer font. Well, I think it's more a matter of the size than the particular font, though. So the remedy would probably be to switch to a font that takes up more screen real-estate, meaning I'll get fewer lines of D to the page. But there *is* a difference between { and ( even with Proggy at 6x10 -- 2 pixels are shifted one position. I suppose it's not any more subtle than the difference between . and , which is seen everywhere. I'm sure I could get used to it if it's what the D community thinks is best. Anyway I think foo{} is more readable than foo.(). thing is that's important. i don't mind !() much myself. like a mole on an otherwise fine piece of ass. got used to it. but like u i also remember in the beginning i was like, what's wrong with walt did he run out of ideas or what. to some1 coming anew to d stuff like what!(the!(hell!())) is freakin' weird. no two ways about it. you just keep starin' at that mole like austin powers. if there's a way to get rid of it then whynot. helps attract newcomerz eh. I thought it was bizarre till I read the justification here http://www.digitalmars.com/d/1.0/templates-revisited.html. Then I thought, OK. Not a bad idea. It's better than parsing ambiguities, and being forced to insert spaces between punctuation to avoid them. But I agree that as an utter newbie to D, foo{bar} would probably have seemed more elegant and obvious as a template syntax than re-purposing the unary NOT operator. The newbie's response to "foo{bar} is a template instantiation" would probably be "ok, sure." instead of "Why??" Still it seems like a big bike shed issue. And it's bizarre coming from the guy who's usually the first one to call "bike shed" anytime anyone else makes a suggestion to improve aesthetics. --bb  Oct 06 2008 "Adam D. Ruppe" <destructionator gmail.com> writes: On Sun, Oct 05, 2008 at 09:29:37AM -0500, Andrei Alexandrescu wrote: Heh. So this change should come together with abolishing goto :o). Noooooooooooooooooooooooooo! Andrei -- Adam D. Ruppe http://arsdnet.net  Oct 05 2008 "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() No it doesn't. Stdout("foo")("bar!").newline;  Oct 06 2008 "Denis Koroskin" <2korden gmail.com> writes: On Mon, 06 Oct 2008 16:42:51 +0400, Jarrett Billingsley <jarrett.billingsley gmail.com> wrote: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() No it doesn't. Stdout("foo")("bar!").newline; And what causes ambiguity here? I mean, imagine you can't drop empty paranthesises.  Oct 06 2008 "Simen Kjaeraas" <simen.kjaras gmail.com> writes: On Tue, 07 Oct 2008 16:27:00 +0200, Benji Smith <dlanguage benjismith.net> wrote: Jarrett Billingsley wrote: On Mon, Oct 6, 2008 at 6:59 AM, Denis Koroskin <2korden gmail.com> wrote: If we don't omit parenthesises, the ambiguity goes away: foo()(5) foo(5)() Stdout("foo")("bar!").newline; This is one of the main reasons I dislike opCall. Combined with optional-parentheses for function invocation, opCall is a poison-pill that creates a lot of potential ambiguities and prevents the implementation of more compelling features. --benji void delegate() foo() { return delegate void() {);}; } ? -- Simen  Oct 08 2008 "Steven Schveighoffer" <schveiguy yahoo.com> writes: "Walter Bright" wrote Steven Schveighoffer wrote: It's very alarming to me that something like this just has no problem getting in the language without community feedback. It's there at the moment so we can look at it and see if we like it. I know Andrei likes it. Anyhow, this is the opportunity for community feedback. Well, here is my feedback. First, I hate it when D has two ways of doing something. For example, C style array declarations, or function pointers. But those have good reasons. We want the new style because it's unambiguous and context-free, but we want the old style to allow easy porting of C code. But this change has no qualities I can see except that Andrei thinks it looks better (at least, that's the only reason he's given). There are not compatibility issues with C or some other language, it's just a new syntax that looks different. Are there problems with the original !()? Please give a reason for this addition besides asthetics, and then we can discuss the merits. Or if the community overwhelmingly loves this new syntax, I guess that's a good reason. Otherwise, I think it should be rejected on the simple principle of not fixing things that aren't broken. -Steve  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Steven Schveighoffer wrote: "Walter Bright" wrote Steven Schveighoffer wrote: It's very alarming to me that something like this just has no problem getting in the language without community feedback. know Andrei likes it. Anyhow, this is the opportunity for community feedback. Well, here is my feedback. First, I hate it when D has two ways of doing something. For example, C style array declarations, or function pointers. But those have good reasons. We want the new style because it's unambiguous and context-free, but we want the old style to allow easy porting of C code. I agree that D should not gratuitously define two ways of doing something. But this change has no qualities I can see except that Andrei thinks it looks better (at least, that's the only reason he's given). Believes, not thinks :o). There are not compatibility issues with C or some other language, it's just a new syntax that looks different. Are there problems with the original !()? Please give a reason for this addition besides asthetics, and then we can discuss the merits. Or if the community overwhelmingly loves this new syntax, I guess that's a good reason. Otherwise, I think it should be rejected on the simple principle of not fixing things that aren't broken. There are no objective differences, only the subjective arguments I brought based on linguistic conotations of "!". And actually I didn't come up with that argument - it literally came to me. Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. The one way to figure whether you'd aesthetically like something or not is to try it on some code. Unfortunately, that's not yet possible until the next release (Walter was kind enough to send me an alpha for a test drive). So my only request is kindly please hold off judgment until you can play with the notation and see how you feel. Andrei  Oct 04 2008 "Steven Schveighoffer" <schveiguy yahoo.com> writes: "Andrei Alexandrescu" wrote Steven Schveighoffer wrote: "Walter Bright" wrote Steven Schveighoffer wrote: It's very alarming to me that something like this just has no problem getting in the language without community feedback. know Andrei likes it. Anyhow, this is the opportunity for community feedback. Well, here is my feedback. First, I hate it when D has two ways of doing something. For example, C style array declarations, or function pointers. But those have good reasons. We want the new style because it's unambiguous and context-free, but we want the old style to allow easy porting of C code. I agree that D should not gratuitously define two ways of doing something. But this change has no qualities I can see except that Andrei thinks it looks better (at least, that's the only reason he's given). Believes, not thinks :o). yes, of course, my bad. There are not compatibility issues with C or some other language, it's just a new syntax that looks different. Are there problems with the original !()? Please give a reason for this addition besides asthetics, and then we can discuss the merits. Or if the community overwhelmingly loves this new syntax, I guess that's a good reason. Otherwise, I think it should be rejected on the simple principle of not fixing things that aren't broken. There are no objective differences, only the subjective arguments I brought based on linguistic conotations of "!". And actually I didn't come up with that argument - it literally came to me. Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. For what it's worth, I never had a 'jarring' experience with the ! syntax. It reads perfectly fine to me, and I actually like it. The one way to figure whether you'd aesthetically like something or not is to try it on some code. Unfortunately, that's not yet possible until the next release (Walter was kind enough to send me an alpha for a test drive). So my only request is kindly please hold off judgment until you can play with the notation and see how you feel. Firstly, I won't be playing with it unless it's released for D1 (which I doubt), and secondly, I don't think it's worth the effort to have something like this changed for minor annoyance. Since it's completely engrained on our brains already and we get along fine with !, there should have to be a really good reason to change it. 'looking better' doesn't strike me as a really good reason, especially when it is subjective (and especially when I disagree with the opinion). This seems like a bicycle shed issue to me. Please note, I'm not arguing for ! because of some technical reason, I probably would have been fine with ., but since it's already !, I think we should keep it that way unless a good technical reason comes up. The reasons you have put forth don't make it worth it in my mind. If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... -Steve  Oct 04 2008 Sean Kelly <sean invisibleduck.org> writes: Steven Schveighoffer wrote: "Andrei Alexandrescu" wrote Steven Schveighoffer wrote: "Walter Bright" wrote Steven Schveighoffer wrote: It's very alarming to me that something like this just has no problem getting in the language without community feedback. know Andrei likes it. Anyhow, this is the opportunity for community feedback. First, I hate it when D has two ways of doing something. For example, C style array declarations, or function pointers. But those have good reasons. We want the new style because it's unambiguous and context-free, but we want the old style to allow easy porting of C code. But this change has no qualities I can see except that Andrei thinks it looks better (at least, that's the only reason he's given). yes, of course, my bad. There are not compatibility issues with C or some other language, it's just a new syntax that looks different. Are there problems with the original !()? Please give a reason for this addition besides asthetics, and then we can discuss the merits. Or if the community overwhelmingly loves this new syntax, I guess that's a good reason. Otherwise, I think it should be rejected on the simple principle of not fixing things that aren't broken. brought based on linguistic conotations of "!". And actually I didn't come up with that argument - it literally came to me. Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. For what it's worth, I never had a 'jarring' experience with the ! syntax. It reads perfectly fine to me, and I actually like it. The one way to figure whether you'd aesthetically like something or not is to try it on some code. Unfortunately, that's not yet possible until the next release (Walter was kind enough to send me an alpha for a test drive). So my only request is kindly please hold off judgment until you can play with the notation and see how you feel. Firstly, I won't be playing with it unless it's released for D1 (which I doubt), and secondly, I don't think it's worth the effort to have something like this changed for minor annoyance. Since it's completely engrained on our brains already and we get along fine with !, there should have to be a really good reason to change it. 'looking better' doesn't strike me as a really good reason, especially when it is subjective (and especially when I disagree with the opinion). This seems like a bicycle shed issue to me. hehe... how about we swap '!' for '.' and in exchange we get to use something other than 'enum' for manifest constants ;-) Sean  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Sean Kelly wrote: hehe... how about we swap '!' for '.' and in exchange we get to use something other than 'enum' for manifest constants ;-) You know what, I believe "." is such an improvement, I'd join the movement. Andrei  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Steven Schveighoffer wrote: If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... Speaking of which... guess what he just did :o). Andrei  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Denis Koroskin wrote: On Sun, 05 Oct 2008 17:31:14 +0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: Steven Schveighoffer wrote: If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... Speaking of which... guess what he just did :o). Andrei Oh, come on... did he? :D His initiative. Can I use this as a bargaining chip? :o) Andrei  Oct 05 2008 Sean Kelly <sean invisibleduck.org> writes: Andrei Alexandrescu wrote: Steven Schveighoffer wrote: If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... Speaking of which... guess what he just did :o). *dances for joy* Sean  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Sean Kelly wrote: Andrei Alexandrescu wrote: Steven Schveighoffer wrote: If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... Speaking of which... guess what he just did :o). *dances for joy* Well are you greased properly for giving .() a shot? :o) Andrei  Oct 05 2008 Sean Kelly <sean invisibleduck.org> writes: Andrei Alexandrescu wrote: Sean Kelly wrote: Andrei Alexandrescu wrote: Steven Schveighoffer wrote: If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... Speaking of which... guess what he just did :o). *dances for joy* Well are you greased properly for giving .() a shot? :o) I'll certainly try it. Sean  Oct 05 2008 Sean Kelly <sean invisibleduck.org> writes: Andrei Alexandrescu wrote: Steven Schveighoffer wrote: "Walter Bright" wrote Steven Schveighoffer wrote: It's very alarming to me that something like this just has no problem getting in the language without community feedback. I know Andrei likes it. Anyhow, this is the opportunity for community feedback. Well, here is my feedback. First, I hate it when D has two ways of doing something. For example, C style array declarations, or function pointers. But those have good reasons. We want the new style because it's unambiguous and context-free, but we want the old style to allow easy porting of C code. I agree that D should not gratuitously define two ways of doing something. But this change has no qualities I can see except that Andrei thinks it looks better (at least, that's the only reason he's given). Believes, not thinks :o). There are not compatibility issues with C or some other language, it's just a new syntax that looks different. Are there problems with the original !()? Please give a reason for this addition besides asthetics, and then we can discuss the merits. Or if the community overwhelmingly loves this new syntax, I guess that's a good reason. Otherwise, I think it should be rejected on the simple principle of not fixing things that aren't broken. There are no objective differences, only the subjective arguments I brought based on linguistic conotations of "!". And actually I didn't come up with that argument - it literally came to me. Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. I like the use of '!' specifically for its linguistic connotation. It communicates to me that what's happening isn't normal run-time stuff. The one way to figure whether you'd aesthetically like something or not is to try it on some code. Unfortunately, that's not yet possible until the next release (Walter was kind enough to send me an alpha for a test drive). So my only request is kindly please hold off judgment until you can play with the notation and see how you feel. Will do. It's easy enough to search-replace '!' with '.' Sean  Oct 04 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Sean Kelly wrote: I like the use of '!' specifically for its linguistic connotation. It communicates to me that what's happening isn't normal run-time stuff. But I'm sure you don't have a beef with function template argument deduction, and normal run-time stuff that ain't. The one way to figure whether you'd aesthetically like something or not is to try it on some code. Unfortunately, that's not yet possible until the next release (Walter was kind enough to send me an alpha for a test drive). So my only request is kindly please hold off judgment until you can play with the notation and see how you feel. Will do. It's easy enough to search-replace '!' with '.' You'll need a sed expression to not catch unary ! and != as well. Andrei  Oct 05 2008 Sean Kelly <sean invisibleduck.org> writes: Andrei Alexandrescu wrote: Sean Kelly wrote: Will do. It's easy enough to search-replace '!' with '.' You'll need a sed expression to not catch unary ! and != as well. Nah, just replace "!(" with ".(" I basically never use "!(exp)" in conditions so there should be no problems. Sean  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Sean Kelly wrote: Andrei Alexandrescu wrote: Sean Kelly wrote: Will do. It's easy enough to search-replace '!' with '.' You'll need a sed expression to not catch unary ! and != as well. Nah, just replace "!(" with ".(" I basically never use "!(exp)" in conditions so there should be no problems. Sean auto reply = "Oh I didn't know that!(sarcasm)"; And for some unknown reason I decided to write templateName! (templateParameter).etc; I believe we require a lexer unless you know you won't write these bad (but valid) code.  Oct 05 2008 Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes: Sean Kelly wrote: Andrei Alexandrescu wrote: Sean Kelly wrote: Will do. It's easy enough to search-replace '!' with '.' You'll need a sed expression to not catch unary ! and != as well. Nah, just replace "!(" with ".(" I basically never use "!(exp)" in conditions so there should be no problems. Well well laziness never helps. sed --in-place -e 's/\([a-zA-Z0-9_]$$$$\s*$$!$$\s*$$(/\1\2.\3(/' *.d Preserves whitespace used around !, too. The major problem is it will transform insides of strings too. Also, won't transform instantiations across lines, and won't work with Unicode symbols... Andrei  Oct 05 2008 Sean Kelly <sean invisibleduck.org> writes: Andrei Alexandrescu wrote: Sean Kelly wrote: Andrei Alexandrescu wrote: Sean Kelly wrote: Will do. It's easy enough to search-replace '!' with '.' You'll need a sed expression to not catch unary ! and != as well. Nah, just replace "!(" with ".(" I basically never use "!(exp)" in conditions so there should be no problems. Well well laziness never helps. sed --in-place -e 's/$$[a-zA-Z0-9_]$$$$\s*$$!$$\s*$$(/\1\2.\3(/' *.d Preserves whitespace used around !, too. The major problem is it will transform insides of strings too. Also, won't transform instantiations across lines, and won't work with Unicode symbols... I'm just talking about my own code here, not a universal conversion tool. Sean  Oct 05 2008 Derek Parnell <derek psych.ward> writes: On Sun, 05 Oct 2008 00:12:06 -0500, Andrei Alexandrescu wrote: Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. I too find the form ... Template!(arg1, arg2, arg3) a bit uncomfortable. If we need to visually distinguish templates (compile-time constructs) from run-time constructs, I would advocate a totally different style all together. Maybe something more along the lines of the DDoc style ... (Template arg1 arg2 arg3) Nested it would look like ... (This (That (TheOther crap))) But I'm being too left-field, I suspect. -- Derek Parnell Melbourne, Australia skype: derek.j.parnell  Oct 05 2008 Christopher Wright <dhasenan gmail.com> writes: Derek Parnell wrote: On Sun, 05 Oct 2008 00:12:06 -0500, Andrei Alexandrescu wrote: Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. I too find the form ... Template!(arg1, arg2, arg3) a bit uncomfortable. If we need to visually distinguish templates (compile-time constructs) from run-time constructs, I would advocate a totally different style all together. Maybe something more along the lines of the DDoc style ... (Template arg1 arg2 arg3) Nested it would look like ... (This (That (TheOther crap))) But I'm being too left-field, I suspect. It's actually a lot quicker to type ( than !( -- it's reasonable for me to use the same shift key for the and the (. So I wouldn't much complain about this, except for the ugliness. And !( is also ugly.  Oct 05 2008 =?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes: Christopher Wright wrote: Derek Parnell wrote: On Sun, 05 Oct 2008 00:12:06 -0500, Andrei Alexandrescu wrote: Word followed by exclamation mark. Our brains are wired to interpret that as an exclamation. If it's frequent enough in code, it becomes really jarring. I too find the form ... Template!(arg1, arg2, arg3) a bit uncomfortable. If we need to visually distinguish templates (compile-time constructs) from run-time constructs, I would advocate a totally different style all together. Maybe something more along the lines of the DDoc style ... (Template arg1 arg2 arg3) Nested it would look like ... (This (That (TheOther crap))) But I'm being too left-field, I suspect. It's actually a lot quicker to type ( than !( -- it's reasonable for me to use the same shift key for the and the (. So I wouldn't much complain about this, except for the ugliness. And !( is also ugly. Since I only use the left shift key, it’s equally quick to type for me. I don’t see much point in basing syntax on how fast you can type. Also, on German keyboard layouts (and I think lots of other non-us based, European layouts), the is at Compose + q, which is pretty uncomfortable.  Oct 05 2008 "Bill Baxter" <wbaxter gmail.com> writes: On Mon, Oct 6, 2008 at 11:58 PM, Steven Schveighoffer <schveiguy yahoo.com> wrote: "Ary Borenszweig" wrote I still vote to keep ! as it's the easiest solution, and I never have found it annoying ;) Yeh, me too. The (and #) also take up too much width in a small mono-space font like the Proggy font I use. And so they run into the previous and following chars making them less readable. ! is nice and thin so it doesn't have that problem. { } vs ( ) is also a fairly subtle distinction in a small font. Usually the context and usage is different enough that that doesn't matter. But of course you may just tell me I should change my font in that case. But I still say ! stands out better. And honestly, my eyes totally just see !(...) as a symbolic string now, devoid of any meaning beyond "this is a template". Mentions of it looking like shouting or negation or anything else brought back a vague recollection of a time long ago when I still could see that. But I can only make it look like shouting in my mind now if I purposefully pretend the parentheses are part of a different word, or pretend to myself that I'm not looking at D code. --bb  Oct 06 2008 "Bruce Adams" <tortoise_74 yeah.who.co.uk> writes: On Sun, 05 Oct 2008 11:48:35 +0100, Tom S <h3r3tic remove.mat.uni.torun.pl> wrote: I don't like using "." for template instantiation. The tokenizer in my eyes clearly separates constructs at ".". On the other hand, "!" as a graphical character is more 'filled', thus doesn't separate the identifier and arguments that much visually. foo.bar <- obviously member access foo.(bar, baz) <- multiple member access? ... It looks like it should yield a tuple containing bar and baz :P  Oct 05 2008 Moritz Warning <moritzwarning web.de> writes: On Sat, 04 Oct 2008 23:50:47 -0500, Andrei Alexandrescu wrote: Alexander Pánek wrote: Andrei Alexandrescu wrote: I believe the clear distinction is not only unnecessary, but undesirable. We should actively fight against it. Andrei I also believe the distinction is unnecessary. About the exclamation mark vs dot. I believe the dot would be worse: - code completion in IDEs get confused - '!' may be an unary operator, but '.' is also some kind of operator that is often used otherwise. - changing the syntax always hurts, even if it might be easy to do so. The justification should be strong.  Oct 05 2008 "Denis Koroskin" <2korden gmail.com> writes: On Sun, 05 Oct 2008 17:31:14 +0400, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: Steven Schveighoffer wrote: If this change is implemented, Walter is going to have a hard time arguing that it's not worth changing invariant to immutable... Speaking of which... guess what he just did :o). Andrei Oh, come on... did he? :D  Oct 05 2008 "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes: On Sun, Oct 5, 2008 at 12:06 AM, Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote: The problem I see with "!" as a template instantiation is not technical. I write a fair amount of templated code and over years the "!" did not grow on me at all. I was time and again consoled by Walter than one day that will happen, but it never did. I also realized that Walter didn't see a problem with it because he writes only little template code. I didn't have much beef with other oddities unique to D. For example, I found no problem accommodating binary "~" and I was wondering what makes "!" different. I was just looking at a page full of templates and it looked like crap. One morning I woke up with the sudden realization of what the problem was: the shouting. In C, "!" is used as a unary operator. That may seem odd at first, but it nevers follows a word so it's tenuous to associate it with the natural language "!". In D, binary "!" _always_ follows a word, a name, something coming from natural language. So the conotation with exclamation jumps at you. That's why I find the choice of "!" poor. I believe it can impede to some extent acquisition of templates by newcomers, and conversely I believe that using .() can make templates more palatable. I tried using ".()" in my code and in only a couple of days it looked and felt way better to me. Based on that experience, I suggest that "!()" is dropped in favor of ".()" for template instantiation for D2. Sean's argument that "The exclamation mark signifies an assertion of sorts" is exactly where I'd want templates not to be: they should be blended in, not a hiccup from normal code. Serious effort has been, and still is, made in D to avoid shell-shocking people about use of templates, and I think ".()" would be a good step in that direction. Long argument short: I don't mind !() at all, and changing it to .() seems like a pointless pedanticism. But since you're the one suggesting it, there's a very good chance of it getting into the language (if it hasn't already), so there's not much use arguing against it.  Oct 05 2008 "Bent Rasmussen" <IncredibleShrinkingSphere Gmail.com> writes: Somewhere there is the dream of a pure function call syntax abs(real) sqrt(abs(real) x); Total unification. And possibly total impossibility. Looks beautiful tho. - Bent "Steven Schveighoffer" <schveiguy yahoo.com> skrev i meddelelsen news:gc9ab4$1ai4$1 digitalmars.com... "Andrei Alexandrescu" wrote (Background: Walter has kindly allowed ".()" as an alternative to the ugly "!()" for template argument specifications.) :( Another case of multiple syntax possibilities. What was wrong with !() ? I didn't consider it ugly at all. In fact, I prefer it. It's very alarming to me that something like this just has no problem getting in the language without community feedback. Just a quick question - I am feeling an increasing desire to add a template called Positive to std.typecons. Then Positive.(real) would restrict its values to only positive real numbers etc. I wouldn't use it, if that helps at all. Even if it was in Tango (i.e. not just because I don't use Phobos). -Steve  Oct 05 2008 KennyTM~ <kennytm gmail.com> writes: Bent Rasmussen wrote: Somewhere there is the dream of a pure function call syntax abs(real) sqrt(abs(real) x); Total unification. And possibly total impossibility. Looks beautiful tho. - Bent But how to check 0 ∉ gamma(ℝ)? This notation is simple for invertible functions and sets with finite elements, but won't be applicable for more complicated functions and types. "Steven Schveighoffer" <schveiguy yahoo.com> skrev i meddelelsen news:gc9ab4$1ai4\$1 digitalmars.com...
"Andrei Alexandrescu" wrote
(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

:(

Another case of multiple syntax possibilities.  What was wrong with
!() ? I didn't consider it ugly at all.  In fact, I prefer it.

It's very alarming to me that something like this just has no problem
getting in the language without community feedback.

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

I wouldn't use it, if that helps at all.  Even if it was in Tango
(i.e. not just because I don't use Phobos).

-Steve


Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Bent Rasmussen wrote:
Somewhere there is the dream of a pure function call syntax

abs(real) sqrt(abs(real) x);

Total unification. And possibly total impossibility.

Looks beautiful tho.

It does look beautiful. It won't as soon as "!" enters the picture.

Andrei

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Denis Koroskin wrote:
On Sun, 05 Oct 2008 20:09:25 +0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Bent Rasmussen wrote:
Somewhere there is the dream of a pure function call syntax
abs(real) sqrt(abs(real) x);
Total unification. And possibly total impossibility.
Looks beautiful tho.

It does look beautiful. It won't as soon as "!" enters the picture.

Andrei

I second that. It also brings templates and functions closer:

int x = sqrt(42); // what is sqrt - a CT-function or a template? I don't
care!

So in the "me" vs. "we" argument there's actually five "me"s or so. This
has Agent Smith written all over it! :o)

Andrei

Oct 05 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Sun, 05 Oct 2008 17:49:48 +0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

KennyTM~ wrote:
Michel Fortin wrote:
On 2008-10-05 01:14:17 -0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> said:

I don't favor "." any more than the next guy, but I am glad there is
awareness of how unfit a choice "!" is. If you have any ideas, please
post them! Ah! I! Exclaimed! Again!

Hum, I don't think we have much choice, it'll have to be something in
this lot:

Positive!(real)(joke);
Positive.(real)(joke);
Positive#(real)(joke);
Positive (real)(joke);
Positive&(real)(joke);
Positive(real)(joke);
Positive´(real)(joke);
Positive^(real)(joke);
Positive¨(real)(joke);
Positive\(real)(joke);

Anything else I forgot?

Or we could use special delimiter characters:

Positive<real>(joke);
Positive“real”(joke);
Positive«real»(joke);
Positive#real (joke);

Each having its own problem though.

My preference still goes to "!(".

- - -

The ".(" syntax makes me think more of something like this:

void func(T, alias methodOfT, A...)(T obj, A args)
{
obj.(methodOfT)(args);
}

which I which I could do. If methodOfT was a string, I suppose I could
use string mixins, but it pushes diagnostics about misnamed methods
further in the template and requires adding quotes to the template
parameter when instanciating.

f«T»(x);
a valid construct, and to workaround that « and » can't be easily
typed you could substitute it with
f\<T\>(x);
---

Yah I would've like French quotes too.

Anyway, I think the .() syntax is not as good as !() because the . is
pretty hideous before another punctuation mark (which may be a good
thing, I don't know), and one could easily miss it.
And even if .() is allowed, please don't remove !() -- it will break
significantly many code, and it doesn't cause any ambiguity either
(unlike .func() vs .prop).

Many languages have successfully dealt with similar situations by simply
allowing both but promoting only one in books and other documentation.
Speaking of which, I'm on verge of signing with Addison Wesley Longman
for delivering TDPL in April.

Andrei

Great news! Your site still says it appears in October, though.

Oct 05 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Sun, 05 Oct 2008 20:09:25 +0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Bent Rasmussen wrote:
Somewhere there is the dream of a pure function call syntax
abs(real) sqrt(abs(real) x);
Total unification. And possibly total impossibility.
Looks beautiful tho.

It does look beautiful. It won't as soon as "!" enters the picture.

Andrei

I second that. It also brings templates and functions together:

int x = sqrt(42); // what is sqrt - a CT-function of a template? I don't
care!

Oct 05 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Sun, 05 Oct 2008 20:09:25 +0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Bent Rasmussen wrote:
Somewhere there is the dream of a pure function call syntax
abs(real) sqrt(abs(real) x);
Total unification. And possibly total impossibility.
Looks beautiful tho.

It does look beautiful. It won't as soon as "!" enters the picture.

Andrei

I second that. It also brings templates and functions closer:

int x = sqrt(42); // what is sqrt - a CT-function or a template? I don't
care!

Oct 05 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Mon, 06 Oct 2008 04:03:08 +0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Jason House wrote:
Andrei Alexandrescu wrote:

Leandro Lucarella wrote:
"enum" as the way to declare manifest constants were much more ugly
than
"!(", and most of the people were against it. I don't see why ".("
should
be introduced.

That's kinda hard to argue against because it's a sheer fact.

enum
types.

defineEnum in std.typecons provides that (and parsing too).

like using enums for a restricted set of options.  That'd allow the
compiler to provide toString and catch misuse in switch statements...
Including when I add or remove allowed values.

Walter hasn't gotten around to implementing the final switch statement,
which does exactly as you mention. For the interested I paste the
relevant section in TDPL - hot off the oven:

\section{The \protect\cc{final switch} Statement}

It is  often the case  that  switch  is  meant to handle  all possible
cases,  such as  all values  of a  small integer  or of  an enumerated
type. If, during maintenance, the  number of cases is changing, all of
the dependent  switch   statements suddenly fall out of  sync and must
be  manually searched  for  and modified.   For  such situations,  the
\cc{final switch} statement comes in handy:

\begin{D}
...
void Handle(uint x) {
final switch (x & deviceStatusMask) {
case 0: ...
case 1: ...
case 2: ...
case 3: ...
}
}
\end{D}

Should  the value of   mask  change  later to,  say, 7,  attempting to
recompile  Handle  is met with refusal on the following grounds:

\begin{lstlisting}[language=sys]
Error: final switch statement must handle all values
\end{lstlisting}

The \cc{final switch} statement looks  at the shape of its controlling
expression to figure out the bounds, as follows:

\begin{itemize*}
\item  If \meta{expression}  is \metai{e}   &  \metaii{e}  and  one of
\metai{e} and \metaii{e} evaluates  to a positive compile-time value
c , then the range is determined as  0  up to (and including)  c .
\item  If  \meta{expression}   is  \metai{e}  \cc{\%}  \metaii{e}  and
\metaii{e} evaluates to a  positive compile-time value  c , then the
range is determined as  0  up to (and not including) \cc{c}.
\item  If  \meta{expression}  is   an  unsigned  right  shift  (either
\metai{e}  \cc{>>}  \metaii{e}  operating  on unsigned  numbers,  or
\metai{e}  \cc{>>>} \metaii{e}),  and if  \metaii{e} evaluates  to a
compile-time value   c , then the range  is determined as   0  up to
(and not including) \cc{1 << (8 *} \metai{e}\cc{.sizeof - c)}.%>>
\item If  \meta{expression} is  the assignment variant  of one  of the
above  ( &= , \cc{\%=}  etc.) then  the range  the same  as  for the
non-assignment variant.
\item If  \meta{expression} is  an enumerated type,  the range  is the
entire set of values of the enumerated type.
\item   Otherwise,  the  range   is   e.min    up  to   and  including
e.max . (The  min  and  max   constants are defined for all numeric
types.)
\end{itemize*}

There are quite a few other  cases in which the range of an expression
could be  effectively determined,  but \cc{final switch}  only handles
the  usual ones.   A  default   label  is allowed  inside a  \cc{final
switch} statement  and practically turns  off all checks  because it
ensures \emph{de facto} that all values are handled.

Andrei

Final switch is great, but why allow default case in it? Putting the
default case into the final switch effectively transforms it into a
regular one discarding all of its benefits. What's the point?

Oct 05 2008
"Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Sun, Oct 5, 2008 at 8:57 PM, Chris R. Miller
<lordsauronthegreat gmail.com> wrote:
The !() syntax seems to serve only as a heads up that it's a template.
Otherwise (as far as I can tell) a simple foo(int)(bar, baaz) would work
just as well as foo!(int)(bar, baaz).

Unambiguous grammar, you fail it.

foo(bar)(baz); // template instantiation or a chained call?

This _can_ be _made_ to work, but it would mean that the parse tree
would be dependent upon semantic analysis, and that just makes things
slow and awful.  I.e. C++.

Oct 05 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Mon, 06 Oct 2008 14:56:43 +0400, Michel Fortin
<michel.fortin michelf.com> wrote:

On 2008-10-05 22:23:16 -0400, Michel Fortin <michel.fortin michelf.com>
said:

Well, not so sure about that: I'm pretty sure it's needed for
disambiguation too. Let's say you have:
void foo(int x)();
void foo(T)(T x);
foo(5);
Is foo(5) a the same as foo!(5), or does it call foo!(int).foo(5) ?
Under the current rules, it's the second (you can write foo!(5) to call
the first). If you allow templates to be instanciated without the "!",
then I guess both will match and you'll have ambiguity.
If you could avoid having sets of parameters, one for the function and
one for the template, then you could get rid of the "!" in a snap...

Or... we could just disallow having both at the same time, just like you
can't have two functions with the same arguments. A call to foo(5) would
be ambigous in the above situation, plain and simple. Is this reasonable?

We could still disambiguate using:

foo!(5);

and:

foo(int)(5);

In this context, the ! becomes the "force this to be template arguments"
operator, or the "do not deduce template arguments, I'll provide them"
operator.

Or we could just forget ! completely and leave the first one impossible
to disambiguate.

Which makes me think that it's sad we can't write the second as:

foo(int, 5);

I'd be much nicer to the eye.

If we don't omit parenthesises, the ambiguity goes away:

foo()(5)
foo(5)()

Oct 06 2008
"Bill Baxter" <wbaxter gmail.com> writes:
On Sun, Oct 5, 2008 at 1:06 PM, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:
The problem I see with "!" as a template instantiation is not technical. I
write a fair amount of templated code and over years the "!" did not grow on
me at all. I was time and again consoled by Walter than one day that will
happen, but it never did. I also realized that Walter didn't see a problem
with it because he writes only little template code.

I'm joining this discussion late, but I just wanted to say the !()
doesn't bother me so much.
What Walter said to you was pretty much how it went for me.  Seemed
weird for a while, but I got used to it.

were suggesting to use plain "()" because the little dot is just so
easy to miss.

I find !() to at least be easier on the eyes than greater-than
less-than everywhere in C++.

I wouldn't be adamantly opposed to a different syntax, but it would
have to be better by leaps and bounds for me to think it was worth the
headache.  And .() doesn't seem leaps and bounds better to me.

I suggest, though, that if you think it looks a lot better you should
at least post some example code showing "before" and "after" to try to
convince us.  Seems like not many here see a lot of point in making
the change, so rather than pleading with everyone to try it out on
their own, why not just save us the effort and show us how it improves
the code you're looking at?

--bb

Oct 06 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Tue, 07 Oct 2008 20:05:28 +0400, Benji Smith <dlanguage benjismith.net>
wrote:

Andrei Alexandrescu wrote:
Benji Smith wrote:
Andrei Alexandrescu wrote:
b) Template Arg and Template (Args)

This approach not only accepts the need for a contraption, it
actually leverages it by allowing you to drop the parens if you only
have one argument. That way " " becomes a true operator, the template
instantiation operator. Note that this can be done with the current
"!" as well, except that Template!Arg does not look to me like
anything enticing.

Interesting.

// If this is possible.......
auto myTemplate = Template   (1, 2, 3, uint);

// ......shouldn't this be possible too?
auto args = (1, 2, 3, uint);
auto myTemplate = Template   args;

All other binary operators can operate on either a literal or on an
expression, and I'd expect a template instantiation operator to do the
same.

What do you think?

define literals.
Andrei

The actual syntax I used isn't important. That's not what I was talking

It was the idea that template instantiation is the result of a binary
operator. Which, to me, implies that the operands could be either
literals or other types of expressions. I suppose the real syntax would
be more like this:

auto args = Tuple   (1, 2, 3, real);
auto myTemplate = Template   args;

So, if " " is a binary operator, it has two operands: a template name
and an argument list. But, currently, there's no way to express either
of those constructs symbolically. Only literally.

It seems to me that, in your proposal, " " is not really an operator. It
might act a little bit like an operator, but since its operands can't
exist by themselves, then they're not really operands. And " " is not an
operator.

It'd be cool if template instantiation really was the result of an
operator, with all of the necessary implications regarding the operands.

Of course, I'm not actually *proposing* that implementation. I'm just
drawing a fine line in the sand delineating what it actually means to be
an "operator" rather than "template syntax".

--benji

You could do it this way:

alias Tuple (1,2,3,real) Args;
alias Template Args MyTemplate;

Oct 07 2008
"Simen Kjaeraas" <simen.kjaras gmail.com> writes:
On Mon, 06 Oct 2008 12:39:29 +0200, Benji Smith <dlanguage benjismith.net>
wrote:

Andrei Alexandrescu wrote:
One morning I woke up with the sudden realization of what the problem
was: the shouting.

Here's my (nutty) opinion:

Neither the "!" nor the "." really want to be there. I think the
language really *wants* to be using a bare set of parens for templates.
Because the language actually wants templates and functions to converge.

Instead of a special-case syntax for templates, and a set of special
rules for CTFE, and a whole set of parallel "static" statements (if,
else, foreach) and a special compile-type-only type construct (tuples),
just let D be D, either at runtime or compile type.

If a function could return a Type, and if that type could be used in a
Type Constructor, then you'd have all the magic template sauce you'd
need, and templates could happily converge themselves with regular
functions.

Hey! I told you it was going to be nutty!!!

<g>

--benji

That would only work for templated functions, though. What about templated
types?

--
Simen

Oct 08 2008
"Simen Kjaeraas" <simen.kjaras gmail.com> writes:
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:

Leandro Lucarella wrote:
"enum" as the way to declare manifest constants were much more ugly than
"!(", and most of the people were against it. I don't see why ".("
should
be introduced.

Ugly or not, enumerated symbols were manifest constants to begin with.
That's kinda hard to argue against because it's a sheer fact.

All bears are animals, so lets call all animals bears. See where this is
wrong?

--
Simen

Oct 08 2008
"Simen Kjaeraas" <simen.kjaras gmail.com> writes:
On Wed, 08 Oct 2008 22:02:18 +0200, Simen Kjaeraas
<simen.kjaras gmail.com> wrote:

On Mon, 06 Oct 2008 12:39:29 +0200, Benji Smith
<dlanguage benjismith.net> wrote:

Andrei Alexandrescu wrote:
One morning I woke up with the sudden realization of what the problem
was: the shouting.

Here's my (nutty) opinion:

Neither the "!" nor the "." really want to be there. I think the
language really *wants* to be using a bare set of parens for templates.
Because the language actually wants templates and functions to converge.

Instead of a special-case syntax for templates, and a set of special
rules for CTFE, and a whole set of parallel "static" statements (if,
else, foreach) and a special compile-type-only type construct (tuples),
just let D be D, either at runtime or compile type.

If a function could return a Type, and if that type could be used in a
Type Constructor, then you'd have all the magic template sauce you'd
need, and templates could happily converge themselves with regular
functions.

Hey! I told you it was going to be nutty!!!

<g>

--benji

That would only work for templated functions, though. What about
templated types?

Forget I ever let my ass do the thinking. I'd really like to see how this
would look, but I feel it'd make for uglier syntax.

--
Simen

Oct 08 2008
"Simen Kjaeraas" <simen.kjaras gmail.com> writes:
Benji Smith <dlanguage benjismith.net> wrote:

This idea first occurred to me when CTFE was introduced. I thought to
myself "if we can have compile-time function exectuion", why can't we
also have "runtime template instantiation"? Why is it only possible to
define a new type (or to choose which type) at compile time?

In languages like Ruby, you can attach new methods to an object at
runtime. In .NET, you can generate, compile, and load new bytecode
instructions on the fly.

It's hard to think of cases where you'd really want to construct a new
type at runtime. But maybe....automatically generating a library of
types by querying a database schema?

--benji

The reasons for such things are to be found in the compiler. Optimizing
an expression whose types you do not know, and allocating space for a
type that may change its size under your feet - sounds to me like tricky

--
Simen

Oct 08 2008
"Simen Kjaeraas" <simen.kjaras gmail.com> writes:
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:

Simen Kjaeraas wrote:
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:

Leandro Lucarella wrote:
"enum" as the way to declare manifest constants were much more ugly
than
"!(", and most of the people were against it. I don't see why ".("
should
be introduced.

Ugly or not, enumerated symbols were manifest constants to begin with.
That's kinda hard to argue against because it's a sheer fact.

All bears are animals, so lets call all animals bears. See where this
is wrong?

The correct reasoning to apply is, if you see a white bear, would you
call it a different way?

Andrei

Mayhaps. But to me, a manifest constant is not just a bear of a
different color, but possibly one with six legs, a prehensile tail,
bat wings, and riding a helicopter. And I'm pretty sure I would not
classify that as a bear, even if it still had fur and powerful jaws,
and would make for a fun teddy.

--
Simen

Oct 08 2008
"Simen Kjaeraas" <simen.kjaras gmail.com> writes:
On Wed, 08 Oct 2008 23:11:14 +0200, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Simen Kjaeraas wrote:
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:

Simen Kjaeraas wrote:
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> wrote:

Leandro Lucarella wrote:
"enum" as the way to declare manifest constants were much more ugly
than
"!(", and most of the people were against it. I don't see why ".("
should
be introduced.

Ugly or not, enumerated symbols were manifest constants to begin
with. That's kinda hard to argue against because it's a sheer fact.

All bears are animals, so lets call all animals bears. See where this
is wrong?

The correct reasoning to apply is, if you see a white bear, would you
call it a different way?

Andrei

different color, but possibly one with six legs, a prehensile tail,
bat wings, and riding a helicopter. And I'm pretty sure I would not
classify that as a bear, even if it still had fur and powerful jaws,
and would make for a fun teddy.

But you just agreed that enum is a manifest constant.

Andrei

Indeed. But my point is that not all manifest constants are enumerations,
as the name enum seems to suggest. That is my gripe with the choice. And
I fear it will continue like that.

--
Simen

Oct 08 2008
Walter Bright <newshound1 digitalmars.com> writes:
Andrei Alexandrescu wrote:
About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.

I'm not a math major. But in college I took 4 years of math, up through
integration in the complex plane and branch cuts (which I never did
properly understand <g>). Every engineering/physics class was a math
class. I never saw this notation. I am not suggesting it doesn't exist,
just that it became commonplace fairly recently, or that it isn't
commonplace at least at the undergraduate level. This plays into the
numbers issue you mentioned.

Oct 04 2008
KennyTM~ <kennytm gmail.com> writes:
Walter Bright wrote:
Andrei Alexandrescu wrote:
About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.

I'm not a math major. But in college I took 4 years of math, up through
integration in the complex plane and branch cuts (which I never did
properly understand <g>). Every engineering/physics class was a math
class. I never saw this notation. I am not suggesting it doesn't exist,
just that it became commonplace fairly recently, or that it isn't
commonplace at least at the undergraduate level. This plays into the
numbers issue you mentioned.

Probably they'd used (0, +∞) and [0, +∞) instead.

---

BTW, negative real numbers can also be indicated as ℝ⁻ (R^- if Unicode
is not supported). Is it now special enough to deserve a Negative!()
template? :p

I think these sign checking should be done through contracts or
"conditional template" (? whatever it's called; I haven't used one of
these yet) instead. Unless you can runtime check that

Positive!(double) x = 6;
Positive!(double) y = 12;
Positive!(double) z = void;
z = x - y;  // raises error.
Positive!(double) w;
din.readf("%g", &w);  // raises error if user enters negative number.

But I don't think uint, etc now even do these checks.

Oct 05 2008
KennyTM~ <kennytm gmail.com> writes:
Bruce Adams wrote:
On Sun, 05 Oct 2008 11:18:24 +0100, KennyTM~ <kennytm gmail.com> wrote:
Probably they'd used (0, +∞) and [0, +∞) instead.

---

BTW, negative real numbers can also be indicated as ℝ⁻ (R^- if Unicode
is not supported). Is it now special enough to deserve a Negative!()
template? :p

Nice use of unicode.

I think these sign checking should be done through contracts or
"conditional template" (? whatever it's called; I haven't used one of
these yet) instead. Unless you can runtime check that

Positive!(double) x = 6;
Positive!(double) y = 12;

Compile time check

Positive!(double) z = void;

This must be an syntax error surely?

type x = void; means don't initialize x. Or have I missed something?

z = x - y;  // raises error.

The return type of subtraction goes outside the postive domain:
i.e. if it needed to exist (which it probably doesn't) the function spec
would be:

double opMinus(Positive!(double) y, Positive!(double) y);

So this is actually:

z = cast(Positive!(double))(x - y)

Hence there is the necessary check which could be either run-time or
compile time.

Most of the time it can't be compile time because if I've initialized x
and y to be some runtime-dependent function (e.g. sin(current time))
then you can't be sure of the sign of x-y. So the check must be made
into runtime unless the expression can be CTFE-ed.

Positive!(double) w;
din.readf("%g", &w);  // raises error if user enters negative number.

But I don't think uint, etc now even do these checks.

This would ideally work as above but I see your problem.
The contract of readf is not tight enough. You should rewrite as:

double wtemp;
Positive!(double) w = wtemp;    // type check applied here

But this is getting ugly :)

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
KennyTM~ wrote:
On Sun, 05 Oct 2008 11:18:24 +0100, KennyTM~ <kennytm gmail.com> wrote:
Probably they'd used (0, +∞) and [0, +∞) instead.

---

BTW, negative real numbers can also be indicated as ℝ⁻ (R^- if
Unicode is not supported). Is it now special enough to deserve a
Negative!() template? :p

Nice use of unicode.

I think these sign checking should be done through contracts or
"conditional template" (? whatever it's called; I haven't used one of
these yet) instead. Unless you can runtime check that

Positive!(double) x = 6;
Positive!(double) y = 12;

Compile time check

Positive!(double) z = void;

This must be an syntax error surely?

type x = void; means don't initialize x. Or have I missed something?

z = x - y;  // raises error.

The return type of subtraction goes outside the postive domain:
i.e. if it needed to exist (which it probably doesn't) the function
spec would be:

double opMinus(Positive!(double) y, Positive!(double) y);

So this is actually:

z = cast(Positive!(double))(x - y)

Hence there is the necessary check which could be either run-time or
compile time.

Most of the time it can't be compile time because if I've initialized x
and y to be some runtime-dependent function (e.g. sin(current time))
then you can't be sure of the sign of x-y. So the check must be made
into runtime unless the expression can be CTFE-ed.

Positive!(double) w;
din.readf("%g", &w);  // raises error if user enters negative number.

But I don't think uint, etc now even do these checks.

This would ideally work as above but I see your problem.
The contract of readf is not tight enough. You should rewrite as:

double wtemp;
Positive!(double) w = wtemp;    // type check applied here

But this is getting ugly :)

Of course. It's because it uses the "!". :o)

Andrei

Oct 05 2008
KennyTM~ <kennytm gmail.com> writes:
Andrei Alexandrescu wrote:
KennyTM~ wrote:
On Sun, 05 Oct 2008 11:18:24 +0100, KennyTM~ <kennytm gmail.com> wrote:
Probably they'd used (0, +∞) and [0, +∞) instead.

---

BTW, negative real numbers can also be indicated as ℝ⁻ (R^- if
Unicode is not supported). Is it now special enough to deserve a
Negative!() template? :p

Nice use of unicode.

I think these sign checking should be done through contracts or
"conditional template" (? whatever it's called; I haven't used one
of these yet) instead. Unless you can runtime check that

Positive!(double) x = 6;
Positive!(double) y = 12;

Compile time check

Positive!(double) z = void;

This must be an syntax error surely?

type x = void; means don't initialize x. Or have I missed something?

z = x - y;  // raises error.

The return type of subtraction goes outside the postive domain:
i.e. if it needed to exist (which it probably doesn't) the function
spec would be:

double opMinus(Positive!(double) y, Positive!(double) y);

So this is actually:

z = cast(Positive!(double))(x - y)

Hence there is the necessary check which could be either run-time or
compile time.

Most of the time it can't be compile time because if I've initialized
x and y to be some runtime-dependent function (e.g. sin(current time))
then you can't be sure of the sign of x-y. So the check must be made
into runtime unless the expression can be CTFE-ed.

Positive!(double) w;
din.readf("%g", &w);  // raises error if user enters negative
number.

But I don't think uint, etc now even do these checks.

This would ideally work as above but I see your problem.
The contract of readf is not tight enough. You should rewrite as:

double wtemp;
Positive!(double) w = wtemp;    // type check applied here

But this is getting ugly :)

Of course. It's because it uses the "!". :o)

Andrei

I mean using temporary variable explicitly is ugly -_-

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
KennyTM~ wrote:
Walter Bright wrote:
Andrei Alexandrescu wrote:
About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.

I'm not a math major. But in college I took 4 years of math, up
through integration in the complex plane and branch cuts (which I
never did properly understand <g>). Every engineering/physics class
was a math class. I never saw this notation. I am not suggesting it
doesn't exist, just that it became commonplace fairly recently, or
that it isn't commonplace at least at the undergraduate level. This
plays into the numbers issue you mentioned.

Probably they'd used (0, +∞) and [0, +∞) instead.

Depends on the field. The problem is, either notation is hard to google for.

BTW, negative real numbers can also be indicated as ℝ⁻ (R^- if Unicode
is not supported). Is it now special enough to deserve a Negative!()
template? :p

Where I grew up I think the sign came as a subscript. This is because
the nonzero "*" sign could then be added as a superscript. The notations
I know of are (in TeX notation):

non-negative real numbers: R_+
non-zero real numbers: R^*
positive numbers: R_+^*

Rarely used (I never saw them, actually):

non-positive real numbers: R_-
negative numbers: R_-^*

Oh, I just realized that bounded numbers can't express nonzero real numbers.

I think these sign checking should be done through contracts or
"conditional template" (? whatever it's called; I haven't used one of
these yet) instead. Unless you can runtime check that

Positive!(double) x = 6;
Positive!(double) y = 12;
Positive!(double) z = void;
z = x - y;  // raises error.
Positive!(double) w;
din.readf("%g", &w);  // raises error if user enters negative number.

But I don't think uint, etc now even do these checks.

They don't because they have a slightly different purpose and charter.

Andrei

Oct 05 2008
On Sun, 05 Oct 2008 11:18:24 +0100, KennyTM~ <kennytm gmail.com> wrote:
Probably they'd used (0, +∞) and [0, +∞) instead.

---

BTW, negative real numbers can also be indicated as ℝ⁻ (R^- if Unicode
is not supported). Is it now special enough to deserve a Negative!()
template? :p

Nice use of unicode.

I think these sign checking should be done through contracts or
"conditional template" (? whatever it's called; I haven't used one of
these yet) instead. Unless you can runtime check that

Positive!(double) x = 6;
Positive!(double) y = 12;

Compile time check

Positive!(double) z = void;

This must be an syntax error surely?

z = x - y;  // raises error.

The return type of subtraction goes outside the postive domain:
i.e. if it needed to exist (which it probably doesn't) the function spec
would be:

double opMinus(Positive!(double) y, Positive!(double) y);

So this is actually:

z = cast(Positive!(double))(x - y)

Hence there is the necessary check which could be either run-time or
compile time.

Positive!(double) w;
din.readf("%g", &w);  // raises error if user enters negative number.

But I don't think uint, etc now even do these checks.

This would ideally work as above but I see your problem.
The contract of readf is not tight enough. You should rewrite as:

double wtemp;
Positive!(double) w = wtemp;    // type check applied here

--
Using Opera's revolutionary e-mail client: http://www.opera.com/mail/

Oct 05 2008
Sean Kelly <sean invisibleduck.org> writes:
Andrei Alexandrescu wrote:
Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

Sounds like range-restricted values, which people have been asking for
as a language feature for ages.  The idea has merit.

However, there is also the risk that Positive has the same fate the many
SafeInt implementation have had in C++: many defined them, nobody used
them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

See below.

In order to get things really started, there's already been an exchange
with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to Positive
in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

So you're saying the problem with contracts here is code duplication?
I'm not sure I follow.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more checks
are necessary.

To be fair, there's one check for each time such a value is constructed
or altered.  So you're simply assuming that the checked value will be
constructed and then never altered.  But how is this different from
using contracts?

I like the idea of checked values for safety, but I think efficiency
concerns would prevent me from using them for actual work.  For example,
let's say that I'm performing a bunch of computations.  I only really
want to check whether the result is in range--I don't care about the
intermediate values.  So I'd be inclined to forgo the use of checked
values for the actual work and simply return a checked type at the end.
But this is exactly how contracts work!  Why would I bother with
checked values if I can do the same checking in in/out clauses?

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.

It's clearly as important to describe the attributes of a variable in
math as it is in programming.  So mathematicians settled on the notation
you mention, and programmers have largely settled on the use of
contracts.  There may still be some value in more math-like notation in
programming, but I don't personally see much of a need for it in this
case.  Like Walter, I'd continue to use contracts unless some compelling
reason can be provided for using this notation instead.

Sean

Oct 04 2008
Ary Borenszweig <ary esperanto.org.ar> writes:
Andrei Alexandrescu escribi:
(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

For example:

Positive.(real) sqrt(Positive.(real) x);

I can't read that. I see a bunch of calls and casts. !() was a little
hard at first, but this is impossible.

Of course, this is just my opinion, I don't know what the others think

Another problem, from an IDE perspective: "Positive." will trigger
autocomplete of Positive's members, ugh.

Oct 04 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Sun, 05 Oct 2008 07:36:58 +0400, Ary Borenszweig <ary esperanto.org.ar>
wrote:
Another problem, from an IDE perspective: "Positive." will trigger
autocomplete of Positive's members, ugh.

Thumbs up! That's you all over :)

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Denis Koroskin wrote:
On Sun, 05 Oct 2008 07:36:58 +0400, Ary Borenszweig
<ary esperanto.org.ar> wrote:
Another problem, from an IDE perspective: "Positive." will trigger
autocomplete of Positive's members, ugh.

Thumbs up! That's you all over :)

Uninstantiated templates don't have members, except inside the template
itself. This is a non-issue.

Andrei

Oct 05 2008
Jason House <jason.james.house gmail.com> writes:
Andrei Alexandrescu Wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

I don't think .() is visually distinct enough, especially when property syntax
can be used.

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

It's interesting, but I'd use contracts instead. I'd use an ultra short
notation with no perceptible user impact (to save me typing). A not null type
is more interesting to me.

The implementation would accept conversion from its base type, e.g.
Positive.(real) can be constructed from a real. The constructor enforces
dynamically the condition. Also, Positive.(real) accepts implicit
conversion to real (no checking necessary).

There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

Ummm... That's not even the correct signature for square root. It should accept
non negative numbers.

These specifications are also efficient because checking for positivity
is no cascading checking necessary so there's one test less to do.

However, there is also the risk that Positive has the same fate the many
SafeInt implementation have had in C++: many defined them, nobody used
them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

In order to get things really started, there's already been an exchange
with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to Positive
in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more checks
are necessary.

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean something.
==============

I'm interesting in further arguments. This feature is a numbers issue
(pun not intended), meaning it will be any good only if enough people
find it useful enough to actually use it in their own code and
libraries, therefore building momentum behind it.

Andrei


Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Jason House wrote:
Andrei Alexandrescu Wrote:
Positive.(real) sqrt(Positive.(real) x);

Ummm... That's not even the correct signature for square root. It
should accept non negative numbers.

Rats. I was thinking positive means >= 0 and strictly positive means >
0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.

Andrei

Oct 04 2008
dsimcha <dsimcha yahoo.com> writes:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
Jason House wrote:
Andrei Alexandrescu Wrote:
Positive.(real) sqrt(Positive.(real) x);

Ummm... That's not even the correct signature for square root. It
should accept non negative numbers.

0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.
Andrei

Maybe create the templates as a back end using whatever name, and then create
typedefs/aliases for ufloat, udouble, ureal?  This would definitely be
consistent
with ints and easy to remember.

Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
Jason House wrote:
Andrei Alexandrescu Wrote:
Positive.(real) sqrt(Positive.(real) x);

should accept non negative numbers.

0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.
Andrei

Maybe create the templates as a back end using whatever name, and then create
typedefs/aliases for ufloat, udouble, ureal?  This would definitely be
consistent
with ints and easy to remember.

I think that's a great idea. So, the question becomes: how do people
feel about using ufloat, udouble, and ureal?

Andrei

Oct 04 2008
=?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes:
Andrei Alexandrescu wrote:
dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s
article
Jason House wrote:
Andrei Alexandrescu Wrote:
Positive.(real) sqrt(Positive.(real) x);

should accept non negative numbers.

0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.
Andrei

Maybe create the templates as a back end using whatever name, and then
create
typedefs/aliases for ufloat, udouble, ureal?  This would definitely be
consistent
with ints and easy to remember.

I think that's a great idea. So, the question becomes: how do people
feel about using ufloat, udouble, and ureal?

I’d even suggest putting those into the language as primitive types — I
just figured out they are not. Puzzled me a bit.

Oct 04 2008
=?ISO-8859-1?Q?Anders_F_Bj=F6rklund?= <afb algonet.se> writes:
Andrei Alexandrescu wrote:

Maybe create the templates as a back end using whatever name, and then
create
typedefs/aliases for ufloat, udouble, ureal?  This would definitely be
consistent
with ints and easy to remember.

I think that's a great idea. So, the question becomes: how do people
feel about using ufloat, udouble, and ureal?

I'll just insert my usual "real is not a type, but an alias"...

At least udouble is easier to understand than Positive.(double)

--anders

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Anders F Bjrklund wrote:
Andrei Alexandrescu wrote:

Maybe create the templates as a back end using whatever name, and
then create
typedefs/aliases for ufloat, udouble, ureal?  This would definitely
be consistent
with ints and easy to remember.

I think that's a great idea. So, the question becomes: how do people
feel about using ufloat, udouble, and ureal?

I'll just insert my usual "real is not a type, but an alias"...

I thought it's a real type. No?

At least udouble is easier to understand than Positive.(double)

The comparison was with Positive!(double). I'm Positive!

Andrei

Oct 05 2008
=?ISO-8859-1?Q?Anders_F_Bj=F6rklund?= <afb algonet.se> writes:
Andrei Alexandrescu wrote:

I'll just insert my usual "real is not a type, but an alias"...

I thought it's a real type. No?

No, "real" is an alias for "largest hardware implemented floating point
size". So it can be anything from 64 to 80 to 96 to 128 bits in size...

I dubbed the two underlying IEEE types "extended" (80) and "quad" (128),
as in "*** precision" (just like single precision and double precision)

At least udouble is easier to understand than Positive.(double)

The comparison was with Positive!(double). I'm Positive!

:-)

--anders

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Anders F Bjrklund wrote:
Andrei Alexandrescu wrote:

I'll just insert my usual "real is not a type, but an alias"...

I thought it's a real type. No?

No, "real" is an alias for "largest hardware implemented floating point
size". So it can be anything from 64 to 80 to 96 to 128 bits in size...

Yes, it's a type of unknown width. But it's a distinct type nontheless
for all I know. For example, even on a system that had 64-bit math, real
would be a distinct type from double even if they had the same size and
behavior.

Andrei

Oct 05 2008
=?ISO-8859-1?Q?Anders_F_Bj=F6rklund?= <afb algonet.se> writes:
Andrei Alexandrescu wrote:

No, "real" is an alias for "largest hardware implemented floating point
size". So it can be anything from 64 to 80 to 96 to 128 bits in size...

Yes, it's a type of unknown width. But it's a distinct type nontheless
for all I know. For example, even on a system that had 64-bit math, real
would be a distinct type from double even if they had the same size and
behavior.

Right, for all practical purposes it maps straight to C's "long double".

--anders

Oct 05 2008
"Peter C. Chapin" <pcc482719 gmail.com> writes:
Andrei Alexandrescu wrote:

Rats. I was thinking positive means >= 0 and strictly positive means >
0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.

Ada supports the ability to create new types from the primitive numeric
finds this useful and would appreciate the sort of feature you are
talking about. In Ada there are even two predefined subtypes of Integer

subtype Positive is Integer range 1 .. Integer'Last;
subtype Natural is Integer range 0 .. Integer'Last;

So for non-negative integers... what about "natural"?

Peter

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Peter C. Chapin wrote:
Andrei Alexandrescu wrote:

Rats. I was thinking positive means >= 0 and strictly positive means >
0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.

Ada supports the ability to create new types from the primitive numeric
finds this useful and would appreciate the sort of feature you are
talking about. In Ada there are even two predefined subtypes of Integer

subtype Positive is Integer range 1 .. Integer'Last;
subtype Natural is Integer range 0 .. Integer'Last;

So for non-negative integers... what about "natural"?

Well uint kinda occupied that space, although as we all know it's not
exactly a natural number.

I think the comparison with experience in Ada is sensible. I wished
there was a predefined subtipe of Real too...

Andrei

Oct 05 2008
"Denis Koroskin" <2korden gmail.com> writes:
On Sun, 05 Oct 2008 08:41:50 +0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

dsimcha wrote:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s
article
Jason House wrote:
Andrei Alexandrescu Wrote:
Positive.(real) sqrt(Positive.(real) x);

should accept non negative numbers.

0. According to Wikipedia, positive really means strictly positive and
the longer-to-type NonNegative should be used instead :o|. For such a
simple concept, a short and sweet name is pivotal. If there are any
ideas for a better choice, please make them known.
Andrei

create
typedefs/aliases for ufloat, udouble, ureal?  This would definitely be
consistent
with ints and easy to remember.

I think that's a great idea. So, the question becomes: how do people
feel about using ufloat, udouble, and ureal?

Andrei

much, Much, MUCH better! Especially once overflows would trigger
exceptions I believe these would become very valuable.

Oct 05 2008
=?UTF-8?B?QWxleGFuZGVyIFDDoW5law==?= writes:
Andrei Alexandrescu wrote:
There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

I think such restrictions/contracts are up to the implementation of an
interface. There’s no point in defining them with interfaces, besides
specific mathematical functions, which don’t play such big role in the
“real world” as far as I can tell.

These specifications are also efficient because checking for positivity
is no cascading checking necessary so there's one test less to do.

Same goes for contracts. It basically happens outside the body of the

However, there is also the risk that Positive has the same fate the many
SafeInt implementation have had in C++: many defined them, nobody used
them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

I wouldn’t, since I can’t seem to see the point of it — well, besides
trying to express mathematical notations in D, which in turn I find
pretty pointless..

About contracts: Let me explain how I think that's inferior to Positive
in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

I don’t think that the amount of functions defined as such really
justify such a kind of (additional) restriction option. Positivity can
be asserted by only accepting positive (unsigned) primitive types and a
null argument is asserted in a contract. Adding another layer of
restriction doesn’t make it any better. Especially not if you only need
it in a very specific set of functions.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more checks
are necessary.

Speaking mathematically correct, you can’t really let sqrt return a
signed, positive value, since every sqrt has two results — positive and
negative. There’s no point in restricting the return type to positive
and especially not signed values.

Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Alexander Pánek wrote:
Andrei Alexandrescu wrote:
There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

I think such restrictions/contracts are up to the implementation of an
interface. There’s no point in defining them with interfaces, besides
specific mathematical functions, which don’t play such big role in the
“real world” as far as I can tell.

Well we do use uint in the real world and we hope (partially in vain,
sigh) that it models natural numbers. Positive gives ufloat, udouble, or
ureal, as truly checked positive numbers. I mean nonnegative. Damn.

These specifications are also efficient because checking for
positivity is done outside sqrt; if you had a Positive.(real) to start
with, there is no cascading checking necessary so there's one test
less to do.

Same goes for contracts. It basically happens outside the body of the

No. Contracts are not foldable. Folding them could be in theory done by
the compiler, but requires nonscalable interprocedural analysis.

However, there is also the risk that Positive has the same fate the
many SafeInt implementation have had in C++: many defined them, nobody
used them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

I wouldn’t, since I can’t seem to see the point of it — well, besides
trying to express mathematical notations in D, which in turn I find
pretty pointless..

Why is that pointless? To the extent it's doable, it would only help.

About contracts: Let me explain how I think that's inferior to
Positive in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

I don’t think that the amount of functions defined as such really
justify such a kind of (additional) restriction option. Positivity can
be asserted by only accepting positive (unsigned) primitive types and a
null argument is asserted in a contract. Adding another layer of
restriction doesn’t make it any better. Especially not if you only need
it in a very specific set of functions.

No, this is a misunderstanding. There's no more need for sqrt to check
its argument - it's guaranteed to be nonnegative. That's the whole point
of the whole shtick.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more
checks are necessary.

Speaking mathematically correct, you can’t really let sqrt return a
signed, positive value, since every sqrt has two results — positive and
negative. There’s no point in restricting the return type to positive
and especially not signed values.

I think this is off. In pretty much all languages I know, sqrt for real
numbers never returns both roots. It returns the positive square root.

Andrei

Oct 04 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Graham St Jack wrote:
I prefer your suggestion of ufloat/udouble/ureal to Positive, and I
would definitely use these. I already use unsigned integer types a
LOT, even more than signed ones.

Have you thought how (and if) auto-casting would work?

I did, and it would work. The problem is there's no precedent for it.

double x;
...
auto y = sqrt(x);

That will do a runtime check and throw if x is negative. That's
unprecedented for an implicit cast, so I was thinking of defining a
universal "unsigned" template function that does the check:

auto y = sqrt(unsigned(x));

As far as template instantiation goes, my feeling is that the "." is
too easily confused with method invocation. I know you are trying to
make them look more similar, but for we mere mortals that don't do
much template programming, we need something that stand out more.
Something less alarming than "!" would be ok, so long as there was
ONLY ONE way.

I agree that in the end there should be only one man standing. And the
reference to mere mortals makes me think we should bring the mountain to
them instead of them to the mountain. I know, lame metaphor.

Andrei

Oct 04 2008
Michel Fortin <michel.fortin michelf.com> writes:
On 2008-10-05 01:55:43 -0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> said:

That will do a runtime check and throw if x is negative. That's
unprecedented for an implicit cast, so I was thinking of defining a
universal "unsigned" template function that does the check:

auto y = sqrt(unsigned(x));

Well, at this point I would prefer if it was a contract. Having to
explicitly convert to unsigned just makes it harder than necessary.

Throwing may be unprecedented for implict casts, but it is standard for
contracts using assertions. So I think it would be okay to implicit
cast and assert the value is non-negative (which would be equivalent to
enforcing a contract).

But then, shouldn't sqrt(-1) give you NaN, or i?

--
Michel Fortin
michel.fortin michelf.com
http://michelf.com/

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Michel Fortin wrote:
On 2008-10-05 01:55:43 -0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> said:

That will do a runtime check and throw if x is negative. That's
unprecedented for an implicit cast, so I was thinking of defining a
universal "unsigned" template function that does the check:

auto y = sqrt(unsigned(x));

Well, at this point I would prefer if it was a contract. Having to
explicitly convert to unsigned just makes it harder than necessary.

But the point is that often you already traffic in nonnegatives, so you
have them handy. Only passing the first time is difficult. But I hear
you. We can make the conversion implicit.

Throwing may be unprecedented for implict casts, but it is standard for
contracts using assertions. So I think it would be okay to implicit cast
and assert the value is non-negative (which would be equivalent to
enforcing a contract).

But then, shouldn't sqrt(-1) give you NaN, or i?

It can't yield i because i has a different type. It gives NaN now, and
believe me, that doesn't help any.

Andrei

Oct 05 2008
Graham St Jack <graham.stjack internode.on.net> writes:
I prefer your suggestion of ufloat/udouble/ureal to Positive,
and I would definitely use these. I already use unsigned integer
types a LOT, even more than signed ones.

Have you thought how (and if) auto-casting would work?

As far as template instantiation goes, my feeling is that
the "." is too easily confused with method invocation. I
know you are trying to make them look more similar, but
for we mere mortals that don't do much template programming,
we need something that stand out more. Something less alarming
than "!" would be ok, so long as there was ONLY ONE way.

Graham.

Oct 04 2008
On Sun, 05 Oct 2008 09:04:37 +0100, Michel Fortin
<michel.fortin michelf.com> wrote:

On 2008-10-05 01:55:43 -0400, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> said:

That will do a runtime check and throw if x is negative. That's
unprecedented for an implicit cast, so I was thinking of defining a
universal "unsigned" template function that does the check:
auto y = sqrt(unsigned(x));

Well, at this point I would prefer if it was a contract. Having to
explicitly convert to unsigned just makes it harder than necessary.

Throwing may be unprecedented for implict casts, but it is standard for
contracts using assertions. So I think it would be okay to implicit cast
and assert the value is non-negative (which would be equivalent to
enforcing a contract).

But then, shouldn't sqrt(-1) give you NaN, or i?

Depends on the type of argument.

For normal integers it should balk at compile time if possible and
assert/throw if necessary
For complex types i would make sense.
For IEEE real numbers the specification probably mandates some behaviour
such as NaN. Anyone read it recently?

Oct 05 2008
Andrei Alexandrescu wrote:
Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

The implementation would accept conversion from its base type, e.g.
Positive.(real) can be constructed from a real. The constructor enforces
dynamically the condition. Also, Positive.(real) accepts implicit
conversion to real (no checking necessary).

There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

These specifications are also efficient because checking for positivity
is no cascading checking necessary so there's one test less to do.

However, there is also the risk that Positive has the same fate the many
SafeInt implementation have had in C++: many defined them, nobody used
them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

In order to get things really started, there's already been an exchange
with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to Positive
in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more checks
are necessary.

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.
==============

I'm interesting in further arguments. This feature is a numbers issue
(pun not intended), meaning it will be any good only if enough people
find it useful enough to actually use it in their own code and
libraries, therefore building momentum behind it.

Andrei

As others have mentioned.

Why a second class form of range restriction?  Why not a first class
implementation like ADA's with ranges and subranges as specific
typedefs?  I know it would be more work for the compiler writer to
implement (if it can't be done in templates) however I prefer more
generic solutions then having many once-off solutions that crudely fit
together.

Being able to simply pick a type that is within the range needed would
save having to write contracts and static contracts all over the place.
It also a great form of documentation.  I would find that useful,
particularly when working with algorithms that traverse arrays in
specific sequences such as spacial data structures but need to maintain
certain constraints.

-Joel

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Janderson wrote:
Andrei Alexandrescu wrote:
Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

The implementation would accept conversion from its base type, e.g.
Positive.(real) can be constructed from a real. The constructor
enforces dynamically the condition. Also, Positive.(real) accepts
implicit conversion to real (no checking necessary).

There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

These specifications are also efficient because checking for
positivity is done outside sqrt; if you had a Positive.(real) to start
with, there is no cascading checking necessary so there's one test
less to do.

However, there is also the risk that Positive has the same fate the
many SafeInt implementation have had in C++: many defined them, nobody
used them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

In order to get things really started, there's already been an
exchange with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to
Positive in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more
checks are necessary.

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.
==============

I'm interesting in further arguments. This feature is a numbers issue
(pun not intended), meaning it will be any good only if enough people
find it useful enough to actually use it in their own code and
libraries, therefore building momentum behind it.

Andrei

As others have mentioned.

Why a second class form of range restriction?  Why not a first class
implementation like ADA's with ranges and subranges as specific
typedefs?  I know it would be more work for the compiler writer to
implement (if it can't be done in templates) however I prefer more
generic solutions then having many once-off solutions that crudely fit
together.

Being able to simply pick a type that is within the range needed would
save having to write contracts and static contracts all over the place.
It also a great form of documentation.  I would find that useful,
particularly when working with algorithms that traverse arrays in
specific sequences such as spacial data structures but need to maintain
certain constraints.

Making ufloat, udouble, ureal as instantiations of Bounded.(low, high)
is a great idea!

Andrei

Oct 05 2008
I would prefer a more general, ADA like, solution.

SUBTYPE Natural IS Integer RANGE 0 .. Integer'Last;
SUBTYPE NonNegFloat IS Float RANGE 0.0 .. Float'Last;
and also :
SUBTYPE CapitalLetter IS Character RANGE 'A' .. 'Z';

just my 2 euro cents;
Bjoern

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
BLS wrote:
I would prefer a more general, ADA like, solution.

SUBTYPE Natural IS Integer RANGE 0 .. Integer'Last;
SUBTYPE NonNegFloat IS Float RANGE 0.0 .. Float'Last;
and also :
SUBTYPE CapitalLetter IS Character RANGE 'A' .. 'Z';

just my 2 euro cents;
Bjoern

I think that's cool, particularly thinking that it can be done entirely
at library level.

Andrei

Oct 05 2008
On Sun, 05 Oct 2008 03:35:57 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

the positive
template to be the focus of attention. As soon as I saw it, I anticipated
the usual
'enflamed discussion'. Didn't you? or was that part of the plan?
Anyway, I am glad some people did eventually get back to your main
question.

[snip]
In order to get things really started, there's already been an exchange
with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to Positive
in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more checks
are necessary.

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.
==============

I'm interesting in further arguments. This feature is a numbers issue
(pun not intended), meaning it will be any good only if enough people
find it useful enough to actually use it in their own code and
libraries, therefore building momentum behind it.

Andrei

As at least one other pointed out.
* means x >= 0 i.e. non negative
+ means x > 0 i.e. strictly positive

I think it is useful to support sub-typing as you suggest. Moreover, I
would
like to see more subtypes. Including things like Negative NegativeOrZero,
and Odd
or Even but not six of fifteen. Prime will be too expensive to check but
it might
still be useful. Its probably better to leave that to people to create
when they
find it useful.

Generalised range restricted sub-types would be a real boon.

I don't see what the problem is with proliferating types. If you have a
function
that works on a restricted range then declaring that makes sense.

Regarding the name I have no good suggestions. There is "Unsigned" which
is a C-ism
that is out of kilter with the mathematical intent. There is "Cardinal"
which is
under rated outside of Modula derived languages but includes only whole
numbers.
Actually I think "Cardinal" would be a useful addition in its own right.

I think subtyping is orthogonal to declaring a contract. Contracts apply to
functions whereas this is a type declaration.
Also you can use it to be more concise in your contracts. To declare that
two non-negative
numbers are greater than each other you could just write:

NonNegative!(x) > NonNegative!(y)

If this is going to end up in a std library why is it a problem if few
people use it?
It is better that it is there and that people are aware of it than that
people go down
separate paths in solving the same problem at a later stage. Perhaps a more
interesting question is how will you be using it?

A second use I can see is selecting two different implementations at
compile time.
A (possibly faster) one for when the contract is supported and a slower or
just different
one when the type contract is not met.

Going back to the sqrt example. Do you propose to change the library
declaration to

NonNegative!(numberType) sqrt( NonNegative!(numberType) X,
NonNegative!(numberType) Y);

Presumably changes like this are the real reason you want more feedback?

My understanding of what you propose is:

This is slightly less readable than using contracts but it is a more
precise definition
of the interface.

Implicit type conversion would test the positivity in calls at compile
time if possible
but otherwise at runtime when necessary.
The internal implementation of square root would not use the type
constructor as it knows it answer
will be positive. It could end with a cast to NonNegative to avoid the
unnecessary test or
more likely always be using NonNegative numbers inside.
Internal temporaries would be checked at compile time (when initialised to
a compile time constant value)
so there would be no added cost to implementing sqrt only using it with
values that might
be negative.

If my understanding is correct you are proposing this mainly because
unlike contracts,
templates are checked by the compiler at compile time.
I suspect that is the real problem. I and others have previously tried to
argue for compile
time checkable contracts.
Another advantage of compile time contracts is that you can design and
test arbitrary new
categories of type without having to add new type specifiers to the
const and pure here. Though pure would require functions to have visible
compile time attributes
(as opposed to the purely invisible ones which must exist internally)
which is another kettle of fish.

Regards,

Bruce.


Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Bruce Adams wrote:
On Sun, 05 Oct 2008 03:35:57 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

template to be the focus of attention. As soon as I saw it, I
anticipated the usual
'enflamed discussion'. Didn't you? or was that part of the plan?
Anyway, I am glad some people did eventually get back to your main
question.

I didn't expect that much hubbub.

In order to get things really started, there's already been an
exchange with Walter on the matter. His reply was (I haven't asked for
permission, but I'm pretty sure he'd agree making it public):

==============
Honestly, I wouldn't use it. I'd rather have an in contract for sqrt
that asserts the argument is positive. Also, this opens the door to
Negative, NegativeOrZero, ZeroOrInfinity, Odd, Even, Prime,
SixOrFifteen, etc.
==============

==============
About contracts: Let me explain how I think that's inferior to
Positive in two ways.

1. Enough functions are defined on positive numbers only, to justify
factoring that contract out of the functions themselves.

2. The efficiency perk is that when using several such functions
together, there's only one check; once in Positive-land, no more
checks are necessary.

About proliferation of types: I don't think that follows at all. Math
found positive numbers special enough to dedicate them a special
notation (|R with subscript "+"). There's also a special notation for
nonzero real numbers (|R with superscript "*"). There is no special
notation for any of the sets you mentioned. That is bound to mean
something.
==============

I'm interesting in further arguments. This feature is a numbers issue
(pun not intended), meaning it will be any good only if enough people
find it useful enough to actually use it in their own code and
libraries, therefore building momentum behind it.

Andrei

As at least one other pointed out.
* means x >= 0 i.e. non negative
+ means x > 0 i.e. strictly positive

Ok.

I think it is useful to support sub-typing as you suggest. Moreover, I
would
like to see more subtypes. Including things like Negative
NegativeOrZero, and Odd
or Even but not six of fifteen. Prime will be too expensive to check but
it might
still be useful. Its probably better to leave that to people to create
when they
find it useful.

Generalised range restricted sub-types would be a real boon.

I don't see what the problem is with proliferating types. If you have a
function
that works on a restricted range then declaring that makes sense.

Regarding the name I have no good suggestions. There is "Unsigned" which
is a C-ism
that is out of kilter with the mathematical intent. There is "Cardinal"
which is
under rated outside of Modula derived languages but includes only whole
numbers.
Actually I think "Cardinal" would be a useful addition in its own right.

I think subtyping is orthogonal to declaring a contract. Contracts apply to
functions whereas this is a type declaration.
Also you can use it to be more concise in your contracts. To declare
that two non-negative
numbers are greater than each other you could just write:

NonNegative!(x) > NonNegative!(y)

If this is going to end up in a std library why is it a problem if few
people use it?
It is better that it is there and that people are aware of it than that
people go down
separate paths in solving the same problem at a later stage. Perhaps a more
interesting question is how will you be using it?

A second use I can see is selecting two different implementations at
compile time.
A (possibly faster) one for when the contract is supported and a slower
or just different
one when the type contract is not met.

These are excellent insights, thanks!

Going back to the sqrt example. Do you propose to change the library
declaration to

NonNegative!(numberType) sqrt( NonNegative!(numberType) X,
NonNegative!(numberType) Y);

Presumably changes like this are the real reason you want more feedback?

Yah. But what is the second argument for?

My understanding of what you propose is:

This is slightly less readable than using contracts but it is a more
precise definition
of the interface.

Yes. The contract goes out of the bowels of the function and from the
documentation, straight in the interface of the function.

Implicit type conversion would test the positivity in calls at compile
time if possible
but otherwise at runtime when necessary.

Yes.

The internal implementation of square root would not use the type
constructor as it knows it answer
will be positive.

Yes. (Wow I didn't think of that one!)

It could end with a cast to NonNegative to avoid the
unnecessary test or
more likely always be using NonNegative numbers inside.

Correct.

Internal temporaries would be checked at compile time (when initialised
to a compile time constant value)
so there would be no added cost to implementing sqrt only using it with
values that might
be negative.

That can't be done in the current language, sigh.

If my understanding is correct you are proposing this mainly because
unlike contracts,
templates are checked by the compiler at compile time.
I suspect that is the real problem. I and others have previously tried
to argue for compile
time checkable contracts.
Another advantage of compile time contracts is that you can design and
test arbitrary new
categories of type without having to add new type specifiers to the
const and pure here. Though pure would require functions to have visible
compile time attributes
(as opposed to the purely invisible ones which must exist internally)
which is another kettle of fish.

I'd love compile-time-checked contracts, but they're simply not doable
with current compiler technology.

Andrei

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Bruce Adams wrote:
On Sun, 05 Oct 2008 15:12:13 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:
Internal temporaries would be checked at compile time (when
initialised to a compile time constant value)
so there would be no added cost to implementing sqrt only using it
with values that might
be negative.

That can't be done in the current language, sigh.

Positive!(int) x = 1;

Not currently.

If my understanding is correct you are proposing this mainly because
unlike contracts,
templates are checked by the compiler at compile time.
I suspect that is the real problem. I and others have previously
tried to argue for compile
time checkable contracts.
Another advantage of compile time contracts is that you can design
and test arbitrary new
categories of type without having to add new type specifiers to the
const and pure here. Though pure would require functions to have
visible compile time attributes
(as opposed to the purely invisible ones which must exist internally)
which is another kettle of fish.

I'd love compile-time-checked contracts, but they're simply not doable
with current compiler technology.

Andrei

I disagree. I'm not saying its easy but it could be done. We would have
to start
with something relatively simple and work our way up but it could be done.

I, too, think it can be done in the same way supersonic mass
transportation can be done, but having done research in the area I can
tell you you are grossly underestimating the difficulties. It is a
project of gargantuan size. Today the most advanced systems only managed
to automatically prove facts that look rather trivial to the casual
reader. There is absolutely no hope for D to embark on this.

Compiler's already do all kinds of clever analyses behind the scenes but
each one
is often hard coded. I suspect the main difficulty is giving users too
much rope
by which to hang themselves, or rather hang the compiler trying to prove
something
it doesn't realise it can't. Marrying declarative / constraint based
programming
at compile time is creeping in via templates. I wish it was less well
hidden.

I discussed the problem this morning with Walter and he also started
rather cocky: if you assert something early on, you can from then on
assume the assertion is true (assuming no assignment took place, which
is not hard if you have CFA in place). He got an arrow in a molar with
the following example:

double[] vec;
foreach (e; vec) assert(e >= 0);
// now we know vec is all nonnegatives
normalize(vec);

The definition of normalize is:

void normalize(double[] vec)
{
foreach (e; vec) assert(e >= 0);
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

If normalize takes udouble[] and you have one of those, there's no need
to recheck. Automated elimination of the checking loop above is really hard.

Andrei

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
Bruce Adams wrote:
On Mon, 06 Oct 2008 00:55:33 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:
Andrei

have to start
with something relatively simple and work our way up but it could be
done.

I, too, think it can be done in the same way supersonic mass
transportation can be done, but having done research in the area I can
tell you you are grossly underestimating the difficulties. It is a
project of gargantuan size. Today the most advanced systems only managed
to automatically prove facts that look rather trivial to the casual
reader. There is absolutely no hope for D to embark on this.

even the
simple cases is a start.
I agree that D won't have this (any time soon) but mainly because there
are several hundred things higher up the priority list.

Compiler's already do all kinds of clever analyses behind the scenes
but each one
is often hard coded. I suspect the main difficulty is giving users
too much rope
by which to hang themselves, or rather hang the compiler trying to
prove something
it doesn't realise it can't. Marrying declarative / constraint based
programming
at compile time is creeping in via templates. I wish it was less well
hidden.

I discussed the problem this morning with Walter and he also started
rather cocky: if you assert something early on, you can from then on
assume the assertion is true (assuming no assignment took place, which
is not hard if you have CFA in place). He got an arrow in a molar with
the following example:

double[] vec;
foreach (e; vec) assert(e >= 0);
// now we know vec is all nonnegatives
normalize(vec);

The definition of normalize is:

void normalize(double[] vec)
{
foreach (e; vec) assert(e >= 0);
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

If normalize takes udouble[] and you have one of those, there's no
need to recheck. Automated elimination of the checking loop above is
really hard.

Andrei

Is it? I think your example needs to be expanded or we may be talking
at cross purposes.
Firstly I would rearrange things a little, though in principle it makes
no difference.

pre
{
static assert(foreach (e; vec) assert(e >= 0));
}
void normalize(double[] vec)
{
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

// now we know vec is all nonnegatives
normalize(vec);   // line Y

Imagine I have a prolog style symbolic unification engine to hand inside
my compiler.

At line X the static assertion is evaluated.
The logical property e>=0 is asserted on the vec symbol.
The compiler reaches line Y.
Vec has not been modified so still has this property associated with it.
We now unify the symbol representing vec with the contract on normalise.
The unification succeeds and everything is fine.

Now imagine we have a stupid analyser.

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

vec[0] -= 1; // line Z

// now we know vec is all nonnegatives
normalize(vec);   // line Y

when the compile time analyser reaches line Z it can't work out whether
or not the
contract still applies, so it removes the assertion that vec is e>=0 for
all elements, or
rather asserts that it is not provably true.
Now when we reach Y the unification fails.
We don't throw a compile time contraint violation error. We haven't
proved it to have failed.
We throw a compile time constraint unprovable error or warning.

Its like a lint warning. Your code may not be wrong but you might want
to consider altering it
in a way that makes it provably correct.

We would really like to be able to assert that certain properties always
hold for a variable
through its life-time. That is a harder problem.

I see something like this as a basis on which more advanced analysis can

Actually re-using static assert above was probably misleading. It would
be better to have something
that says talk to the compile time theorem prover (a prolog interpreter
would do).

I have been meaning to write something along these lines for years but
so far I haven't got around to it
so I might as well stop keeping it under my hat.

Regards,

Bruce.

I think it's terrific to try your hand at it. I for one know am not
equipped for such a pursuit. I have no idea how to perform unification
over loops, particularly when they may have myriads of little
differences while still having the same semantics; how to do that
cross-procedurally in reasonable time; how to take control flow
sensitivity into account; and why exactly people who've worked hard at
it haven't gotten very far. But I am equipped to define a type that
enforces all that simply and clearly, today.

Andrei

Oct 05 2008
Andrei Alexandrescu wrote:
On Mon, 06 Oct 2008 00:55:33 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:
Andrei

have to start
with something relatively simple and work our way up but it could be
done.

I, too, think it can be done in the same way supersonic mass
transportation can be done, but having done research in the area I can
tell you you are grossly underestimating the difficulties. It is a
project of gargantuan size. Today the most advanced systems only managed
to automatically prove facts that look rather trivial to the casual
reader. There is absolutely no hope for D to embark on this.

even the
simple cases is a start.
I agree that D won't have this (any time soon) but mainly because there
are several hundred things higher up the priority list.

Compiler's already do all kinds of clever analyses behind the scenes
but each one
is often hard coded. I suspect the main difficulty is giving users
too much rope
by which to hang themselves, or rather hang the compiler trying to
prove something
it doesn't realise it can't. Marrying declarative / constraint based
programming
at compile time is creeping in via templates. I wish it was less
well hidden.

I discussed the problem this morning with Walter and he also started
rather cocky: if you assert something early on, you can from then on
assume the assertion is true (assuming no assignment took place, which
is not hard if you have CFA in place). He got an arrow in a molar with
the following example:

double[] vec;
foreach (e; vec) assert(e >= 0);
// now we know vec is all nonnegatives
normalize(vec);

The definition of normalize is:

void normalize(double[] vec)
{
foreach (e; vec) assert(e >= 0);
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

If normalize takes udouble[] and you have one of those, there's no
need to recheck. Automated elimination of the checking loop above is
really hard.

Andrei

Is it? I think your example needs to be expanded or we may be talking
at cross purposes.
Firstly I would rearrange things a little, though in principle it makes
no difference.

pre
{
static assert(foreach (e; vec) assert(e >= 0));
}
void normalize(double[] vec)
{
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

// now we know vec is all nonnegatives
normalize(vec);   // line Y

Imagine I have a prolog style symbolic unification engine to hand
inside my compiler.

At line X the static assertion is evaluated.
The logical property e>=0 is asserted on the vec symbol.
The compiler reaches line Y.
Vec has not been modified so still has this property associated with it.
We now unify the symbol representing vec with the contract on normalise.
The unification succeeds and everything is fine.

Now imagine we have a stupid analyser.

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

vec[0] -= 1; // line Z

// now we know vec is all nonnegatives
normalize(vec);   // line Y

when the compile time analyser reaches line Z it can't work out
whether or not the
contract still applies, so it removes the assertion that vec is e>=0
for all elements, or
rather asserts that it is not provably true.
Now when we reach Y the unification fails.
We don't throw a compile time contraint violation error. We haven't
proved it to have failed.
We throw a compile time constraint unprovable error or warning.

Its like a lint warning. Your code may not be wrong but you might want
to consider altering it
in a way that makes it provably correct.

We would really like to be able to assert that certain properties
always hold for a variable
through its life-time. That is a harder problem.

I see something like this as a basis on which more advanced analysis

Actually re-using static assert above was probably misleading. It
would be better to have something
that says talk to the compile time theorem prover (a prolog
interpreter would do).

I have been meaning to write something along these lines for years but
so far I haven't got around to it
so I might as well stop keeping it under my hat.

Regards,

Bruce.

I think it's terrific to try your hand at it. I for one know am not
equipped for such a pursuit. I have no idea how to perform unification
over loops, particularly when they may have myriads of little
differences while still having the same semantics; how to do that
cross-procedurally in reasonable time; how to take control flow
sensitivity into account; and why exactly people who've worked hard at
it haven't gotten very far. But I am equipped to define a type that
enforces all that simply and clearly, today.

Andrei

I'm not an expert at optimizers, but I do read a whole lot.  This type
of analysis is often call 'value range propagation'.  Tracking the
possible values for data as it flows around and eliminating checks based
on prior events.  Most modern compilers do some amount of it.  The
question is how much and under what circumstances.  I'm not sure how
many combine that with static value analysis to create multiple function
versions.  IE, 'enough' callers to justify emitting two different forms
of the function, each with different base assumptions about the incoming
data and adjusting call sites.  I know that some compilers do that for
known constant values.  I guess it's something halfway to inlining.

I can guess at what dmd's backend does.. or rather doesn't do. :)

Later,

Oct 05 2008
Reply to Andrei,

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

I think the runtime/compiletime distinction is important, sort of for the
same reason that cast(T) is used (make things stand out, but Re '!' not as

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
BCS wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

I think the runtime/compiletime distinction is important, sort of for
the same reason that cast(T) is used (make things stand out, but Re '!'

This has been discussed. Implicit function template instantiation and
compile-time function evaluation have been successful partly because
they unify the run-time and the compile-time realms.

Andrei

Oct 05 2008
Reply to Andrei,

BCS wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to
the ugly "!()" for template argument specifications.)

I think the runtime/compiletime distinction is important, sort of for
the same reason that cast(T) is used (make things stand out, but Re
'!' not as a bad thing).

compile-time function evaluation have been successful partly because
they unify the run-time and the compile-time realms.

Andrei

Yes they are good because they unify the implementation of RT&CT but that's
not what I'm referring to. What I am liking is the disjunction between the
use of them. I want to be able to look at a block of code and see at a glance
that it will collapse to nothing in the executable or get put in as code
to get executed.

Oct 05 2008
Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
BCS wrote:

BCS wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to
the ugly "!()" for template argument specifications.)

I think the runtime/compiletime distinction is important, sort of for
the same reason that cast(T) is used (make things stand out, but Re
'!' not as a bad thing).

compile-time function evaluation have been successful partly because
they unify the run-time and the compile-time realms.

Andrei

Yes they are good because they unify the implementation of RT&CT but
that's not what I'm referring to. What I am liking is the disjunction
between the use of them. I want to be able to look at a block of code
and see at a glance that it will collapse to nothing in the executable
or get put in as code to get executed.

Well I guess it all depends on how hard the glance is and how sharp your
eye is... :o)

Andrei

Oct 05 2008
Reply to Andrei,

Well I guess it all depends on how hard the glance is and how sharp

Andrei

Easier is better. I'd rather spend my time and effort on other things.

Oct 06 2008
On Sun, 05 Oct 2008 15:12:13 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

On Sun, 05 Oct 2008 03:35:57 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:

Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

template to be the focus of attention. As soon as I saw it, I
anticipated the usual
'enflamed discussion'. Didn't you? or was that part of the plan?
Anyway, I am glad some people did eventually get back to your main
question.

I didn't expect that much hubbub.

Going back to the sqrt example. Do you propose to change the library
declaration to
NonNegative!(numberType) sqrt( NonNegative!(numberType) X,
NonNegative!(numberType) Y);
Presumably changes like this are the real reason you want more
feedback?

Yah. But what is the second argument for?

thoroughly. :)

Internal temporaries would be checked at compile time (when initialised
to a compile time constant value)
so there would be no added cost to implementing sqrt only using it with
values that might
be negative.

That can't be done in the current language, sigh.

Positive!(int) x = 1;

If my understanding is correct you are proposing this mainly because
unlike contracts,
templates are checked by the compiler at compile time.
I suspect that is the real problem. I and others have previously tried
to argue for compile
time checkable contracts.
Another advantage of compile time contracts is that you can design and
test arbitrary new
categories of type without having to add new type specifiers to the
const and pure here. Though pure would require functions to have
visible compile time attributes
(as opposed to the purely invisible ones which must exist internally)
which is another kettle of fish.

I'd love compile-time-checked contracts, but they're simply not doable
with current compiler technology.

Andrei

I disagree. I'm not saying its easy but it could be done. We would have to
start
with something relatively simple and work our way up but it could be done.
Compiler's already do all kinds of clever analyses behind the scenes but
each one
is often hard coded. I suspect the main difficulty is giving users too
much rope
by which to hang themselves, or rather hang the compiler trying to prove
something
it doesn't realise it can't. Marrying declarative / constraint based
programming
at compile time is creeping in via templates. I wish it was less well
hidden.

Regards,

Bruce.

Oct 05 2008
On Mon, 06 Oct 2008 00:55:33 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:
Andrei

have to start
with something relatively simple and work our way up but it could be
done.

I, too, think it can be done in the same way supersonic mass
transportation can be done, but having done research in the area I can
tell you you are grossly underestimating the difficulties. It is a
project of gargantuan size. Today the most advanced systems only managed
to automatically prove facts that look rather trivial to the casual
reader. There is absolutely no hope for D to embark on this.

the
simple cases is a start.
I agree that D won't have this (any time soon) but mainly because there
are several hundred things higher up the priority list.

Compiler's already do all kinds of clever analyses behind the scenes
but each one
is often hard coded. I suspect the main difficulty is giving users too
much rope
by which to hang themselves, or rather hang the compiler trying to
prove something
it doesn't realise it can't. Marrying declarative / constraint based
programming
at compile time is creeping in via templates. I wish it was less well
hidden.

I discussed the problem this morning with Walter and he also started
rather cocky: if you assert something early on, you can from then on
assume the assertion is true (assuming no assignment took place, which
is not hard if you have CFA in place). He got an arrow in a molar with
the following example:

double[] vec;
foreach (e; vec) assert(e >= 0);
// now we know vec is all nonnegatives
normalize(vec);

The definition of normalize is:

void normalize(double[] vec)
{
foreach (e; vec) assert(e >= 0);
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

If normalize takes udouble[] and you have one of those, there's no need
to recheck. Automated elimination of the checking loop above is really
hard.

Andrei

Is it? I think your example needs to be expanded or we may be talking
at cross purposes.
Firstly I would rearrange things a little, though in principle it makes
no difference.

pre
{
static assert(foreach (e; vec) assert(e >= 0));
}
void normalize(double[] vec)
{
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

// now we know vec is all nonnegatives
normalize(vec);   // line Y

Imagine I have a prolog style symbolic unification engine to hand inside
my compiler.

At line X the static assertion is evaluated.
The logical property e>=0 is asserted on the vec symbol.
The compiler reaches line Y.
Vec has not been modified so still has this property associated with it.
We now unify the symbol representing vec with the contract on normalise.
The unification succeeds and everything is fine.

Now imagine we have a stupid analyser.

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

vec[0] -= 1; // line Z

// now we know vec is all nonnegatives
normalize(vec);   // line Y

when the compile time analyser reaches line Z it can't work out whether or
not the
contract still applies, so it removes the assertion that vec is e>=0 for
all elements, or
rather asserts that it is not provably true.
Now when we reach Y the unification fails.
We don't throw a compile time contraint violation error. We haven't proved
it to have failed.
We throw a compile time constraint unprovable error or warning.

Its like a lint warning. Your code may not be wrong but you might want to
consider altering it
in a way that makes it provably correct.

We would really like to be able to assert that certain properties always
hold for a variable
through its life-time. That is a harder problem.

I see something like this as a basis on which more advanced analysis can

Actually re-using static assert above was probably misleading. It would be
better to have something
that says talk to the compile time theorem prover (a prolog interpreter
would do).

I have been meaning to write something along these lines for years but so
far I haven't got around to it
so I might as well stop keeping it under my hat.

Regards,

Bruce.

Oct 05 2008
On Mon, 06 Oct 2008 06:17:44 +0100, Brad Roberts <braddr puremagic.com>
wrote:

Andrei Alexandrescu wrote:
On Mon, 06 Oct 2008 00:55:33 +0100, Andrei Alexandrescu
<SeeWebsiteForEmail erdani.org> wrote:
Andrei

have to start
with something relatively simple and work our way up but it could be
done.

I, too, think it can be done in the same way supersonic mass
transportation can be done, but having done research in the area I can
tell you you are grossly underestimating the difficulties. It is a
project of gargantuan size. Today the most advanced systems only
managed
to automatically prove facts that look rather trivial to the casual
reader. There is absolutely no hope for D to embark on this.

even the
simple cases is a start.
I agree that D won't have this (any time soon) but mainly because there
are several hundred things higher up the priority list.

Compiler's already do all kinds of clever analyses behind the scenes
but each one
is often hard coded. I suspect the main difficulty is giving users
too much rope
by which to hang themselves, or rather hang the compiler trying to
prove something
it doesn't realise it can't. Marrying declarative / constraint based
programming
at compile time is creeping in via templates. I wish it was less
well hidden.

I discussed the problem this morning with Walter and he also started
rather cocky: if you assert something early on, you can from then on
assume the assertion is true (assuming no assignment took place, which
is not hard if you have CFA in place). He got an arrow in a molar with
the following example:

double[] vec;
foreach (e; vec) assert(e >= 0);
// now we know vec is all nonnegatives
normalize(vec);

The definition of normalize is:

void normalize(double[] vec)
{
foreach (e; vec) assert(e >= 0);
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

If normalize takes udouble[] and you have one of those, there's no
need to recheck. Automated elimination of the checking loop above is
really hard.

Andrei

Is it? I think your example needs to be expanded or we may be talking
at cross purposes.
Firstly I would rearrange things a little, though in principle it makes
no difference.

pre
{
static assert(foreach (e; vec) assert(e >= 0));
}
void normalize(double[] vec)
{
auto sum = reduce "a + b"(vec, 0);
assert(sum > 0);
foreach (ref e; vec) e /= sum;
}

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

// now we know vec is all nonnegatives
normalize(vec);   // line Y

Imagine I have a prolog style symbolic unification engine to hand
inside my compiler.

At line X the static assertion is evaluated.
The logical property e>=0 is asserted on the vec symbol.
The compiler reaches line Y.
Vec has not been modified so still has this property associated with
it.
We now unify the symbol representing vec with the contract on
normalise.
The unification succeeds and everything is fine.

Now imagine we have a stupid analyser.

double[] vec;
static assert(foreach (e; vec) assert(e >= 0));  // line X

vec[0] -= 1; // line Z

// now we know vec is all nonnegatives
normalize(vec);   // line Y

when the compile time analyser reaches line Z it can't work out
whether or not the
contract still applies, so it removes the assertion that vec is e>=0
for all elements, or
rather asserts that it is not provably true.
Now when we reach Y the unification fails.
We don't throw a compile time contraint violation error. We haven't
proved it to have failed.
We throw a compile time constraint unprovable error or warning.

Its like a lint warning. Your code may not be wrong but you might want
to consider altering it
in a way that makes it provably correct.

We would really like to be able to assert that certain properties
always hold for a variable
through its life-time. That is a harder problem.

I see something like this as a basis on which more advanced analysis

Actually re-using static assert above was probably misleading. It
would be better to have something
that says talk to the compile time theorem prover (a prolog
interpreter would do).

I have been meaning to write something along these lines for years but
so far I haven't got around to it
so I might as well stop keeping it under my hat.

Regards,

Bruce.

I think it's terrific to try your hand at it. I for one know am not
equipped for such a pursuit. I have no idea how to perform unification
over loops, particularly when they may have myriads of little
differences while still having the same semantics; how to do that
cross-procedurally in reasonable time; how to take control flow
sensitivity into account; and why exactly people who've worked hard at
it haven't gotten very far. But I am equipped to define a type that
enforces all that simply and clearly, today.

Andrei

I'm not an expert at optimizers, but I do read a whole lot.  This type
of analysis is often call 'value range propagation'.  Tracking the
possible values for data as it flows around and eliminating checks based
on prior events.  Most modern compilers do some amount of it.  The
question is how much and under what circumstances.  I'm not sure how
many combine that with static value analysis to create multiple function
versions.  IE, 'enough' callers to justify emitting two different forms
of the function, each with different base assumptions about the incoming
data and adjusting call sites.  I know that some compilers do that for
known constant values.  I guess it's something halfway to inlining.

I can guess at what dmd's backend does.. or rather doesn't do. :)

Later,

Perhaps more can be done with LLVM.

I was actually suggesting something more radical than this. Having a turing
structures
used to represent the data flow analysis. This is what I mean by rope
enough
to hang yourself by. This isn't done currently for many reasons.
1. its a sledgehammer to crack a nut (though it is more general purpose)
- as Andrei points out he can do myriad useful things today without this
2. compiler authors are rightly uneasy about exposing internal
data-structures at compile time
3. compiler authors are rightly uneasy permitting activities that can
potential
result in longer compile times and especially infinitely long compile
times (though templates
make this possible)
4. many programmers are uneasy about marrying different programming styles.
One of D's successes is actually in making template meta-programming more
like regular procedural/functional
OO programming and less like pattern matching / logical / declarative
programming.
That makes it more comprehendable to the masses which is a good thing.
But it also hides the possibility of slipping a constraint solver in there.
Though I don't think the CTFE system and templates are powerful enough to
write an interpreter in.
are constant expressions.
It would be unnecessarily challenging to make this state mutable from
different places in the program,
if its even possible. This is where a multi-level language might win.

I like the idea of possibly generating two different function
implementations internally for the
internal optimizer. However, I was suggesting the analysis is focused on
contracts at interface boundaries.

Regards,

Bruce.

Oct 06 2008
Don <nospam nospam.com.au> writes:
Andrei Alexandrescu wrote:
Hello,

(Background: Walter has kindly allowed ".()" as an alternative to the
ugly "!()" for template argument specifications.)

Just a quick question - I am feeling an increasing desire to add a
template called Positive to std.typecons. Then Positive.(real) would
restrict its values to only positive real numbers etc.

The implementation would accept conversion from its base type, e.g.
Positive.(real) can be constructed from a real. The constructor enforces
dynamically the condition. Also, Positive.(real) accepts implicit
conversion to real (no checking necessary).

There are many places in which Positive can be useful, most notably
specifications of interfaces. For example:

Positive.(real) sqrt(Positive.(real) x);

From the IEEE definition of sqrt(x), x can be >=0, which includes -0.
For negative zero, the return result is -0.
However, not all positive-valued functions will accept -0 as an
argument. They also vary in whether or not they will accept an infinity
or a NaN.
So there's an annoying bit of complication.

These specifications are also efficient because checking for positivity
is no cascading checking necessary so there's one test less to do.

However, there is also the risk that Positive has the same fate the many
SafeInt implementation have had in C++: many defined them, nobody used
them. What do you think? If you had Positive in std and felt like
crunching some numbers, would you use it?

I think it probably is similar to SafeInt in C++. It just doesn't add
enough value. Essentially, it allows you to drop some trivial contracts.
But I don't think it scales particularly well. As math functions gain
more arguments, the relationships in the 'in' contracts tend to get more
complicated.

Much more useful would be positive int. Meaning, the top bit of the int
is always 0, which is a completely different concept to uint. Then we
could have implicit conversion from posint -> int and posint -> uint,
and disallow conversions between int <-> uint.

But really I'd like to see polysemous types first...

Oct 06 2008
e-t172 <e-t172 akegroup.org> writes:
Content-Type: text/plain; charset=UTF-8; format=flowed
Content-Transfer-Encoding: quoted-printable

Andrei Alexandrescu a =C3=A9crit :
"enum" as the way to declare manifest constants were much more ugly th=

"!(", and most of the people were against it. I don't see why ".(" sho=

be introduced.

Ugly or not, enumerated symbols were manifest constants to begin with. =

Sure. However manifest constants weren't enumerated symbols to begin with=
=2E

--=20
Etienne Dechamps / e-t172 - AKE Group

Website: http://www.e-t172.net/
Contact: e-t172 akegroup.org

Phone: +33547414942

Oct 06 2008