質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

89.64%

C# TCP通信 複数クライアント

解決済

回答 3

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 6,393

g1mkt

score 13

前提・実現したいこと

当方サーバ、C#の勉強中であります。

C#でTCP通信のサーバを作成しております。
複数クライアントを想定しております。複数というのは同時に0~100万のクライアントを想定しております。
クライアントは1~1000番あるファイルの中の「ファイル■番の●文字から●●文字まで送ってというリクエスト」を送ります。
サーバは接続してきたクライアントに、「ファイル■番の●文字目から●●文字目まで」お送るという工程をします。
データのやり取りが終了したら切断します。

プログラムの流れは

TcpListenerで随時、リクエストしてきたクライアントをTcp接続承認

クライアント毎にスレッドを作成

===スレッド毎====
クライアントからデータを受信

受信データから指定ファイルをバッファに読み込む

●文字目から●●文字目まで抽出

クライアントへデータを送信

切断
===スレッド毎====

というものにしようかと思っております。
つまり、1スレッド1クライアントとなります。
その一つ一つのスレッド毎の中でファイルを読み込み、からデータ送受信
、切断を行います。

そこでなのですが、各ファイルのサイズが2Mbyteとしたとき、万が一にも
100万のクライアントが一気にリクエストをサーバに送った時、サーバは固まると思います。(メモリ不足)そこで、
①【ある一定数の接続されたクライアントがいるときは、TcpListnerを停止】もしくは、
②【スレッドを使わずにクライアントが1つ接続していればTcpListenerを停止】させようかと思っております。(1つずつ接続はサーバとしてどうなのか。。。)

なので、リクエストをだしたクライアントには返事が帰ってこないので、
返事が帰ってこないときは定期的にさらにリクエストを出してもらおうと思っております。

ここで、上記の仕様に改善点等のご指摘を下さるとうれしいです。
また、実際のサーバプログラムはどのようなものなのかご教授下さるとうれしいです。URLでも嬉しいです。
尚今のところ②で考えております。

補足情報(言語/FW/ツール等のバージョンなど)

VisualSudio2015 C# NET4.5

追記

ご回答有難うございます。ご回答いただいたリンク等で勉強させて頂き、何を使うか検討させて頂きます。

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 3

+3

これは、一般的に C10K 問題と呼ばれています。 C10K でググればいろいろとでますが、以下を参考にされてはいかがでしょうか。

C10K問題

その後も少し検索しました。C#であれば AKKA とかを使うと良いのではないでしょうか。

Akka.NETのサンプルを動かしてみる

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/10/30 23:16

    mit0223様
    ご回答有難うございます。C10K問題というのですね。リング有難うございます。
    勉強させて頂き、検討させて頂きます。

    キャンセル

checkベストアンサー

+2

参考となるURL

非同期サーバー ソケットの例

サーバーは極力軽く作って、大量の処理を行う前提で上記のサンプルは有効でしょうか?
いろいろ非同期で作成して、DBアクセスや、ファイルアクセスも非同期で行う事が望ましいと思います。

スレッド生成はコストが高いですから、非同期で少ないスレッドで次々処理する方が得策だと思います。

nodejs での実装のようですが、実際に 運用されている人の記事
http://qiita.com/kidach1/items/b75882edd4f715ebc213
が参考になります。

ある程度を超えると、やはり性能チューニングのためにライブラリに任せず、自分で細かいコードを書いているようです。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/10/30 23:19

    KazuhiroKato様
    ご回答有難うございます。やはりスレッドは少ない方が良いですよね。リンク有難うございます。勉強させて頂きます。

    キャンセル

+2

サーバ1台あたりのリソースはロジックの工夫やお金で上限を増やせますが、コスト面や物理面で限界があるかと思います。
接続した後にも何をさせるかによっても消費するリソースは大きく変動します。

100万台を処理できるようにするには、例えばサーバ1台で10万台処理できるなら10台並べるだけの話です。

IoTでよく利用されるプロトコルの一つにMQTTがありますが、それを実装したMQTT Brokerを活用されることを検討してみてはいかがでしょうか。

C++で実装されたMosquittoや、クラスタを組むことができるVerneMQあたりが個人的に推奨します。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/10/30 23:15

    moonphase様
    ご回答有難うございます。MQTT Bokeを視野に入れ検討させて頂きます。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 89.64%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる