从 C# 中的一个小型文件传输套接字应用程序开始(目前主要是 MS 示例代码)。ManualResetEvent.WaitOne() 遇到问题。我在foreach 循环中调用它,所以也许这就是问题所在。
无论如何,我都在尝试订购/阻止 BeginSend 调用,以便它们在文件传输成功后启动。但似乎即使我在每次 BeginSend 之后调用 WaitOne() ,它们也会出现故障。
这是一个示例:
public class AsynchronousClient {
// ManualResetEvent instances signal completion.
private static ManualResetEvent connectDone =
new ManualResetEvent(false);
private static ManualResetEvent sendDone =
new ManualResetEvent(false);
private static ManualResetEvent receiveDone =
new ManualResetEvent(false);
...
private static void SendAll(Socket client, String path)
{
String[] files = GetFiles(path);
int i = 0;
foreach(String file in files){
Console.WriteLine("STEP 1 - Files left: {0}", files.Length - i);
SendFile(client, Path.GetFullPath(file), files.Length - i);
sendDone.WaitOne();
i++;
}
}
private static void SendFile(Socket client, String path, int FilesLeft )
{
byte[] filesLeft = BitConverter.GetBytes((Int64)FilesLeft);
byte[] fileData = File.ReadAllBytes(path);
byte[] fileLength = BitConverter.GetBytes((Int64) fileData.Length);
byte[] fileMD5;
using (MD5 md5Hash = MD5.Create())
{
fileMD5 = md5Hash.ComputeHash(fileData);
}
byte[] filepathdata = Encoding.Unicode.GetBytes(path);
byte[] filepathLength = BitConverter.GetBytes((Int16)filepathdata.Length);
byte[] byteData = filesLeft.Concat(fileLength).Concat(fileMD5).Concat(filepathLength).Concat(filepathdata).Concat(fileData).ToArray();
Console.WriteLine("STEP 2 - File length: {0}", fileData.Length);
// Begin sending the data to the remote device.
client.BeginSend(byteData, 0, byteData.Length, 0,
new AsyncCallback(SendCallback), client);
}
private static void SendCallback(IAsyncResult ar)
{
try
{
// Retrieve the socket from the state object.
Socket client = (Socket)ar.AsyncState;
// Complete sending the data to the remote device.
int bytesSent = client.EndSend(ar);
Console.WriteLine("STEP 3 - Sent {0} bytes to server.", bytesSent);
// Signal that all bytes have been sent.
sendDone.Set();
}
catch (Exception e)
{
Console.WriteLine(e.ToString());
}
}
...这是(不)步骤的顺序:
STEP 1 - Files left: 16
STEP 2 - File length: 432759
STEP 3 - Sent 433033 bytes to server.
STEP 1 - Files left: 15
STEP 2 - File length: 262623
STEP 1 - Files left: 14
STEP 3 - Sent 262897 bytes to server.
STEP 2 - File length: 459683
STEP 1 - Files left: 13
STEP 2 - File length: 369381
STEP 1 - Files left: 12
STEP 2 - File length: 271126
STEP 1 - Files left: 11
STEP 3 - Sent 459957 bytes to server.
STEP 3 - Sent 369679 bytes to server.
STEP 2 - File length: 1647983
STEP 1 - Files left: 10
STEP 2 - File length: 24761
STEP 1 - Files left: 9
STEP 3 - Sent 25049 bytes to server.
STEP 3 - Sent 271424 bytes to server.
STEP 2 - File length: 858717
STEP 1 - Files left: 8
STEP 2 - File length: 214031
STEP 1 - Files left: 7
STEP 2 - File length: 531963
STEP 1 - Files left: 6
STEP 2 - File length: 227950
STEP 1 - Files left: 5
STEP 2 - File length: 394068
STEP 1 - Files left: 4
STEP 2 - File length: 243546
STEP 1 - Files left: 3
STEP 2 - File length: 173656
STEP 1 - Files left: 2
STEP 2 - File length: 712417
STEP 1 - Files left: 1
STEP 3 - Sent 1648279 bytes to server.
STEP 2 - File length: 1631924
STEP 3 - Sent 859001 bytes to server.
STEP 3 - Sent 214309 bytes to server.
STEP 3 - Sent 532239 bytes to server.
STEP 3 - Sent 228226 bytes to server.
STEP 3 - Sent 394346 bytes to server.
STEP 3 - Sent 243822 bytes to server.
STEP 3 - Sent 173936 bytes to server.
STEP 3 - Sent 712701 bytes to server.
STEP 3 - Sent 1632220 bytes to server.
ReceiveCallback: bytesRead <= 0
Response received : OK
问题是:即使步骤无序,文件数据在服务器端也是完整的。在完成之前多次调用 BeginSend 似乎是可行的,但我仍然希望在开始另一次传输之前等待文件通过服务器。