Office 中的線程支援

本文提供 Microsoft Office 物件模型中如何支援線程的資訊。 Office 物件模型不是安全線程,但可以在 Office 方案中使用多個線程。 Office 應用程式 數據分割是元件物件模型 (COM) 伺服器。 COM 可讓用戶端在任意線程上呼叫 COM 伺服器。 對於不安全線程的 COM 伺服器,COM 會提供一個機制來串行化並行呼叫,讓一個邏輯線程隨時在伺服器上執行。 這種機制稱為單個線程 Apartment (STA) 模型。 由於呼叫已串行化,因此當伺服器忙碌或正在處理背景線程上的其他呼叫時,呼叫端可能會封鎖一段時間。

適用於: 本主題中的資訊適用於檔層級專案和 VSTO 載入宏專案。 請參閱 Office 應用程式 lication 和項目類型所提供的功能。

使用多個線程時所需的知識

若要使用多個線程,您必須至少具備下列多線程層面的基本知識:

  • Windows API

  • COM 多線程概念

  • 並行

  • 同步處理

  • 封送處理

    如需多線程的一般資訊,請參閱 Managed 線程處理

    Office 會在主要 STA 中執行。 瞭解這的含意,可讓您瞭解如何搭配 Office 使用多個線程。

基本多線程案例

Office 方案中的程序代碼一律會在主要 UI 線程上執行。 您可能想要藉由在背景線程上執行個別工作,來讓應用程式效能順暢。 目標是一次完成兩個工作,而不是一個工作,後面接著另一個工作,這應該會導致更順暢的執行(使用多個線程的主要原因)。 例如,您可能會在主要 Excel UI 線程上擁有事件程式代碼,而且在背景線程上,您可以執行一項工作,從伺服器收集數據,並使用來自伺服器的數據來更新 Excel UI 中的數據格。

呼叫 Office 物件模型的背景線程

當背景線程呼叫 Office 應用程式 lication 時,呼叫會自動跨 STA 界限封送處理。 不過,不保證 Office 應用程式 lication 可以在背景線程建立呼叫時處理呼叫。 有幾種可能性:

  1. Office 應用程式 複製必須抽出訊息,呼叫才能有機會輸入。 如果在不產生的情況下進行繁重的處理,可能需要一點時間。

  2. 如果另一個邏輯線程已經在Apartment中,新線程就無法輸入。 當邏輯線程進入 Office 應用程式 數據刪除,然後重新進入呼叫端的公寓時,就會發生這種情況。 應用程式會遭到封鎖,等待該呼叫傳回。

  3. Excel 可能處於無法立即處理來電的狀態。 例如,Office 應用程式 lication 可能會顯示強制回應對話方塊。

    如需 2 和 3 的可能性,COM 會提供 IMessageFilter 介面。 如果伺服器實作它,所有呼叫都會透過 HandleIncomingCall 方法輸入。 針對可能性 2,系統會自動拒絕呼叫。 針對可能性 3,伺服器可以根據情況拒絕呼叫。 如果呼叫遭到拒絕,呼叫端必須決定該怎麼做。 一般而言,呼叫端會 實作 IMessageFilter,在此情況下,會通知 RetryRejectedCall 方法拒絕。

    不過,在Visual Studio中使用 Office 開發工具建立的解決方案案例中,COM Interop 會將所有拒絕的呼叫 COMException 轉換成 (「訊息篩選指出應用程式忙碌中」)。 每當您在背景線程上進行物件模型呼叫時,都必須準備好處理此例外狀況。 通常,這牽涉到重試一段時間,然後顯示對話框。 不過,您也可以將背景線程建立為 STA,然後註冊該線程的訊息篩選器來處理此案例。

正確啟動線程

當您建立新的 STA 線程時,請在啟動線程之前,將 Apartment 狀態設定為 STA。 下列程式碼範例會示範如何執行這項操作。

System.Threading.Thread t = new System.Threading.Thread(AnObject.aMethod);

t.SetApartmentState(System.Threading.ApartmentState.STA);
t.Start();

如需詳細資訊,請參閱 受控線程最佳做法

無模式表單

無模式表單可在顯示表單時,允許與應用程式進行某種類型的互動。 使用者與窗體互動,表單與應用程式互動而不關閉。 Office 物件模型支援 Managed 無模式表單;不過,不應該在背景線程上使用它們。