首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

Socket 非同步操作方法詳解(一):BeginAccept/EndAccept 核心機制與程式碼範例

     編輯:關於C語言

為什麼需要非同步 Socket?

傳統同步 Accept() 會阻塞主執行緒,導致應用程式無法處理其他工作(如 UI 回應、其他連線)。非同步模式將「等待連線」交給作業系統與執行緒池,主執行緒得以自由執行其他邏輯。

Socket 非同步方法配對表

Begin 方法End 方法功能
BeginAcceptEndAccept非同步接受連入連線
BeginConnectEndConnect非同步連線至遠端
BeginDisconnectEndDisconnect非同步斷開連線
BeginReceiveEndReceive非同步接收資料
BeginReceiveFromEndReceiveFrom非同步從指定裝置接收 (UDP)
BeginSendEndSend非同步發送資料
BeginSendFileEndSendFile非同步發送檔案
BeginSendToEndSendTo非同步發送至特定遠端 (UDP)

所有方法皆為成對出現,核心機制:在 Begin 方法註冊回呼,事件發生時執行回呼,回呼中呼叫對應 End 方法取得結果。

BeginAccept / EndAccept 詳細簽章

BeginAccept

public IAsyncResult BeginAccept(AsyncCallback callback, object state);
  • callback:連線建立時觸發的委派。
  • state:使用者自訂狀態物件,常傳遞 Socket 本身。

EndAccept 三種多載

public Socket EndAccept(IAsyncResult asyncResult);
public Socket EndAccept(out byte[] buffer, IAsyncResult asyncResult);
public Socket EndAccept(out byte[] buffer, out int bytesTransferred, IAsyncResult asyncResult);
多載用途
第 1 種最常用,單純取得新連線的 Socket
第 2 種同時取得新連線與連線建立時隨附的初始資料(需啟用 SocketOptionName.AcceptConnection)
第 3 種更進一步取得已傳輸位元組數
  • asyncResult:儲存非同步作業狀態與使用者資料。
  • out buffer / out bytesTransferred:類似 ref,但強調「輸出」語意,呼叫前無需初始化。

完整程式碼範例:非同步 TCP 伺服器

private AsyncCallback callbackOnAccept;
private Socket listener;

public void StartServer()
{
    listener = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
    listener.Bind(new IPEndPoint(IPAddress.Any, 8888));
    listener.Listen(100);

    callbackOnAccept = new AsyncCallback(OnAccept);
    listener.BeginAccept(callbackOnAccept, listener); // 開始第一次非同步接受
}

private void OnAccept(IAsyncResult ar)
{
    Socket listener = (Socket)ar.AsyncState;
    Socket client = listener.EndAccept(ar); // 取得新連線

    // 立即啟動下一次接受,形成循環
    listener.BeginAccept(callbackOnAccept, listener);

    // 這裡處理 client 通訊(可再用 BeginReceive/EndReceive)
    Console.WriteLine($"Client connected: {client.RemoteEndPoint}");
}

關鍵重點

  1. 回呼中必須再次呼叫 BeginAccept,否則伺服器只能接受一個連線。
  2. state 傳遞 listener 讓回呼能持續接受新連線。
  3. 非同步接受不阻塞主執行緒,適合 WinForm/WPF/UI 應用。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved