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实现UDP传输视频等文件(简易聊天室) -> 正文阅读

[网络协议]Java实现UDP传输视频等文件(简易聊天室)

前言

UDP是一种无连接的通信方式,要使用UDP通信需要知道目的站的端口号以及IP地址

1: 类 DatagramSocket 和 DatagramPacket 实现了基于 UDP 协议网络程序。
2: UDP数据报通过数据报套接字 DatagramSocket 发送和接收,系统不保证
UDP数据报一定能够安全送到目的地,也不能确定什么时候可以抵达。

3: DatagramPacket 对象封装了UDP数据报,在数据报中包含了发送端的IP
地址和端口号以及接收端的IP地址和端口号。

4: UDP协议中每个数据报都给出了完整的地址信息,因此无须建立发送方和
接收方的连接。如同发快递包裹一样。

注:
本文将以一台计算机进行相互间通信,及模拟一个聊天室,如果需要与其他人通信,那么只需要修改目的端IP地址即可

接收端代码

由于是相互通信,因此需要实现接收以及发送操作,为了能模拟电脑上那种发送资源的情况.我设定了一个判定标志,如果有一方发送了video,那么发送方将进入发送资源状态,而接收端将接收发送端发送来的资源.
Receiver端用于接收数据,因此只需要设定自己的端口即可,因为自身的IP地址其实是一个已知量.其余部分的注释再代码中.

package IntnetProgram_ch14.ChatRoom.Finally;

import java.io.*;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.Socket;
import java.net.SocketException;
import java.util.Scanner;

/**
 * User: Serendipityl1n
 * Date: 2022/1/2
 * Time: 15:47
 * Description: No Description
 */
public class Receiver implements Runnable{
    String ReceiveData;     //表示接收端收到的数据以字符串显示展现
    byte[]buffer=new byte[1024]; //接收数据时使用的缓冲区
    DatagramPacket repacket;  //UDP数据包 其中的data域是该包中的数据
    OutputStreamWriter osw; //用于文本输出
    private DatagramSocket socket=null;//私有socket用于定义自己的端口
    private String fromWho; //判断来自谁的消息
    private int port;//自身端口号

    public Receiver(String fromWho, int port) {
        this.fromWho = fromWho;
        this.port = port;
        try {
            socket=new DatagramSocket(port);//将端口号设置为port
        } catch (SocketException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void run() {
        StringBuilder sb=new StringBuilder();
        while (true) {
            try {
                osw=new OutputStreamWriter(//使用osw可以设定字符格式
                new FileOutputStream("hell.txt",true),"UTF-8");
                repacket = new DatagramPacket(buffer,0,buffer.length);//设定接收数据包长度
                socket.receive(repacket);//侦听数据包
                ReceiveData=new String(repacket.getData(),0, repacket.getLength());//取出包数据
                if(!ReceiveData.equals("bye"))//标志判断
                    sb.append(ReceiveData);//如果不是bye就持续写入包发送来的数据
                System.out.println(fromWho+":"+ReceiveData);//输出消息
                if(ReceiveData.equals("bye"))
                {//如果是bye就结束程序 并且写入记录到txt文本中
                    osw.write(sb.toString());
                    osw.close();
                    socket.close();
                    System.exit(0);
                }
                if(ReceiveData.equals("video"))//判断标志
                {//此时video已经被读取了一次,接下来应该进入video状态的接收数据
                    socket.receive(repacket);//
                    String name=new String(repacket.getData(),0,repacket.getLength());
                    //System.out.println(name);//显示本次文件文件名
                    FileOutputStream fos=new FileOutputStream(new File("D:\\图片\\"+name));
                    //将文件写入到目的地址 地址可以自己修改
                    repacket = new DatagramPacket(buffer,0,buffer.length);//报数据缓冲区
                    do{
                        socket.receive(repacket);//读取数据
                        fos.write(repacket.getData(),0,repacket.getLength());//写入数据
                    }while(!(new String(repacket.getData(),0, repacket.getLength()).equals("over")));
                    //未收到结束标志over将一直接收
                    System.out.println("图片传输完成!!我收到了");
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

发送端代码

package IntnetProgram_ch14.ChatRoom.Finally;

import java.io.*;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetSocketAddress;
import java.net.SocketException;
import java.util.Scanner;

/**
 * User: Serendipityl1n
 * Date: 2022/1/2
 * Time: 15:47
 * Description: No Description
 */
public class Sender implements Runnable{
    DatagramSocket socket=null;
    DatagramPacket packet=null;
    String SendData=null;
    BufferedReader br;
    private int toPort;             //目的端口
    private int fromPort;           //发送端口
    private String toIP;            //目的ip
    private InetSocketAddress inet; //socket

    public Sender(int fromPort,int toPort,String toIP) {
        this.toPort = toPort;
        this.fromPort=fromPort;
        this.toIP = toIP;
        try {
            socket=new DatagramSocket(fromPort);
            inet=new InetSocketAddress(toIP,toPort);
            br=new BufferedReader(new InputStreamReader(System.in));
        } catch (SocketException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void run() {
        while (true) {
            try {
                SendData=br.readLine();
                DatagramPacket packet = new DatagramPacket(SendData.getBytes(),0,SendData.getBytes().length,this.inet);
                socket.send(packet);
                if(SendData.equals("bye"))
                {
                    try {
                        br.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                    socket.close();
                    System.exit(0);
                }
                if(SendData.equals("video"))
                {
                    //D:\\图片\\图片\\asd.jpg
                    System.out.println("输入要传输的文件的路径");
                    String path= new Scanner(System.in).nextLine();//读取路径
                    System.out.println(".....等待对方接收中");
                    //System.out.println(path.lastIndexOf("."));  //返回最后一次出现的数组下标
                    String houzhui=path.substring(path.lastIndexOf("\\\\"));//标记最后一次出现\\的地方 之后接着的就是文件名
                    packet = new DatagramPacket(houzhui.getBytes(),0,houzhui.length(),this.inet);
                    //使用substring可以得到最后的文件名 然后发送文件名 接受方就能知道这次文件的文件名
                    socket.send(packet);//发送文件名给接受发
                    //Thread.sleep(1000*5);
                    FileInputStream fis=new FileInputStream(new File(path));//文件输入流 读取文件
                    byte[]readbuffer=new byte[1024];
                    int len;
                    while((len=fis.read(readbuffer))!=-1) //判断文件还没发送结束
                    {
                        //System.out.println("发送文件中"); //发送文件
                        socket.send(new DatagramPacket(readbuffer,0,readbuffer.length,this.inet));
                    }
                    System.out.println("图片发送结束"); //文件发送结束
                    packet = new DatagramPacket("over".getBytes(),0,"over".length(),this.inet);
                    socket.send(packet);//发送结束标志位
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}

聊天对象1

用于模拟聊天室中的两个人

package IntnetProgram_ch14.ChatRoom.Finally;

/**
 * User: Serendipityl1n
 * Date: 2022/1/2
 * Time: 15:48
 * Description: No Description
 */
public class TestWife {
    public static void main(String[] args) {
        new Thread(new Receiver("同学1",7777)).start();

        new Thread(new Sender(2828,4444,"localhost")).start();

    }
}

聊天对象2

package IntnetProgram_ch14.ChatRoom.Finally;

/**
 * User: Serendipityl1n
 * Date: 2022/1/2
 * Time: 15:48
 * Description: No Description
 */
public class TestWife {
    public static void main(String[] args) {
        new Thread(new Receiver("同学2",7777)).start();

        new Thread(new Sender(2828,4444,"localhost")).start();

    }
}

源码下载:

源文件夹

文件夹格式

在这里插入图片描述

聊天记录

在这里插入图片描述
在这里插入图片描述

文件下载结果

在这里插入图片描述

  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2022-01-04 13:46:39  更:2022-01-04 13:48:58 
 
开发: 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年10日历 -2024/10/5 9:25:25-

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