ゴーチャンネルチャンネル

信道(Channel)

チャンネル(Channel)はコルーチン間の通信路とみなすことができます。データは、チャネルの一端から送信され、他端に受信されても​​よいです。

デフォルトの同期モードは、ペアを送受信するために必要とされます。他のチャンネルはウェイクアップ後に準備ができるまで、それ以外の場合はブロックされます。

チャネルとチャネルバッファにバッファリングされていないチャネル
バッファなしのチャネルは:同期チャネルは、任意の値を格納する能力の前に受信されません。チャネルのこのタイプは、それ以外の場合は、ブロッキングにつながる、次のチャンネルを操作する準備ができて、同時に送受信します。
バッファチャンネル:開かれたが、チャネルの1つまたは複数の値を格納するために作成することができる場合、チャネルは、非同期です。このタイプは、同時送受信を必要としません。長い未使用スペースがバッファ内にあるようにデータを送信するために使用される、あるいはさらに含むデータを受信することができるように、その後、通信はブロックせずに行われます。

送信し、デフォルトのブロッキング(同期)を受け取ります。これは何を意味するのでしょうか?データがチャネルに送信されると、プログラム制御は、チャネルからデータを読み出すために、いくつかの他のコルーチン移動するまでステートメントの送信データブロックで発生する、ブロックされていないであろう。
データチャネルを読み込むとき同様に、このチャンネルにいない他のコルーチンの書き込みデータ場合は、その後、リード処理は常にブロックされます。
チャネルのこのような特性は、囲碁コルーチンの間で効率的な通信をサポートすることができ、明示的な条件変数のロックまたは他の一般的なプログラミング言語を使用する必要はありません。

チャンネル声明

VaRのCHちゃんT

我々は、T CHチャネルと呼ばれるタイプの名前を宣言
チャンネル0がnilです。私達はちょうどマップを作成し、同じスライス、作る組み込み関数によってチャネルを作成する必要があります。

バッファなしチャンネル

CH:=メイク(ちゃんT)

チャネル・バッファ

CH:=メイク(ちゃんT、キャップ)

(1)チャネルを作成します。

     //組み込み型チャンネル
    VARチャンA int型
    IF A == nilの{ 
        A =メイク(チャンint型)
        fmt.Printf( "%T \ N-"、A)チャンはint // 
    } 
    //カスタム型チャネル
    VAR人チャンP 
    ゼロP == {IF 
        P =メーク(チャン人)//チャンmain.personの
        fmt.Printf( "%T \ N-"、P)
    }

(2)チャネルを介してデータを送受信します

注:デフォルトでは、送信することで、ブロックされた受信します

データ:= < - //データチャネルから読み出され、読み出された値が変数データに割り当てられます。
< -データ//チャネルにデータを書き込みます。
メインパッケージ
のインポート(
    "FMT" 
    ""時間を
{こんにちはFUNC(ちゃんブール値を行なわ)
    (hello "のルーチンがスリープ状態に起こっている行く)fmt.Println" 
    time.Sleep(4 * time.Second)
    //只有写数据后才能继续执行
    <なさ-真
    fmt.Println( "ハロー目を覚ましルーチン行くと完了に書き込みに行く")
} 
メインFUNC(){ 
    行わ:=メイク(ちゃんブール値)
    (行われる)ハロー行く
    <-done 
    fmt.Println(」メイン受信データ")
}

(4)デッドロック

データ伝送チャネルへのGoコルーチンは、合理的な存在になります場合は、他のコルーチンGoがデータを受信すると言うこと。そうでない場合、プログラムは、実行時にデッドロックの形成をパニックの引き金となるでしょう。

より多くのコルーチンGoは、チャネルからのデータを受信することがある場合は同様に、我々は別のコルーチンが書き込みデータチャネルに行きます、または他のプログラムがパニックを誘発することを期待しています。

メインパッケージ

メインFUNCを(){   
    CH =メイク(チャンINT)
    CH < - 5 
}

(5)単方向チャネル双方向チャネルと

双方向チャネル:即ち、両方のチャネル上でデータを送信し、データを受信することができます。
単方向チャネル:チャネルのみがデータを送信または受信することができます。

単方向チャネル:

メインパッケージ

インポート"FMT"を

{ - (INT sendchちゃん<)のsendData funcを   
    sendch < - 10 
} 

)主FUNC({   
    sendch:=メイク(チャン< - INT)     
    のsendData(sendch)行く
    fmt.Println(< - sendch)を
}

ちゃん< - int型専用トランスポートチャネルはちゃんを矢印のように定義されます。:私たちは、コンパイラエラーので、唯一の伝送チャネルを介してデータを受信するための主な機能に試してみました
。<-sendch(送信専用タイプちゃん<のから受け取る- INT):無効な操作
すべてがうまくいっているが、データCDを読むことができませんそれはどのような送信チャンネルは何か?
どこ変換チャネル(チャンネル変換)です。トランスポート・チャネルCDまたはCD収率(受信のみ)チャネルに双方向チャネルを変換することは可能であるが、その逆ではありません。

メインパッケージ

インポート"FMTを" 

のsendData funcを(sendchちゃん< - int)を{   
    sendch < - 10 
} 
FUNCをメイン(){   
    CHA1:=メイク(チャンINT)     
    行きのsendData(CHA1)
    fmt.Println(< - CHA1)
}

私たちは、双方向チャネルCHA1を作成しました。CHA1はのsendDataのコルーチンにパラメータとして渡されます。レーンのsendData関数パラメータはsendchちゃん< - INT CHA1 CDは、伝送チャネルに変換されます。
するとチャンネルは、Goは双方向チャネルであるメインコルーチンながら、コルーチンのsendData CDトランスポートチャネルです。プログラムは、最終的な出力10を印刷します。

(6)クローズチャンネル

データの送信者には、チャネルデータが送信されないことを受信者に通知する、チャネルを閉じることができます。

データがチャネルから受信した場合、受信者は、チャネルが閉じられているかどうかをチェックするために多変数を使用することができます。

V、OK:= < - CH
声明以上、データチャネルが送信される場合は、正常trueに[OK]を等しい、受け取りました。し、[OK]を等しいfalseの場合、我々は、閉じたチャネルを読み取ろうということ。
チャンネル値にクローズから読むチャネル型のゼロ値です。例えば、チャネルは、int型のチャネルである場合、値が閉チャネルから読み出されるゼロであろう。

メインパッケージ

のインポート(   
    "FMT" 

FUNCプロデューサ(CHNLチャンINT){   
    iについて:= 0; I <10; I ++ { 
        CHNL < - I 
    }近い(CHNL)
} 

メインFUNC(){   
    CH:= makeが(ちゃんint型)     
    プロデューサー(CH)を行く     
    {のために
        = <-ch:V、OK         
        であればOK == falseを{             
            休憩
        } 
        FMT。 println( "受信"、V、OK)
    } 
}

上記の手順で、0から9までプロデューサコルーチンは、チャネルCHN1を書き込み、その後、チャネルを閉じます。
私たちは、変数OKチャンネルが閉じられたかどうかをチェックし、無限ループのための主な機能を持っています。[OK]が偽に等しい場合は、説明したチャネルが閉じられた後、forループを終了します。
trueにOK等しい場合は、値が出て受信した印刷の値はokです。

(7)チャネルを横切ります

トラバーサルのためのチャネルのサポート範囲

メインパッケージ

のインポート(
    "FMT" 
    "時間" 

FUNCプロデューサー(CHNLチャンint型){ 
    延期閉じる(CHNL)//エンドプログラムの実行、閉じたチャネル
    I用:= 0; I <10; I ++ { 
        time.sleep(300 *時間.Millisecond)//一つの第二の追記
        CHNL < - I //書き込み
    } 
} 
FUNCメイン(){ 
    CH =メイク(チャンINT)
    ゴープロデューサー(CH)
    // CH受信されたデータチャネルのチャネルが閉じられるまで。
    V用:範囲= CH { 
        fmt.Println(V)
    } 
} 

これは、ループの繰り返し処理用のカスタムチャネルとすることができます

{用
        := <-CH //が読み取らV、OK 
        fmt.Println(V、OK)
        データは、サイクルを読み出すことができない場合// {== falseにOK IFを
            BREAK 
        } 
    }

 

おすすめ

転載: www.cnblogs.com/-wenli/p/11817266.html
おすすめ