网络编程UDP和TCP

网络参考模型图:

UDP的实现:

无论发送还是接收端,都要有一个数据包,一个是发送,一个作接收,只能两个人单独聊天

发送端Send:
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.util.Scanner;

public class udpSendTest {
    public static void main(String[] args) throws Exception{
        Scanner sc = new Scanner(System.in);
        String shuju=null;
        //建立udp包
        DatagramSocket s = new DatagramSocket();
        while (true){
            System.out.println("请输入你要发送的消息:");
            shuju=sc.nextLine();//可以接受其他字符
            //将数据打包
            byte[] bytes = shuju.getBytes();
            String IP="192.168.27.20";
            InetAddress ip = InetAddress.getByName(IP);
            int port=8888;//在1025-2的16次方以内都行
            DatagramPacket packet = new DatagramPacket(bytes,bytes.length,ip,port);
            //打包完成,对象就将打包的数据发送
            s.send(packet);
            //当不想发送消息,就输入关闭
            if(shuju.equals("关闭")){
                System.out.println("发送端在3秒后即将关闭。。。");
                Thread.sleep(3000);
                break;
            }

        }
    }
}

接收端Receive:
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;

public class udpReceiveTest {
    public static void main(String[] args) throws Exception{
        //作为接受端,也要有一个udp对象,与发送端不同的是,接收端要在建立udp对象的时候写上端口号
        DatagramSocket r = new DatagramSocket(8888);
        //也要建立一个包,只不过是空数据包,就不需要写ip,和端口号
        byte[] bytes = new byte[2048];
        DatagramPacket packet = new DatagramPacket(bytes,bytes.length);
        while (true){
        //接收包
        r.receive(packet);
        //解析包
        byte[] data = packet.getData();
        int length = packet.getLength();
        //包里是字节数据,要转成字符串
        String s = new String(data,0,length);
        //如果当发送端输入关闭,那么接受端也会停止接收
            if(s.equals("关闭")){
                System.out.println("接收端即将关闭");
                break;
            }
        //在接受数据的时候,我还想知道是谁发送的数据,是什么时间发送的,所以可以根据包查询一下
        InetAddress address = packet.getAddress();//获取发送端的原生ip地址,是包含用户名和ip号的
        String hostName = address.getHostName();//从原生ip地址中获取用户名
        String ip = address.getHostAddress();//从原生ip地址中获取ip
        System.out.println("发送者的ip地址为:"+ip);
        System.out.println("一位叫:"+hostName+"给您发送了一条信息");
        System.out.println("信息内容是:"+s);



        }


    }
}

TCP的实现:多人聊天室

字节输入输出流的实现,加入多线程,可以让多人一起进入聊天室

客户端Client:
import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
import java.util.Scanner;

public class tcpClient {
    public static void main(String[] args) throws Exception{
        Scanner sc = new Scanner(System.in);
        String ip="192.168.26.12";
        int port=2024;
        //万一服务端崩溃或者未打开,凡是用到socket的地方都会报异常,需要处理一下
        try{
            //创建tcp的客户端
            Socket socket = new Socket(ip,port);//传入ip和端口号
            while (true){
                System.out.println("请输入你要发送的内容:");
                String neirong=sc.nextLine();
                if(neirong.equals("关闭")){
                    System.out.println("客户端已关闭!");
                    break;
                }
                //得到管道的字节输出流
                OutputStream os = socket.getOutputStream();
                os.write(neirong.getBytes());
                //           //接受服务端的通知
                InputStream is = socket.getInputStream();
                byte[] bytes = new byte[2024];
                int i = is.read(bytes);//读字节的时候,就不要while,因为外面有一层while,再套while读取会阻塞
                String s = new String(bytes, 0, i);
                System.out.println(s);

            }
            //释放资源
            socket.close();

        }catch (Exception e){
            System.out.println("服务端异常,请检查服务端是否打开或者中断");
        }

    }
}

服务端Server:
import java.io.InputStream;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket;

public class tcpServer {
    public static void main(String[] args) throws Exception{
        //创建服务端对象
        ServerSocket ss = new ServerSocket(2024);
        //一直监听客户端
        while (true){//如果不加while,只会监听一次,当客户端关闭,服务端也就关闭了
        Socket socket = ss.accept();
        new ClientThread(socket).start();
        }


        }
    }
    //如果只按照上面的写法,当客户端关闭,服务器也会自动关闭,这是不行的,服务器要一直监听,做服务功能
    //所以设置一个线程,来来提供服务
    class  ClientThread extends Thread{
        private Socket socket;

        public ClientThread(Socket socket) {
            this.socket = socket;
        }

        @Override
        public void run() {
            System.out.println("============🙂欢迎来到TCP聊天室==============");
            try{
                InetAddress inetAddress = socket.getInetAddress();
                String hostAddress = inetAddress.getHostAddress();
                String hostName = inetAddress.getHostName();
                System.out.println("ip:"+hostAddress+","+"用户"+hostName+"已上线🚀");
                //通过客户端获取管道的输入流
                InputStream is = socket.getInputStream();
                //读取客户端的数据
                int len=0;
                byte[] bytes = new byte[2024];
                while ((len=is.read(bytes))!=-1){
                    String s = new String(bytes, 0, len);

                    System.out.println("用户"+socket.getInetAddress().getHostName()+"发来一条信息:"+s);
                    //获取客户端的输出流,反馈客户端,服务端已经收到信息
                    OutputStream os = socket.getOutputStream();
                    String s1="服务端已收到!";
                    byte[] bytes1 = s1.getBytes();
                    os.write(bytes1);
            }
        }catch (Exception e){
//                e.printStackTrace();// TODO:如果客户非正常关闭,说明客户端断开连接,要提示以下
                System.out.println("================================");
                System.out.println(socket.getInetAddress().getHostName()+"客户端已断开连接。。。。");
                System.out.println("================================");
            }
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

我的K8409

你的鼓励将是我创作的最大动力!

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值