I would like to propose to add a fourth step to this plan to remove
the close builtin too. Instead, we could close channels with c <- v,
false. This is analogous to deletion from maps and have the added
benefit that, then, only the sender would be allowed to close
channels. It could even be more useful than close() if c <- v, false
meant that, from now on, the channel will always return v, instead of
the zero value, although I'm not sure this is a good idea.
Of course, this would have to wait until the other changes are in but,
do you think it would be a logical next step?
--
- yiyus || JGL .
The "closed" builtin function is going away because it's too easy to
misuse it (e.g. from the sender's side). Your proposal is not removing
the "close" functionality, only turning it from a builtin function to
a remarkably subtle operator operation.
Arguably the syntax for deleting from maps is also obscure; if
anything that should be the one to get changed.
Dave.
This has been discussed before:
http://groups.google.com/group/golang-nuts/browse_thread/thread/55758d25014282db/
I think that the same reasons given to delete from maps with a
comma-false assigment apply to closing channels sending v, false.
Since it is simmetrical to receiving from a channel, I don't think is
too subtle. rsc wrote about maps:
"If you know about x, ok = m[k] and what it means for ok to be false,
then m[k] = x, false should be plenty clear."
s/= m[k]/= <- c/
s/m[k] =/c <-/
In fact, almost everything in that thread would apply here (for
example, the possible use of the blank identifier as the zero value).
> I think that the same reasons given to delete from maps with a
> comma-false assigment apply to closing channels sending v, false.
> Since it is simmetrical to receiving from a channel, I don't think is
> too subtle.
Closing a channel is not symmetric to receiving on a channel.
Closing a channel, if anything, is symmetric to opening a channel,
which you do with the "make" function.
Dave.
Assigning to a map and deleting from a map are exclusive operations.
You can be either assigning or deleting, but not both. The map
deletion syntax is clear, if a little weird.
Closing and sending to a channel are orthogonal operations. You can
close, send, or close and send. The proposed syntax doesn't make it
clear what is happening, exactly.
Andrew
I don't understand this. Either you send to a channel or you close it,
but how do you close and send?
Maybe what you mean is that c <- v, false can mean two different
things: first send v, then close the channel, or just close the
channel. What I propose is that what you send is what you will
receive. If you send false as second value the next receive operation
has to get false, so the channel has to be closed and the value can be
discarded.
I agree that having a dummy value there can be confusing, that is why
I suggested to return that value instead of the zero value. Then, the
rule would be very simple and clear: after sending v, false to a
channel (and all the previous values have been received) every receive
operation will get v, false without blocking and any send operation
will panic.
Russ
On 9 Mar 2011 19:30, "yy" <yiyu...@gmail.com> wrote:
>
> The final result will be that the closed() builtin will
> disappear and will be replaced by v, ok <- c, where ok is false if the
> channel was closed.
>
It's quite rare that I've used a non-blocking read from a chan, in fact I think it was only to test the syntax, but I thought that :
v, ok := <- c
Was a "non blocking" read from the channel.
How would that work with your proposed :
v, ok <- c
To check on the receiver if the channel has been closed by the sender, assuming you also use a non blocking read?
Personally, I'm quite happy with close / closed.
This was a typo, sorry. I meant:
v, ok := <- c
Non blocking operations have to be done adding a default case to
select now. Using comma-ok to indicate if the channel is closed and
removing the closed() builtin is a planned change to the language
which has not been done yet. See the thread I referenced in my first
post on this thread, where the plan is fully explained.
The real reason I proposed this change is because it limits channel
closing to senders. The parallelism with deletion from maps is just a
happy coincidence, and a precedent for a similar syntax.
Maybe limiting the check for closed to receivers (as is planned) is
enough to avoid miss-usage, but even then people could close a channel
from the receiver and recover from a panic in the sender if it was
closed. If that became a new pattern (let's hope not), removing
close() could be a way to avoid it (another one is to not allow using
close() on a channel you cannot send to).
Is there any reason I'm missing to let receivers to close a channel?
Making channel closing a special send operation looks to me like a
reasonable way to enforce the idea that the sender is the responsible
of closing.
Other benefits of the <- v, false syntax are that it removes a builtin
(close is an useful name) and that it can simplify some code when you
close or send depending on a condition, as in:
v, err = fn()
c <- v, err == nil
However, I'm not sure this is very common (after a very quick search,
I did not see anywhere in the library where it could be directly
applied).
I don't think any of these reasons is enough to justify a change on
their own, but maybe they are when put together. Anyway, I think the
most sensible thing to do, for the moment, is to wait and see how the
changes to receive operations work.
that would be easy to do by making it illegal to call close
on a receive-only channel. i think that should probably
happen anyway, but others probably have a different opinion.
have any of you found a legitimate use for closing a receive-only
channel?
there is no legitimate use, by definition.
the use of directionally typed channels is not very
common in go programs so restricting close would
not have much practical effect but it might be
worth considering.
russ
it's not that uncommon in libraries. for instance the channel
in a time.Ticker is receive-only.
it would also be an instant warning of misuse - i've seen
people do this when they haven't quite grasped how
channels are supposed to be used.