Chapter 8 Goroutines and Channels
Go enable both styles of concurrent programming. This chapter presents coroutines and channels, which support communicating sequential processes or CSP, a model of Concurr Ency in which values is passed between independent activities (Goroutines) but variables is for the most part Confin Ed to a single activity. Chapter 9 covers some aspects of the more traditional model of shared memory multithreading, which would be familiar if you ' ve used threads in the other mainstream languages. Chapter 9 also points out some important hazards and pitfalls of concurrent programming that we won ' t delve to in this C Hapter.
Goroutine two modes, one for two goroutine between the communication, variables is limited to a separate activities.
Another multi-threading, similar to other mainstream languages, is characterized by the shared memory multithreading.
8.1 Goroutines
In Go, each concurrently executing activity is called a goroutine.
In Golang, each concurrently executing activity is called a goroutine.
If you had used operating system threads or threads in other languages, then you can assume for now that a goroutine is s Imilar to a thread, and you'll be able to write correct programs. The differences between threads and Goroutines is essentially quantitative, not qualitative, and would be described in SEC tion 9.8.
The difference between threads and goroutines is quantitative, not qualitative. A further explanation will be made in 9.8.
When a program starts, it's only goroutine are the one that calls the main function, so we call it the main goroutine. New Goroutines is created by the GO statement. Syntactically, a go statement is an ordinary function or method call prefixed by the keyword go. A Go statement causes the function to being called in a newly created goroutine. The GO statement itself completes immediately:
When a program starts, the program's only main function is the main goroutine.
package mainimport ( "time" "fmt")func main() { go spinner(5 * time.Millisecond) const n = 45 fibN := fib(n) fmt.Printf("\rFibonacci(%d) = %d\n", n, fibN)}func spinner(delay time.Duration) { for { for _, r := range `-\|/` { fmt.Printf("\r%c", r) time.Sleep(delay) } }}func fib(x int) int { if x < 2 { return x } return fib(x - 1) + fib(x - 2)}
The/R in the program indicates carriage return
Other than by returning from main or exiting-the program, there is no programmatic-for-one goroutine to stop another, But as we'll see later, there is ways to communicate with a goroutine to request that it stop itself.
In addition to returning from the main function or exiting the current program, there is no procedural way to let one goroutine stop the other goroutine, but there is a way for a goroutine to send a message to another goroutine to stop himself.
8.2 example:concurrent Clock Server
A clock example
Server
package mainimport ( "net" "log" "io" "time")func main() { listener, err := net.Listen("tcp", "localhost:8000") if err != nil { log.Fatal(err) } for { conn, err := listener.Accept() if err != nil { log.Print(err) continue } handleConn(conn) }}func handleConn(c net.Conn) { defer c.Close() for { _, err := io.WriteString(c, time.Now().Format("15:04:05\n")) if err != nil { return } time.Sleep(1 * time.Second) }}
The important thing is three steps:
- Listener, err: = Net. Listen ("TCP", "localhost:8000")
- Conn, err: = Listener. Accept ()
- _, Err: = Io. WriteString (c, time. Now (). Format ("15:04:05\n"))
Note: The time taken must be 2016/1/2 15:04:05 (123456) January 2 3:4 Five Seconds
https://segmentfault.com/q/1010000010976398/a-1020000010982052
Connect using NC commands on the client
NC localhost 8000
Client
Package Mainimport ("NET" "Log" "IO" "OS") Func main () {conn, err: = Net. Dial ("TCP", "localhost:8000") if err! = Nil {log. Fatal (ERR)} defer conn. Close () _, Err1: = Io. Copy (OS. STDOUT, conn) if err! = Nil {log. Fatal (ERR1)}}