I got some goroutines, all waiting to write something to the same unbuffered channel.When some other goroutine starts reading from that channel, al values come in in the same order the goroutines tried to write to the channel.
Is this by design? Is this something I can rely on?
--
You received this message because you are subscribed to a topic in the Google Groups "golang-nuts" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/golang-nuts/PWt4r9b40bc/unsubscribe.
To unsubscribe from this group and all its topics, send an email to golang-nuts...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.
A single channel may be used in send statements, receive operations, and calls to the built-in functionscapandlenby any number of goroutines without further synchronization. Channels act as first-in-first-out queues. For example, if one goroutine sends values on a channel and a second goroutine receives them, the values are received in the order sent.
ch := make(chan int, 2)go func(){ch <- 1}()time.Sleep(1*time.Millisecond)go func(){ch <- 2}()fmt.Println(<-ch)fmt.Println(<-ch)
The kth receive on a channel with capacity C happens before the k+Cth send from that channel completes.
Yup, then it is in order... http://tip.golang.org/ref/spec#Channel_types
For example, if one goroutine sends values on a channel and a second goroutine receives them, the values are received in the order sent.
ch := make(chan int, 2)go func(){ch <- 1}()time.Sleep(1*time.Millisecond)go func(){ch <- 2}()fmt.Println(<-ch)fmt.Println(<-ch)
ch := make(chan int, 2)go func(){ch <- 1}()time.Sleep(1*time.Millisecond)go func(){ch <- 2}()fmt.Println(<-ch)fmt.Println(<-ch)
Here, neither channel send happens before the other.
The only way to specify 'order of operations' between two goroutines is by using synchronization (usually with channels). In the above example, there is no such synchronization, and so there is no guarantee. This would be true for a buffered or unbuffered channel.
On Sunday, June 15, 2014 8:51:21 PM UTC+12, Peter Kleiweg wrote:I got some goroutines, all waiting to write something to the same unbuffered channel.When some other goroutine starts reading from that channel, al values come in in the same order the goroutines tried to write to the channel. Is this by design? Is this something I can rely on?
The sleep in your original example is not a form of synchronization that is reliable. The order of output in that code is still entirely dependant on cpu load, number of goroutines in the system , GOMAXPROCS and the operating systems thread scheduler. Its possible a sudden system lag causes the first send to be delayed longer than the sleep, which means the second send could arrive throwing off your order.
Perhaps a sentence saying the order is undefined should be added.
Could you give me an example of code where two sends can be guaranteed to have been started in a specified order? Also with the guarantee that the read has started only after both sends have started. Also you can't use sleep because that is not a reliable guarantee.
I'd like to see a real example of this, I'm not even sure it's possible given the semantics of channels and locks.
Op zondag 15 juni 2014 20:27:06 UTC+2 schreef Brendan Tracey:ch := make(chan int, 2)go func(){ch <- 1}()time.Sleep(1*time.Millisecond)go func(){ch <- 2}()fmt.Println(<-ch)fmt.Println(<-ch)
Here, neither channel send happens before the other.Yes, it does, because the channel is buffered, and there is time between the start of the goroutines.
The only way to specify 'order of operations' between two goroutines is by using synchronization (usually with channels). In the above example, there is no such synchronization, and so there is no guarantee. This would be true for a buffered or unbuffered channel.People keep saying that about unbuffered channels, order is undefined, no guarantees. And still, the result is ordered. Every time. I haven't seen an example yet where the order is not preserved.
So, the question remains: why is the order preserved? Is it by design or a result of how channels are implemented? The specs are not sufficiently specific about this.
I looks like communicating over an unbuffered channel isn't one synchronisation between two goroutines, but two synchronisations, one of a sending goroutine with the channel action, and the other of a receiving goroutine with the same channel action.
My point isn't at all about ensuring one goroutine attempts a send before another goroutine does.
The simple answer has already been explained, you cant rely on this even if it seems to be ordered by a buffer.You seem to fail to understand the technical reasons behind the answer.
The specification on the release node is clear: http://golang.org/ref/spec#Channel_typesIt is the specification on tip that is confusing: http://tip.golang.org/ref/spec#Channel_types
Go isn't a quantum computer. Things happen at a certain time, even if you don't know at what time. There is an order of things. Even if two goroutines try to send on a channel at exactly the same time, those attempts are not handled at the same time.
Go isn't a quantum computer. Things happen at a certain time, even if you don't know at what time. There is an order of things. Even if two goroutines try to send on a channel at exactly the same time, those attempts are not handled at the same time.
--
You received this message because you are subscribed to a topic in the Google Groups "golang-nuts" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/golang-nuts/PWt4r9b40bc/unsubscribe.
To unsubscribe from this group and all its topics, send an email to golang-nuts...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.
This code does not demonstrate that property. There is no HB relationships between any of the sends. The sends happen concurrently.
--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts...@googlegroups.com.
I am only talking about the succeeding of one send before the other in the same order the attempts were started.
I got some goroutines, all waiting to write something to the same unbuffered channel.When some other goroutine starts reading from that channel, al values come in in the same order the goroutines tried to write to the channel. Is this by design? Is this something I can rely on?