IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 网络协议 -> Java 网络编程入门 -> 正文阅读

[网络协议]Java 网络编程入门

前言

了解Java网络编程,打好网络编程的基础。

一、TCP消息发送

1、Client

package com.xhu.java.net;

import java.io.IOException;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;

public class TCPClient {
    public static void main(String[] args) {
        //获取本机IP地址
        InetAddress clientServer = null;
        Socket socket = null;
        OutputStream outputStream = null;
        try {
            clientServer = InetAddress.getByName("127.0.0.1");
            //设置一个端口号
            int port = 9999;
            //生成socket
            socket = new Socket(clientServer, port);
            //发送消息
            outputStream = socket.getOutputStream();
            outputStream.write("学TCP".getBytes());
        } catch (UnknownHostException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            //关闭流
            if (outputStream != null) {
                try {
                    outputStream.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            //关闭socket
            if (socket != null) {
                try {
                    socket.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }


    }
}

2、Server

package com.xhu.java.net;

import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;

public class TCPServer {
    public static void main(String[] args) {
        //服务端IP+端口,即socket
        ServerSocket serverSocket = null;
        Socket accept = null;
        InputStream is = null;
        ByteArrayOutputStream baos = null;
        try {
        //开放端口
            serverSocket = new ServerSocket(9999);
            //接收客户端的连接
            accept = serverSocket.accept();
            //把信息读出来
            is = accept.getInputStream();
            //为了防止乱码,用字节数组包装流读出正确的字符
            baos = new ByteArrayOutputStream();
            int n = 0;
            while (true) {
                try {
                    if (!((n = is.read()) != -1)) break;
                } catch (IOException e) {
                    e.printStackTrace();
                }
                baos.write(n);

            }
            System.out.println(baos.toString());
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if (baos != null) {
                try {
                    baos.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if (is != null) {
                try {
                    is.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if (accept != null) {
                try {
                    accept.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if (serverSocket != null) {
                try {
                    serverSocket.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }
}

二、UDP消息发送

UDP不建立连接,发完包就不管了。

package com.xhu.java.net;

import java.io.IOException;
import java.net.*;

public class UDPClient {
    public static void main(String[] args) throws IOException {
        //1.创建socket
        DatagramSocket socket = new DatagramSocket();
        //2.发送包
        socket.send(new DatagramPacket("udp信息可有可无".getBytes(),
                0, "udp信息可有可无".getBytes().length, InetAddress.getByName("localhost"), 9999));
        //3.关闭
        socket.close();
        //就这样给服务端发送了,不用建立连接,发了就不管了。
    }
}

package com.xhu.java.net;

import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;

public class UDPServer {
    public static void main(String[] args) throws IOException {
        //1.开放端口
        DatagramSocket socket = new DatagramSocket(9999);
        //2.接收包
        byte[] buffer = new byte[1024];
        DatagramPacket packet = new DatagramPacket(buffer, 0, buffer.length);
        //阻塞接收
        socket.receive(packet);
        //输出数据
        System.out.println(new String(packet.getData(), 0, packet.getLength()));
        System.out.println(packet.getAddress());
        //关闭连接
        socket.close();
        //这是不严格的服务端,不建立连接,只有发送端和接收端。这里也可以给其它发。
    }
}

三、UDP聊天

1、发送方

package com.xhu.java.net;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.*;

public class UDPClientA {
    public static void main(String[] args) throws IOException {
        //1.创建socket,开放一个端口
        DatagramSocket socket = new DatagramSocket(9998);
        //2.发送包
        //获取键盘输入
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        while (true) {
            String msg = br.readLine();
            byte[] msgBytes = msg.getBytes();
            InetAddress receive = InetAddress.getByName("localhost");
            int port = 9999;
            DatagramPacket packet = new DatagramPacket(msgBytes, 0, msgBytes.length, receive, port);
            socket.send(packet);
            if ("bye".equalsIgnoreCase(msg)) {
                //关闭连接
                br.close();
                socket.close();
                break;
            }
        }
        //就这样给服务端发送了,不用建立连接,发了就不管了。
    }
}

2、接收方

package com.xhu.java.net;

import java.io.BufferedWriter;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.net.DatagramPacket;
import java.net.DatagramSocket;

public class UDPClientB {
    public static void main(String[] args) throws IOException {
        //1.开放端口
        DatagramSocket socket = new DatagramSocket(9999);
        //2.接收包
        while (true) {
            byte[] buffer = new byte[1024];
            DatagramPacket packet = new DatagramPacket(buffer, 0, buffer.length);
            //阻塞接收
            socket.receive(packet);
            //输出数据
            BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
            String msg = new String(packet.getData(), 0, packet.getLength());
            bw.write(packet.getAddress() + ":" + msg);
            bw.flush();
            bw.newLine();
            if ("bye".equalsIgnoreCase(msg)) {
                //关闭连接
                bw.close();
                socket.close();
                break;
            }
        }
        //这是不严格的服务端,不建立连接,只有发送端和接收端。这里也可以给其它发。
    }
}

四、多线程UDP聊天

先了解多线程入门

1、ClientA

package com.xhu.java.net;

import java.io.*;
import java.net.*;

public class UDPClientA {
    public static void main(String[] args) throws IOException {
        //1.开放端口
        DatagramSocket socket = new DatagramSocket(9998);
        Send s = new Send(socket);
        Receive r = new Receive(socket);
        new Thread(s).start();
        new Thread(r).start();
    }

    //发送线程
    static class Send implements Runnable {
        private DatagramSocket socket;

        public Send(DatagramSocket socket) {
            this.socket = socket;
        }

        @Override
        public void run() {
            //2.发送包
            //获取键盘输入
            BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
            while (true) {
                String msg = null;
                try {
                    msg = br.readLine();
                    byte[] msgBytes = msg.getBytes();
                    InetAddress receive = InetAddress.getByName("localhost");
                    int port = 9999;
                    DatagramPacket packet = new DatagramPacket(msgBytes, 0, msgBytes.length, receive, port);
                    socket.send(packet);
                    if ("bye".equalsIgnoreCase(msg)) {
                        //关闭连接
                        br.close();
                        socket.close();
                        break;
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    //接收线程
    static class Receive implements Runnable {
        private DatagramSocket socket;

        public Receive(DatagramSocket socket) {
            this.socket = socket;
        }

        @Override
        public void run() {
            //2.接收包
            while (true) {
                byte[] buffer = new byte[1024];
                DatagramPacket packet = new DatagramPacket(buffer, 0, buffer.length);
                //阻塞接收
                try {
                    socket.receive(packet);
                    //输出数据
                    BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
                    String msg = new String(packet.getData(), 0, packet.getLength());
                    bw.write(packet.getAddress().getHostName() + ":" + String.valueOf(packet.getPort()) + ":" + msg);
                    bw.flush();
                    bw.newLine();
                    bw.flush();
                    if ("bye".equalsIgnoreCase(msg)) {
                        //关闭连接
                        bw.close();
                        socket.close();
                        break;
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }

            }
        }
    }
}

2、ClientB

package com.xhu.java.net;

import java.io.*;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;

public class UDPClientB {
    public static void main(String[] args) throws IOException {
        //1.开放端口
        DatagramSocket socket = new DatagramSocket(9999);
        Send s = new Send(socket);
        Receive r = new Receive(socket);
        new Thread(s).start();
        new Thread(r).start();
    }

    //发送线程
    static class Send implements Runnable {
        private DatagramSocket socket;

        public Send(DatagramSocket socket) {
            this.socket = socket;
        }

        @Override
        public void run() {
            //2.发送包
            //获取键盘输入
            BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
            while (true) {
                String msg = null;
                try {
                    msg = br.readLine();
                    byte[] msgBytes = msg.getBytes();
                    InetAddress receive = InetAddress.getByName("localhost");
                    int port = 9998;
                    DatagramPacket packet = new DatagramPacket(msgBytes, 0, msgBytes.length, receive, port);
                    socket.send(packet);
                    if ("bye".equalsIgnoreCase(msg)) {
                        //关闭连接
                        br.close();
                        socket.close();
                        break;
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    //接收线程
    static class Receive implements Runnable {
        private DatagramSocket socket;

        public Receive(DatagramSocket socket) {
            this.socket = socket;
        }

        @Override
        public void run() {
            //2.接收包
            while (true) {
                byte[] buffer = new byte[1024];
                DatagramPacket packet = new DatagramPacket(buffer, 0, buffer.length);
                //阻塞接收
                try {
                    socket.receive(packet);
                    //输出数据
                    BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
                    String msg = new String(packet.getData(), 0, packet.getLength());
                    bw.write(packet.getAddress().getHostName() + ":" + String.valueOf(packet.getPort()) + ":" + msg);
                    bw.flush();
                    bw.newLine();
                    bw.flush();
                    if ("bye".equalsIgnoreCase(msg)) {
                        //关闭连接
                        bw.close();
                        socket.close();
                        break;
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }

            }
        }
    }
}

注:
1)这里有些bug啊,比如结束时,一个线程over,应该关联另一个线程,也让它over。这里主要体现思想,能通信,仅供参考。
2)如发送、接收线程体只用写原始的两个类,可以传入socket和port来完成不同的socket的线程。

五、URL下载网络资源

package com.xhu.java.net;

import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;

public class DownByURL {
    public static void main(String[] args) {
        //下载地址(下载字符)
        String urlName = "https://img-baofun.zhhainiao.com/market/133/2366564fa6b83158208eb3181752a8d6_preview.mp4";//协议:/域名或IP:端口/项目/资源
        InputStream is = null;
        OutputStream osw = null;
        try {
            URL url = new URL(urlName);
            //连接
            HttpURLConnection uc = (HttpURLConnection) url.openConnection();
            is = new BufferedInputStream(uc.getInputStream());
            osw = new BufferedOutputStream(new FileOutputStream("壁纸.mp4"));
            int n = 0;
            while ((n = is.read()) != -1) {
                osw.write(n);
            }
            osw.flush();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if (is != null) {
                try {
                    is.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if (osw != null) {
                try {
                    osw.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }

    }
}

总结

通信靠 socket,网络通信就是socket里的InputStream / OutputStream

参考文献

[1] Java 网络编程 狂神

  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2021-11-24 08:19:34  更:2021-11-24 08:21:04 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 7:26:25-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码