我正在尝试通过套接字发送多个文件。我写的发送器和接收器功能如下。 的发件人
public void sendFileX() throws IOException {
DataOutputStream dos = new DataOutputStream(
connection.getOutputStream());
//send file number
dos.writeInt(filesToSend.length);
dos.flush();
//send file names
for (int i = 0; i < filesToSend.length; i++) {
dos.writeUTF(filesToSend[i].getName());
}
dos.flush();
//send file sizes
for (int i = 0; i < filesToSend.length; i++) {
File myFile = new File("" + filesToSend[i] + "");
dos.writeLong(myFile.length());
}
dos.flush();
// send the file
os = connection.getOutputStream();
for (int i = 0; i < filesToSend.length; i++) {
File myFile = new File("" + filesToSend[i] + "");
byte[] mybytearray = new byte[(int) myFile.length()];
fis = new FileInputStream(myFile);
bis = new BufferedInputStream(fis);
bis.read(mybytearray, 0, mybytearray.length);
os.write(mybytearray, 0, mybytearray.length);
}
os.flush();
os.close();
bis.close();
}
接收者是: 的接收器
private void recieveFileY() throws IOException
{
DataInputStream dis = new DataInputStream(connection.getInputStream());
//receive file number
int len = dis.readInt();
//receive file names
fileNames = new String[len];
for(int i = 0; i < len; i++)
{
fileNames[i] = dis.readUTF();
}
//receive file sizes
fileSizes = new long[len];
for(int i = 0; i < len; i++)
{
fileSizes[i] = dis.readLong();
}
for(int i = 0; i <len; i++)
{
System.out.println(fileNames[i]+", size: "+fileSizes[i]);
}
//receive files
is = connection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(is));
for(int i = 0; i < len; i++)
{
String fileSaveLocation = "c:/"+fileNames[i];
fos = new FileOutputStream(fileSaveLocation);
bos = new BufferedOutputStream(fos);
byte[] bytesToRead = new byte[(int) fileSizes[i]];
is.read(bytesToRead, 0, bytesToRead.length);
bos.write(bytesToRead);
}
对于这个接收器,我得到所有文件但是有些文件缺少数据,因为is.read()可能无法读取完整数据。 但如果我使用这个接收器,我应该得到整个文件。 Receiver2
private void recieveFileX() throws IOException
{
DataInputStream dis = new DataInputStream(connection.getInputStream());
//receive file number
int len = dis.readInt();
//receive file names
fileNames = new String[len];
for(int i = 0; i < len; i++)
{
fileNames[i] = dis.readUTF();
}
//receive file sizes
fileSizes = new long[len];
for(int i = 0; i < len; i++)
{
fileSizes[i] = dis.readLong();
}
for(int i = 0; i <len; i++)
{
System.out.println(fileNames[i]+", size: "+fileSizes[i]);
}
//receive files
is = connection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(is));
for(int i = 0; i < len; i++)
{
String fileSaveLocation = "c:/"+fileNames[i];
fos = new FileOutputStream(fileSaveLocation);
bos = new BufferedOutputStream(fos);
byte[] bytesToRead = new byte[(int) fileSizes[i]];
bytesRead = is.read(bytesToRead, 0, bytesToRead.length);
current = bytesRead;
do {
bytesRead = is.read(bytesToRead, current,
(bytesToRead.length - current));
if (bytesRead >= 0)
current += bytesRead;
System.out.println("I am in do while loop");
} while (bytesRead > -1);
bos.write(bytesToRead);
System.out.println("Saved " + fileNames[i]);
}
bos.flush();
bos.close();
is.close();
}
但这里的问题是在完成读取一个文件之后,inputStream中有更多数据可用,因此is.read()不会返回-1到bytesRead并且我陷入了无限循环。 请有人帮助我。提前致谢。
最后我的代码工作
private void recieveFileX() throws IOException
{
DataInputStream dis = new DataInputStream(connection.getInputStream());
//receive file number
int len = dis.readInt();
//receive file names
fileNames = new String[len];
for(int i = 0; i < len; i++)
{
fileNames[i] = dis.readUTF();
}
//receive file sizes
fileSizes = new long[len];
for(int i = 0; i < len; i++)
{
fileSizes[i] = dis.readLong();
}
for(int i = 0; i <len; i++)
{
System.out.println(fileNames[i]+", size: "+fileSizes[i]);
}
//receive files
is = connection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(is));
for(int i = 0; i < len; i++)
{
String fileSaveLocation = "c:/"+fileNames[i];
fos = new FileOutputStream(fileSaveLocation);
bos = new BufferedOutputStream(fos);
byte[] bytesToRead = new byte[(int) fileSizes[i]];
/*is.read(bytesToRead, 0, bytesToRead.length);
bos.write(bytesToRead);
bos.flush();
int count;
while ((count = is.read(bytesToRead)) > 0)
{
bos.write(bytesToRead, 0, count);
}
bytesRead = is.read(bytesToRead, 0, bytesToRead.length);
current = bytesRead;
do {
bytesRead = is.read(bytesToRead, current,
(bytesToRead.length - current));
if (bytesRead >= 0)
current += bytesRead;
System.out.println("I am in do while loop");
} while (bytesRead > -1);*/
while(true)
{
bytesRead = is.read(bytesToRead,current,(bytesToRead.length - current));
System.out.println("BytesRead = " + bytesRead);
if(bytesRead <=0)
{
System.out.println("loop breker 1 worked");
break;
}
current += bytesRead;
if(current == fileSizes[i])
{
System.out.println("loop breker 2 worked");
break;
}
System.out.println("Current = " + current);
}
bos.write(bytesToRead);
System.out.println("Saved " + fileNames[i]);
current = 0;
}
bos.flush();
bos.close();
is.close();
}
谢谢大家帮助我。
答案 0 :(得分:0)
您正在使用两种不同的复制循环。在这一个:
is.read(bytesToRead, 0, bytesToRead.length);
您完全忽略了返回值。它可以是-1表示文件结束,或者它可以是读取计数。所以你也假设read()
填充了缓冲区。没有指定这样做。你不需要两个不同的循环来做同样的事情。在两端使用相同的代码:
while ((count = in.read(buffer)) > 0)
{
out.write(buffer, 0, count);
}
这适用于任何大于零的缓冲区大小。我通常使用8192,但如果你愿意,可以使用更多。
如果要保持套接字打开以进行更多发送,则需要:
DataOutputStream.writeLong()
DataInputStream.readLong()
修改复制循环以准确读取多个字节:
long runningTotal = 0;
while (runningTotal < total && (count = in.read(buffer, 0, (int)Math.min(buffer.length, total-runningTotal)) > 0)
{
out.write(buffer, 0, count);
runningTotal += count;
}
E&安培; OE