通信课程二

本节课目标:

1 :循环等待客户机连接

2 : 创建服务器线程,实现多人聊天

3 : 方法封装,方便调用


一:循环等待客户机连接

问题:服务器只能支持一个客户机连接,不能同时多台客户机连接

解决:循环调用Socket client = ss.accept();//ss连接对象

           通过while封装,代码如下:

while(true){
	Socket client = ss.accept();
	...............//获取输入输出流
	...............//发送欢迎字符串至客户机
	...............//循环读取字节,读取bye结束
	...............//关闭连接
}

二、创建服务器线程,实现多人聊天

问题:当通过while循环获取连接,同样还是无法实现多人连接,因为此时服务器是单线程,当一个客户机连接,必须等待当前客户机结束聊天后才能继续连接下一个客户机。

解决 : 通过线程处理,让每个连接对象并行执行,也就是当一个客户机连接时,服务器启动分线程处理,服务器主线程继续等待下一个客户机连接。

<span style="color:#993399;">//分线程</span>
public class ServerThread extends Thread(){
	public void run(){
		...............//获取输入输出流
		...............//发送欢迎字符串至客户机
		...............//循环读取字节,读取bye结束
		...............//关闭连接
	}
}
<span style="color:#993399;">//主线程</span>
while(true){
	Socket client = ss.accept();
	ServerThread st = new ServerThread(client);
	st.start();
	
}

三、公共方法提取

原因:一些公共的跟当前类无关,如果调用,为了避免对象传值的麻烦,一般单独封装到一个类中,并公共方法都标志Wie静态,方便调用,如发送消息,接收消息方法!

操作:      1.创建一个NetJava类
            2.把发送消息方法和接收消息方法封装到NetJava类中,并
	     标志为静态的!
               public static void sendMsg(OutputStream ous,String msg){}
               public static String readMsg(InputStream ins){}
具体代码

import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;

<span style="color:#993399;">//分线程</span>
public class MyServer {
	//创建一个队列,用来存储客户机对象
	public ArrayList<ServerThread> list= new ArrayList<ServerThread>();
	public static void main(String[] args) {
		MyServer ms = new MyServer();
		ms.initServer(9090);
	}

	private void initServer(int port) {
		//创建服务器
		try {
			ServerSocket ss = new ServerSocket(port);
			System.out.println("创建服务器成功,等待客户机连接....");
			while(true){
				Socket server = ss.accept();
				System.out.println("客户机成功连接,ip地址为 :"+server.getRemoteSocketAddress());
				ServerThread sthread = new ServerThread(server);
				list.add(sthread);
				sthread.start();
				
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
		
	}

}
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
<span style="color:#993399;">
//分线程</span>
public class ServerThread extends Thread{
	private Socket server;
	public String name;
	public ServerThread(Socket server){
		this.server = server;
	}
	public void run() {
		try {
			InputStream ins = server.getInputStream();
			OutputStream ous = server.getOutputStream();
			String msg = "欢迎来到我的聊天室";
			byte[] bytes = msg.getBytes();
			ous.write(bytes);
			ous.flush();
			
			msg = "请输入姓名:";
			ous.write(msg.getBytes());
			ous.flush();
			//接收客户端输入的姓名
			name = readMessage(ins);
			System.out.println("用户名为: "+name);
			
			//读取消息
			String str = "";
			while(!"bye".equals(str)){
				str = readMessage(ins);
				System.out.println(name+"说 :"+str);		
			}
			ous.close();
			ins.close();
			server.close();
			
		} catch (IOException e) {
			e.printStackTrace();
		}
		
		
	}
	//定义一个读取消息的方法
        <span style="color:#993399;">//公共方法</span>
          public String readMessage(InputStream ins){
		StringBuffer sb = new StringBuffer();
		try {
		int readByte = ins.read();
			while(readByte!= 13){
				sb.append((char)readByte);
				readByte = ins.read();
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
		
		return sb.toString().trim();
		
	}

}





  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值