June 05, 2004
"Kevin Bealer" <Kevin_member@pathlink.com> escribió en el mensaje
news:c9qm08$1mkv$1@digitaldaemon.com
| Using opCall for non-new applications is only confusing if you typically
| overload the opCall to mean "new".  The normal use of opCall (in my
opinion) is
| as a "functor", i.e. "operator()" in C++.  Suppose I have a function:
|
| flip(int a)
| {
| ..
| }
|
| ..and code that calls it.  I can make it into an object, which is then
used as
| a function, but also holds state and may have other methods.
|
| This ability to tack state, ie member vars, onto a function by converting
into a
| class and using it as a functor is useful to a lot of folks.  The C++ STL
for
| example is designed to allow functors in almost all places where a
function
| would otherwise be used.  Your opCall syntax conflicts with that idiom.
|
| If the conflict between syntaxes is dangerous, then maybe you should
switch to
| the side of the road that (almost) everyone else is driving on?
|
| Kevin

Not really. The following compiles just fine:

class A
{
    static void opCall () {}
    void opCall (int a) {}
}

Notice that they don't take the same arguments. If they do, then there's a compiler error about both functions conflicting, but I think that's a bug.

-----------------------
Carlos Santander Bernal


June 05, 2004
In article <c9qm08$1mkv$1@digitaldaemon.com>, Kevin Bealer says...

>Using opCall for non-new applications is only confusing if you typically
>overload the opCall to mean "new".  The normal use of opCall (in my opinion) is
>as a "functor", i.e. "operator()" in C++.
<snip>

I am perfectly well aware of that. I have been using functors for a very long time. There are one or two in Int, come to think of it.

But you're talking about /non-static/ opCall.

Believe it or not, in the D world, there is a /static/ opCall. This is somewhat pointless, since a static functor is just - well - a function. And because it looks so much like a constructor, and because structs don't have constructors, that's what gets used, despite the fact that it wasn't designed for that purpose.

Arcane Jill



June 05, 2004
"Arcane Jill" <Arcane_member@pathlink.com> wrote in message news:c9rq7c$a78$1@digitaldaemon.com...
> In article <c9qm08$1mkv$1@digitaldaemon.com>, Kevin Bealer says...
>
> >Using opCall for non-new applications is only confusing if you typically overload the opCall to mean "new".  The normal use of opCall (in my
opinion) is
> >as a "functor", i.e. "operator()" in C++.
> <snip>
>
> I am perfectly well aware of that. I have been using functors for a very
long
> time. There are one or two in Int, come to think of it.
>
> But you're talking about /non-static/ opCall.
>
> Believe it or not, in the D world, there is a /static/ opCall. This is
somewhat
> pointless, since a static functor is just - well - a function. And because
it
> looks so much like a constructor, and because structs don't have
constructors,
> that's what gets used, despite the fact that it wasn't designed for that purpose.

D also has other operators in static versions: so it is possible to do something like:

class A
{
    static int opAdd(char[] x){}
}

and then you us it:

A + "some string";

Having static operators IMO is a good thing because it gives us a
flexibility
in writing code. Someone might find it useful to define static opCall to
do something other that constructing, so why not. The problem would
be solved by letting structs have constructors (also not asking for
destructors)
and then there would be no confusion: use new to construct, and static
opCall
(if you need it) for something else.

> Arcane Jill
>
>
>


June 05, 2004
In article <c9rq7c$a78$1@digitaldaemon.com>, Arcane Jill says...
>
>In article <c9qm08$1mkv$1@digitaldaemon.com>, Kevin Bealer says...
>
>>Using opCall for non-new applications is only confusing if you typically
>>overload the opCall to mean "new".  The normal use of opCall (in my opinion) is
>>as a "functor", i.e. "operator()" in C++.
><snip>
>
>I am perfectly well aware of that. I have been using functors for a very long time. There are one or two in Int, come to think of it.
>
>But you're talking about /non-static/ opCall.
>
>Believe it or not, in the D world, there is a /static/ opCall. This is somewhat pointless, since a static functor is just - well - a function. And because it looks so much like a constructor, and because structs don't have constructors, that's what gets used, despite the fact that it wasn't designed for that purpose.
>
>Arcane Jill

You're right.. sorry about that.

Kevin



June 06, 2004
Walter wrote:

>If everyone would be satisfied with 1) no destructors and 2) bit copies for
>assignment and copy constructor and 3) no RAII for structs, I would be much
>more amenable to adding them in <g>.
>  
>
I've not problem with this (adding a constructor for structs).  We all see structs as a light weight class so we don't want these other things in them anyway.  I think this should be looked on from a practical stand-point (what will make this language better), rather then how to prevent arguments about the language (ie if this feature is left out then no-one can claim that D is flawed). 

Java left out pointers, so no-one can argue against all the evils of pointers but then no-one can make use of pointers in java either.

-- 
-Anderson: http://badmama.com.au/~anderson/
June 06, 2004
In article <c9qiqn$1i01$1@digitaldaemon.com>, Walter wrote:
> 
>> But, Walter - structs don't have constructors, remember? So, that would leave me with no choice but to overload static opCall() to achieve the same effect.  And while this would have the (rather nice) benefit of causing the word "new" to disappear from people's source code in relevant places - I rather thought you didn't like this approach. I mean, we're ending up with SOME things getting constructed with the syntax A(), OTHER things getting constructed with new A(), and YET MORE things offering both options. This is surely going to be confusing to people. Perhaps you might consider adopting my suggestion of making the keyword "new" optional in all cases, merging the functions of this() and static opCall(), and allowing structs to have constructors?
> 
> The trouble with allowing structs to have constructors, is then there's the issue of overloadable assignment operators and the default copy constructor, both of which I avoid. Then if there are constructors, why not destructors, and the whole complicated C++ mess appears (think what happens when you pass a struct as a function parameter).
> 
> If everyone would be satisfied with 1) no destructors and 2) bit copies for assignment and copy constructor and 3) no RAII for structs, I would be much more amenable to adding them in <g>.

I'd love to have constructors!

Finally a decent Vector type that's actually supported by the language!

I might be able to settle with 2).

And destructors anyone can implement themselves:

struct X { .. }

void f()
{
    X x;

    try
    {
        // function body
    }
    finally
    {
        X.destroy();
    }
}

So there we have a nice convention for RAII for structs.

On the other hand, the compiler _could_ implement it for me, so I didn't have to go through the trouble...

On the third (?) hand, I suppose that a try-catch-finally statement is designed to look like "this construct will cause some run-time overhead". In that it's more "transparent" than just a struct that is standing there, innocently, but causing invisible overhead because of preparation for stack unwinding...

(Of course, not all exception handling implementations incur overhead when the exception is not actually thrown, but those do not tend to grow the executable size noticeably)

-Antti

-- 
I will not be using Plan 9 in the creation of weapons of mass destruction to be used by nations other than the US.
June 07, 2004
Walter wrote:

> 
> "Arcane Jill" <Arcane_member@pathlink.com> wrote in message news:c9la0f$2rpa$1@digitaldaemon.com...
>> In the latest version I've actually removed the copy constructor and dup
> from
>> Int, so you can't deep copy it any more. I did this because you don't need
> to
>> deep copy it, ever, and I realized (in the end, after some prompting)
>> that
> the
>> presence of those functions might mislead people into thinking
> copy-by-value for
>> this class did anything useful.
> 
> I've been thinking about the issue of BigInteger being implemented as a class, but desiring copy-by-value semantics. If you adopt the paradigm of copy-on-write for the internal array, wouldn't that achieve cbv semantics?

If BigInteger is implemented as a class containing a reference to the data, this will not work: If you do a copy on write, this will change the reference inside the object, but other locations in the code might still hold a reference to the same object, so their value will be changed as well.

What you would have to do, is copy-on-write for the whole object. For example:

------------------
class BigInteger {
        opAdd(BigInteger other) {
                BigInteger res = new BigInteger;
                res.value = ...;
                return res;
        }
}
------------------

I don't even know, whether this should be called "copy-on-write" at all. It is more like considering BigInteger objects as read-only once they are constructed.

June 07, 2004
Arcane Jill wrote:

> You see, until a few days' ago, I would have considered that it *HAD* to be a class, because it is _unbelievably_ important to me that I am able to wipe memory after use

Why do you want to do that on a per-object basis? The probably cleaner, easier and more secure way might be to use a different allocator for the critical data: This allocator would then just place all sensitive data in an isolated block of memory. As soon as the critical portion of your code is over, you can simply wipe that block completely with an explicit command.

June 07, 2004
In article <ca14k2$1rlj$1@digitaldaemon.com>, Norbert Nemec says...
>
>If BigInteger is implemented as a class containing a reference to the data, this will not work:

I'm smarter than that.

When I said "implement copy by value semantics" you should implicitly read into my words "and make it work". I know how array references are stored, and how to play with them.

Jill


PS. The class is called Int. The phrase "big integer" is a suitable description, but it is not the name of the class, and should not be capitalized or concatenated.


June 07, 2004
In article <ca151q$1st0$1@digitaldaemon.com>, Norbert Nemec says...
>
>Arcane Jill wrote:
>
>> You see, until a few days' ago, I would have considered that it *HAD* to be a class, because it is _unbelievably_ important to me that I am able to wipe memory after use
>
>Why do you want to do that on a per-object basis? The probably cleaner, easier and more secure way might be to use a different allocator for the critical data: This allocator would then just place all sensitive data in an isolated block of memory. As soon as the critical portion of your code is over, you can simply wipe that block completely with an explicit command.

Did that a few hours ago.
Jill