如何在Java中通过套接字发送文件列表

如何在Java中通过套接字发送文件列表,java,sockets,Java,Sockets,我使用该代码通过套接字发送单个文件。但是,我需要能够通过套接字发送多个文件(基本上是一个目录中的所有文件),并让客户端识别文件之间的分离。坦率地说,我完全不知道该怎么办。任何提示都会有帮助 注意1:我需要一种方法,以一个连续的流发送文件,客户端可以将其分离为单个文件。它不能依赖客户机的个别请求 注2:要回答一个问题,我很确定我会在评论中得到答案,不,这不是作业 编辑有人建议我可以先发送文件大小,然后再发送文件本身。我如何才能做到这一点,因为通过套接字发送文件总是以预先确定的字节数组或单个字节完成

我使用该代码通过套接字发送单个文件。但是,我需要能够通过套接字发送多个文件(基本上是一个目录中的所有文件),并让客户端识别文件之间的分离。坦率地说,我完全不知道该怎么办。任何提示都会有帮助

注意1:我需要一种方法,以一个连续的流发送文件,客户端可以将其分离为单个文件。它不能依赖客户机的个别请求

注2:要回答一个问题,我很确定我会在评论中得到答案,不,这不是作业


编辑有人建议我可以先发送文件大小,然后再发送文件本身。我如何才能做到这一点,因为通过套接字发送文件总是以预先确定的字节数组或单个字节完成,而不是以
file.length()

返回的长度来完成。您可以在客户端压缩文件,并将压缩后的流发送到服务器

e、 g:

OutputStream output = connection.getOutputStream();
ZipOutputStream out = new ZipOutputStream(output);

也许最快的方法是自动将目录中的文件压缩并解压到一个文件中,请参见java.util.zip package

您可以在每个文件之前先发送文件的大小,这样客户端就可以知道当前文件何时结束,并期待下一个文件(大小)。这将允许您对所有文件使用一个连续流。

一个非常简单的方法是在发送每个文件之前发送文件长度,以便确定文件之间的间隔


当然,如果接收过程是Java,您可以只发送对象。

以下是完整的实现:

发送方:

String directory = ...;
String hostDomain = ...;
int port = ...;

File[] files = new File(directory).listFiles();

Socket socket = new Socket(InetAddress.getByName(hostDomain), port);

BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
DataOutputStream dos = new DataOutputStream(bos);

dos.writeInt(files.length);

for(File file : files)
{
    long length = file.length();
    dos.writeLong(length);

    String name = file.getName();
    dos.writeUTF(name);

    FileInputStream fis = new FileInputStream(file);
    BufferedInputStream bis = new BufferedInputStream(fis);

    int theByte = 0;
    while((theByte = bis.read()) != -1) bos.write(theByte);

    bis.close();
}

dos.close();
String dirPath = ...;

ServerSocket serverSocket = ...;
Socket socket = serverSocket.accept();

BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
DataInputStream dis = new DataInputStream(bis);

int filesCount = dis.readInt();
File[] files = new File[filesCount];

for(int i = 0; i < filesCount; i++)
{
    long fileLength = dis.readLong();
    String fileName = dis.readUTF();

    files[i] = new File(dirPath + "/" + fileName);

    FileOutputStream fos = new FileOutputStream(files[i]);
    BufferedOutputStream bos = new BufferedOutputStream(fos);

    for(int j = 0; j < fileLength; j++) bos.write(bis.read());

    bos.close();
}

dis.close();
接收器端:

String directory = ...;
String hostDomain = ...;
int port = ...;

File[] files = new File(directory).listFiles();

Socket socket = new Socket(InetAddress.getByName(hostDomain), port);

BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
DataOutputStream dos = new DataOutputStream(bos);

dos.writeInt(files.length);

for(File file : files)
{
    long length = file.length();
    dos.writeLong(length);

    String name = file.getName();
    dos.writeUTF(name);

    FileInputStream fis = new FileInputStream(file);
    BufferedInputStream bis = new BufferedInputStream(fis);

    int theByte = 0;
    while((theByte = bis.read()) != -1) bos.write(theByte);

    bis.close();
}

dos.close();
String dirPath = ...;

ServerSocket serverSocket = ...;
Socket socket = serverSocket.accept();

BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
DataInputStream dis = new DataInputStream(bis);

int filesCount = dis.readInt();
File[] files = new File[filesCount];

for(int i = 0; i < filesCount; i++)
{
    long fileLength = dis.readLong();
    String fileName = dis.readUTF();

    files[i] = new File(dirPath + "/" + fileName);

    FileOutputStream fos = new FileOutputStream(files[i]);
    BufferedOutputStream bos = new BufferedOutputStream(fos);

    for(int j = 0; j < fileLength; j++) bos.write(bis.read());

    bos.close();
}

dis.close();
String dirPath=。。。;
ServerSocket服务器套接字=。。。;
Socket=serverSocket.accept();
BufferedInputStream bis=新的BufferedInputStream(socket.getInputStream());
DataInputStream dis=新的DataInputStream(bis);
int filescont=dis.readInt();
File[]files=新文件[filescont];
对于(int i=0;i

我没有测试它,但我希望它能工作

谢谢,但是拉链不是特别有用。我需要一个能够在下一个文件仍在流传输时处理一个文件的流。你能给我一个快速的例子吗?我对套接字编程非常陌生,我不确定如何发送文件的大小,因为您要么必须发送一个预先确定的字节数组,要么发送一个字节,而不是
file.length()
将返回的长度。您可以将
file.length()
转换为适当大小的字节数组并使用它(
Long.SIZE
告诉您位的数量,通过一点数学,您可以得到字节的数量)--查看如何执行Long->byte数组conversion@Attila或者简单地使用
DataInputStream
DataOutputStream
:)不确定我是否不清楚或者什么,但是客户端和服务器似乎与我的意图相反。不管怎样,这是一个非常简单的解决方案。谢谢@伊渥克哎呀,我看到标题后就写代码了。然而,这并没有什么大的区别,我很高兴我能帮上忙:)完美的解决方案。非常感谢
readUTF()
如何知道文件名何时完成?如果您能接收到另一种语言的流,您需要如何识别文件名的结尾和数据的开头?