转到lang,频道处理顺序

I'm studying Go lang through 'A tour of Go', and it's hard to understand Go channel running sequence,

package main

import "fmt"
import "time"

func sum(a []int, c chan int) {

    sum := 0
    for _, v := range a {
        time.Sleep(1000 * time.Millisecond)
        sum += v
    }
    c <- sum // send sum to c
}

func main() {
    a := []int{7, 2, 8, -9, 4, 0}

    c := make(chan int)
    go sum(a[:len(a)/2], c)
    go sum(a[len(a)/2:], c)
    x, y := <-c, <-c // receive from c

    fmt.Println(x, y, x+y)
    fmt.Println("Print this first,")
}

If run above the code, I expected,

Print this first,
17 -5 12

Because, Go routine runs as non-blocking, a But, actually it prints,

17 -5 12
Print this first,

The other example that I found in internet,

package main

import "fmt"

type Data struct {
    i int
}

func func1(c chan *Data ) {
    fmt.Println("Called")
    for {
        var t *Data;
        t = <-c //receive
        t.i += 10 //increment
        c <- t   //send it back
    }
}

func main() {
    c := make(chan *Data)
    t := Data{10}
    go func1(c)
    println(t.i)
    c <- &t //send a pointer to our t
    i := <-c //receive the result
    println(i.i)
    println(t.i)
}

Also, I expected, it prints "Called" first, but the result is

10
20
20
Called

What I am misunderstanding? please help me to understand Go routine and channel.

In your first example, x, y := <-c, <-c will block until it reads off c twice, and then assign values to x, y. Channels aside, you have an assignment, a print statement, then another print statement. Those are all synchronous things, and will happen in the order you state them in. There's no way the second print statement would print first.

The second one is because fmt.Println writes to STDOUT and println to STDERR. If you are consistent (say use println everywhere) then you see:

10
Called
20
20

That's cause there's a race between the first println(t.i) in the main and the println("Called") that's happening in the goroutine. I'm guessing with GOMAXPROCS set to 1, this will happen consistently. With GOMAXPROCS set to NumCPU, I get a mix of results, sometimes looking like the above, and sometimes like this:

10Called

20
20