我在互联网上进行一些研究之后编写了该代码,以便通过同一网络的计算机发送文件。但是,有时它会发送文件损坏或质量低(如果文件是图片)。你能看看吗? 注意:我只想发送10MB大小的文件。
服务器
class Server
{
IPEndPoint end;
Socket sock;
public Server()
{
end = new IPEndPoint(IPAddress.Any, 5656);
sock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.IP);
sock.Bind(end);
}
public static string path;
public static string MsgCurrent = "Stopped";
public void StartServer()
{
try
{
MsgCurrent = "Starting...";
sock.Listen(100);
MsgCurrent = "Works and looks for files";
Socket clientSock = sock.Accept();
byte[] clientData = new byte[1024 * 1024 * 10]; //count per byte
int receivedByteLen = clientSock.Receive(clientData);
MsgCurrent = "Receiving file ...";
int fNameLen = BitConverter.ToInt32(clientData, 0);
string fName = Encoding.ASCII.GetString(clientData, 4, fNameLen);
BinaryWriter write = new BinaryWriter(File.Open(path + "/" + fName, FileMode.Append));
write.Write(clientData, 4 + fNameLen, receivedByteLen - 4 - fNameLen);
MsgCurrent = "Saving file....";
write.Close();
clientSock.Close();
MsgCurrent = "The file was received";
}
catch
{
MsgCurrent = "Error, the file was not received";
}
}
}
客户端
class Client
{
public static string ipsendf;//added
public static string MsgCurrent = "Idle";
public static void SendFile(string fName)
{
try
{
IPAddress ip = IPAddress.Parse(ipsendf); //127.0.0.1 in "" as string
IPEndPoint end = new IPEndPoint(ip, 5656);
Socket sock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.IP);
string path = "";
fName = fName.Replace("\\", "/");
while (fName.IndexOf("/") > -1)
{
path += fName.Substring(0, fName.IndexOf("/") + 1);
fName = fName.Substring(fName.IndexOf("/") + 1);
}
byte[] fNameByte = Encoding.ASCII.GetBytes(fName);
if (fNameByte.Length > 10 * 1024 * 1024) //count per byte
{
//MsgCurrent = "File is greater than 850 kb";
MsgCurrent = "File is greater than 10MB";
return;
}
MsgCurrent = "Buffering...";
byte[] fileData = File.ReadAllBytes(path + fName);
byte[] clientData = new byte[4 + fNameByte.Length + fileData.Length];
byte[] fNameLen = BitConverter.GetBytes(fNameByte.Length);
fNameLen.CopyTo(clientData, 0);
fNameByte.CopyTo(clientData, 4);
fileData.CopyTo(clientData, 4 + fNameByte.Length);
MsgCurrent = "Connecting to server ...";
sock.Connect(end);
MsgCurrent = "File sending ...";
sock.Send(clientData);
MsgCurrent = "Disconnecting...";
sock.Close();
MsgCurrent = "The file was sent ..";
}
catch (Exception ex)
{
//do nothing
}
}
}
答案 0 :(得分:0)
套接字的默认接收大小为8,192字节(for reference)。因此,从您的代码看起来在服务器上,您只需要读取消息的前8,192个字节。
您可以增加缓冲区大小以匹配您分配的10 MB clientData
缓冲区的大小,例如,某些位于.Accept()
之后和Receive()
之前的位置。
clientSock.ReceiveBufferSize = 1024 * 1024 * 10;
或者,通过检查是否还有剩余内容可以读取并继续填充本地缓冲区。你可能会在本地网络上获得潜在的大量消息,但一般来说,通常以块的形式进行这种消息。
此外,您在服务器中写入文件时使用FileMode.Append
,而我原本以为您需要FileMode.Create
。否则,如果您发送两次相同的文件,您将获得一个20MB的文件,而不是一个10MB的文件。