我使用 Spring.NET 框架创建 WCF 服务。该服务是数学服务,为客户端应用程序提供一些计算。
我对多核服务器上的 WCF 服务并行化有疑问。举个简单的例子,我有 20 个内核的服务器。
首先是一个简化的代码。
//WS interface
public interface IMatlabService
{
List<ResultData> Calculate(byte [] data);
}
//WS class definition
[ServiceBehavior(Namespace = "http://server.com/MatlabService")]
public class MatlabService: IMatlabService
{
public IMatlabManager MatlabManager{get;set:}
//web metod for math computations
public List<ResultData> Calculate(byte [] data)
{
var result = new List<ResultData>();
//do math work in another thread
Task<List<ResultData>> task = Task.Factory.StartNew<List<ResultData>>(() =>
{
return MatlabManager.CalculateWithFiniteElementMethod(data);
});
result.AddRange(task.Result)
return result;
}
}
public interface IMatlabManager
{
List<ResultData> CalculateWithFiniteElementMethod(byte [] data);
}
public class MatlabManager : IMatlabManager
{
public List<ResultData> CalculateWithFiniteElementMethod(byte [] data)
{
// do some math work
}
}
使用 Spring.NET,我将 Web 服务和管理器类配置为非单例。
Spring.NET XML 配置在这里。
Matlab 管理器配置:
<object name="matlabManager"
type="MatlabManager"
singleton="false"/>
MatlabService 配置:
<object name="matlabService"
type="MatlabService"
singleton="false">
<property name="MatlabManager" ref="matlabManager"/>
</object>
来自 web.config 的 WCF 服务配置
<behavior name="Behavior1">
<serviceMetadata httpGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="true"/>
</behavior>
<services>
<service name="matlabService"
behaviorConfiguration="Behavior1">
<endpoint address=""
binding="basicHttpBinding"
contract="IMatlabService"
bindingNamespace="http://server.com/MatlabService"/>
<endpoint contract="IMetadataExchange"
binding="mexHttpBinding"
address="mex"/>
</service>
</services>
SVC 文件。
<%@ ServiceHost Language="C#" Debug="true" Service="MatlabServiceService" Factory="Spring.ServiceModel.Activation.ServiceHostFactory" %>
我相信对于每个客户端 Web 方法调用都会创建 MatlabService 的新实例,并且 WCF 服务工作是在新线程(WCF 服务线程)上完成的,并且操作系统将此线程分配给 CPU 核心。
或者我错了,行为每次调用都会创建新的服务对象,我必须在 ServiceBehavior 属性 InstanceContextMode 中定义?
[服务行为(InstanceContextMode=InstanceContextMode.PerCall)]
在 MatlabService 的 Web 方法计算中,我使用 System.Threading.Tasks 进行并行化,因此数学工作在另一个线程(数学线程)中完成。
为每个调用创建 WCF 服务线程,并在 WCF 服务线程中创建数学线程。
我不确定这是否属实。
也许需要在 ConcurrencyMode 中允许 WCF 服务中的多线程?
[ServiceBehavior(InstanceContextMode=InstanceContextMode.PerCall,ConcurrencyMode = ConcurrencyMode.Multiple)]
我想听听如何并行化多核 CPU 的 web 方法调用。我用谷歌搜索,但没有找到任何清晰有用的东西,因为我使用 Spring.NET 框架来创建 WCF 服务。