一般的なTCP利用の通信形態

ソケットの起源は、BSD系UNIXのC言語におけるプロセス間通信やネットワークに関するプログラム群です。 現在では、IPアドレスとポート番号を利用した仮想的インターフェースを指すことが多いようです。 (つまり、IPアドレスとポート番号を利用して通信しあう接続部分です。)

Javaでは、TCP通信(サーバー、クライアント共に)に使うクラスが Socketの名前になっています。
そして、接続待機用のTCPサーバー用クラス名が、ServerSocketになっています。

対して、Microsoftの.NET Frameworkでは、 TCP通信(サーバー、クライアント共に)に使うクラスが TcpClientの名前になっています。
そして、接続待機用のTCPサーバー用クラス名が、TcpListenerになっています。
よって、Visual Basic や C#では、 サーバー側で、TcpListenerオブジェクトでクライアントの接続を待機し、 クライアントが接続してくると、その通信用のTcpClientが取得できます。
クライアントでは、TcpClientのオブジェクトでサーバーに接続し、 それから取得できる送受信用のストリームで通信します。
どちらもTcpClientのオブジェクトから取得できる送受信用のストリームで 相手と通信します。

一般にサーバーでは、複数のクライアントと通信できますが、そのイメージを以下に示します。 次へをボタンが消えるまでクリックして確認ください。

上記のサーバ側には複数のソケットが使われます。(クライアントが接続することで生成)
この時、サーバー側のソケットのIPアドレスはポート番号は同じです。
例えば、Webサーバであれば全てのサーバ側通信用ソケットのポートは同じ80番号となります。
つまり、ポートとソケットは一対多の対応となり得る訳でする。

複数のクライアントと接続可能なプログラムのイメージ(Java例)

01
02
03
04
05
06
07
08
09
10 11
12
13
14
15
16
17
18
19
20 21
22
23
24
25
26
27
28
29
30 31
32
33
34
35
36
37
38
39
40 41
42
43
44
45
import java.io.*;
import java.net.*;
public class SocketThread implements Runnable {
	Socket soket;	//通信用ソケット
	Thread thread;	//スレッド管理クラス
	InputStream sok_in;		//byte入力用
	InputStreamReader sok_is;	//文字入力用
	BufferedReader sok_br;		//文字列入力用
	OutputStream os;		//byte出力用
	String sendData = "ここはクライアント側へ送信するメッセージとして変更\r\n";
	String receiveData = null;
	public void init() throws Exception {//送受信ストリームを取得
		this.sok_in = soket.getInputStream();
		this.sok_is = new InputStreamReader(sok_in);
		this.sok_br = new BufferedReader(sok_is);//入力用
		this.os = soket.getOutputStream();//出力用
	}
	public void send() throws Exception{//送信メソッド
		this.os.write(sendData.getBytes());
		this.os.flush();//送信してない情報があれば、全て送信する。
	}
	public void receive() throws Exception {//受信メソッド
		System.out.println(receiveData = sok_br.readLine());
	}
	public void doLoop()throws Exception {//送受信ループ
		while(thread != null){
			send();//送信
			receive();//受信
		}
	}
	public void run() {//スレッドの実行範囲
		try{
			init();//送受信ストリームを取得
			doLoop();//送受信ループ
		}
		catch(Exception e) {
			e.printStackTrace();
		}
		thread = null;
	}
	public SocketThread(Socket soket) throws Exception {
		this.soket = soket; 				//コンストラクタ
		this.thread = new Thread(this);//スレッドインスタンス生成
		this.thread.start();//上記のrunメソッドを別スレッドで実行する
	}
}

SocketThreadの生成で、引数で指定した接続相手と通信を開始します。
接続すると、上記27行の送信と28行の受信を繰り返すことになります。

			while (true) {
				//クライアントからの接続を待ち、接続してきたら、
				//	そのクライアントと通信するソケットを取得する。
				Socket clientSock = serverSock.accept();
				new SocketThread(clientSock);// serverSock用ソケットと別スレッド通信開始
			}