我正在构建一个非常简单的服务器,它必须在.NET中使用命名管道,并将在Windows窗体GUI之后运行。我已经能够在'Server'类(下面)中实现ServiceHost,并使用'Client'类与它进行通信。我遇到的问题是找出关闭在线程上运行的ServiceHost的正确方法,以及在窗体关闭时处理线程。我是线程和命名管道的新手,所以要好!
这是启动我的服务器/客户端的表单:
public partial class MyForm : Form
{
Thread server;
Client client;
public MyForm()
{
InitializeComponent();
server = new Thread(() => new Server());
server.Start();
client = new Client();
client.Connect();
}
}
private void MyForm_FormClosed(object sender, FormClosedEventArgs e)
{
// Close server thread and disconnect client.
client.Disconnect();
// Properly close server connection and dispose of thread(?)
}
这是Server类:
class Server : IDisposable
{
public ServiceHost host;
private bool disposed = false;
public Server()
{
host = new ServiceHost(
typeof(Services),
new Uri[]{
new Uri("net.pipe://localhost")
});
host.AddServiceEndpoint(typeof(IServices), new NetNamedPipeBinding(), "GetData");
host.AddServiceEndpoint(typeof(IServices), new NetNamedPipeBinding(), "SubmitData");
host.Open();
Console.WriteLine("Server is available.");
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if(!this.disposed)
{
if(disposing)
{
host.Close();
}
disposed = true;
}
}
~Server()
{
Dispose(false);
}
}
使用IDisposable是一个很好的方法,当我完成我的线程时如何调用Dispose()?
答案 0 :(得分:8)
你正在努力实现这一目标。
不要创建一个线程来启动ServiceHost
。 ServiceHost
将在内部管理自己的线程以进行服务调用。创建一个新线程只是为了启动ServiceHost
没有任何好处。在Connect()
初始化并运行之前,您的客户端ServiceHost
调用也不会成功。因此,server.Start()
和client.Connect()
之间需要同步。新线程没有为您节省任何费用。
除非你有充分的理由,否则不要在C#中使用终结器。 ~Server()
是一个坏主意。
完全摆脱Server
课程。包装器不会为您购买任何东西(除非您正在进行未在发布的代码中显示的配置管理)。
在MyForm()
中创建服务主机,并在host.Close()
中致电MyForm_FormClosed()
。完成。强>