Boost logo

Boost :

From: Victor A. Wagner Jr. (vawjr_at_[hidden])
Date: 2005-10-15 15:19:49


At 20:28 2005-10-14, Joe Gottman wrote:

>"Joel de Guzman" <joel_at_[hidden]> wrote in message
>news:diphko$tba$1_at_sea.gmane.org...
> > David Abrahams wrote:
> >> Joel de Guzman <joel_at_[hidden]> writes:
> >>
> >>
> >>>>Rebinding semantics are there _precisely_ and _only_ to solve a problem
> >>>>posed by nullability.
> >>>
> >>>Sorry, I don't buy that.
> >>
> >>
> >> Why not?
> >
> > I think this is again an artifact of the confusion between the
> > dual interfaces that optional provides. optional has an identity
> > crisis of being a pointer (as the author's original model) and
> > a variant<T, nil> (which I suggested later on). The rebinding
> > behavior that Fernando rationalized was long and winding and
> > confusing. I don't recall anymore his exact rationale. All I
> > know is that when you have to explain your design using so much
> > wordings, then something is wrong, and I don't buy the gobbledegook.
>
> Here is an interesting thought experiment. What should std::swap do with
>optional<X &>? In general, swap(x, y) usually has the same effect as the
>following code, except for perhaps a stronger exception guarantee and faster
>performance:
> Foo temp(x); // Step 1. Assume x and y are of type Foo
> x = y; // Step 2
> y = temp; // Step 3
>
>That being the case, what would the following code do?
> int a = 1;
> int b = 2;
> optional<int &> x(a);
> optional<int &> y(b);
> swap(x, y);
>
> Assume that swap is not specialized for optional, and consider two cases.
> Case 1: rebind.
> Step 1 of swap above binds temp to a, step 2 rebinds x to b and step
>3 rebinds y to a. Thus the end result is that x and y are each rebound to
>what the other one was pointing to before.
>
> Case 2: no rebind.
> In this case, Step 1 above binds temp to a as before. But step 2
>results in *x = *y, so a is set equal to b and both a and b now equal 2.
>Then step 3 results in *y = *temp, so b is set equal to a, but since a and b
>are already equal due to step 1, there results in no change. Thus the end
>result is that the original value in a is lost.
>
>Of course we would specialize swap for optional<T> to call swap(*x, *y) if
>both x and y are initialized, but I think the fact that this is not
>equivalent to the unspecialized version is an argument in favor of the
>rebind semantics.

I concur that it's an argument in favor of rebind.

On a vaguely related note, I belive that swap semantics haven't been
adequately studied. This seems somewhat odd since every computer
I've worked on at the instruction level has had a swap (or exchange)
instruction. Sometimes it was only registers, others register with
memory (a nice atomic test/set instruction, btw) and even a stack
machine which would swap the top two elements.

Where is this fundamental (it must be fundamental if all the machines
implement it) operation in all of our "high level" languages?
It's not. Well we add it to the library in C++ (std::swap) but
ottherwise ignore it. I came within a fraction (of an inch,
millimeter, whatever) of adding an operator (I was going to use :=:)
to a Pascal compiler we were implementing for our architecture (of
course it had a swap instruction) just to see how it would get
used. Alas, the boss said no.

Many (well, sci-fi anyhow) stories have been written about "if a word
isn't in the language, then the people must not have the concept"
(most often referring to the concept of "war"). In C++ "words" (well
the verbs) are operators. As we all know, there is no swap operator
in C++. People will argue that functions are also words
(verbs). Nonetheless, swap is pretty much a poor cousin in this language.

I seem to recall a discussion recently about "move" semantics. I
didn't read it carefully but what I thought they were driving at was
that if one get it working properly some function return (and
subsequent (immediate) assignment) implementations would be
simplified. I submit that if the problem is to "move" from a
temporary location (let's call it ret) to a destination (dest) then:

swap(dest, ret);
.....and then let ret go "out of scope" more than suffices.

A slight nag in the back of my brain says that Feynman's lecture(s?)
on computation showed that exchanging information was cost free, it
was destroying information that had an energy cost. To say this
keeps me awake at night would be an exaggeration, but I still wonder
from time to time.....
Why can't I swap two references?
Why can't I have a standard container of references?

>Joe Gottman
>
>
>
>
>_______________________________________________
>Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost

Victor A. Wagner Jr. http://rudbek.com
The five most dangerous words in the English language:
               "There oughta be a law"


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk