14

我正在创建一个自定义的.net 硬件框架,其他程序员将使用它来控制某些硬件。他们将添加对我们的 DLL 的引用以访问我们的硬件框架。我需要一个可以从多个应用程序(进程)访问的共享类。

单例模式似乎是我需要的,但它只适用于进程中的多个线程。我可能完全错了,但这是我目前拥有的 C# 代码示例。我不禁觉得设计不正确。我希望我可以分享更具体的信息,但我不能。

  • 我必须强调,我无法控制客户应用程序。解决方案必须包含在框架 (DLL) 本身内。

框架:(共享 DLL)

public class Resources
{
    static readonly Resources m_instance = new Resources();

    public string Data;

    private Resources()
    {
        Data = DateTime.Now.ToString();
    }

    public static Resources Instance
    {
        get
        {
            return m_instance;
        }
    }
} 

测试应用程序:(最终是客户应用程序)

class Program
{
    static void Main(string[] args)
    {
        Console.WriteLine("Press enter to capture the resource!");
        Console.ReadLine();

        var resources = Resources.Instance;
        Console.WriteLine("\r\n{0}: {1}\r\n", Thread.CurrentThread.ManagedThreadId, resources.Data);

        BackgroundWorker worker = new BackgroundWorker();
        worker.DoWork += WorkerDoWork;
        worker.RunWorkerAsync();

        while (worker.IsBusy)
        {
            Thread.Sleep(100);
        }

        Console.WriteLine("Press enter to close the process!");
        Console.ReadLine();
    }

    static void WorkerDoWork(object sender, DoWorkEventArgs e)
    {
        var resources = Resources.Instance;
        Console.WriteLine("\r\n{0}: {1}\r\n", Thread.CurrentThread.ManagedThreadId, resources.Data);
    }
}

第一个启动的应用程序提供以下输出:

按回车键获取资源!

1:2009 年 6 月 24 日上午 8 点 27 分 34 秒

3:2009 年 6 月 24 日上午 8 点 27 分 34 秒

按回车关闭进程!

第二个应用程序提供以下输出:

按回车键获取资源!

9:2009 年 6 月 24 日上午 8 点 27 分 35 秒

10:2009 年 6 月 24 日上午 8 点 27 分 35 秒

按回车关闭进程!

结论

我希望看到两个应用程序都返回相同的类的第一次实例化时间的字符串。

如您所见,单例适用于进程内的多个线程,但不适用于跨进程。也许这无法完成,因为我似乎找不到任何解决方案。

4

5 回答 5

7

是的,可以在多个进程之间共享一个单例。但是,您需要利用支持进程间通信的技术来实现此结果。

允许您直接共享对象的最流行的技术是 Remoting 和 WCF。

举一个与其中任何一个共享单例的示例超出了 SO 答案的范围。但是对于这些中的每一个,网上都有很多教程。谷歌搜索任何一种技术加上单例应该会让你走上正确的道路。

于 2009-06-24T12:44:36.327 回答
5

您不能使用单例跨应用程序同步。每个都在自己的应用程序空间中运行,出于安​​全考虑,不能访问内存/对象/等。从另一个没有通信方法(如远程)同步两个他们将不得不远程进入第三个程序。

于 2009-06-24T12:43:27.653 回答
2

为了补充凯文的答案,您的类 Resources 的构造函数应该真正私有化,以使其成为真正的单例,否则没有什么能阻止某人通过构造函数创建 Resources 类的新实例。这并不能解决您的问题,但确实可以防止滥用 Singleton。

于 2009-06-24T12:44:37.060 回答
1

简单地从两个不同进程调用不同程序集中的单例属性将创建该类的不同实例。

但是您可以使用 .Net Remoting在进程之间轻松共享信息,或者如果您只需要简单的信号 ( EventWaitHandle ),则可以触发进程间事件。

[编辑:]为了让调用者看起来像一个单例,您可以公开一个类,该类将在内部使用远程处理来实例化单例,然后透明地返回实例。这是一个(我认为)这样做的例子:http: //www.codeproject.com/KB/dotnet/remotingsingleton.aspx

于 2009-06-24T12:53:25.607 回答
0

如上所述,有一些方法可以做到这一点。但是如果你使用 WCF 或远程处理就很笨拙。请尝试进程间线程同步技术。

有关更多信息,请阅读有关线程的在线免费电子书

http://www.albahari.com/threading/

在这里特别看到跨进程同步结构......

http://www.albahari.com/threading/part2.aspx#_Synchronization_Essentials

于 2009-06-24T13:00:27.090 回答