1

次の動作を説明できる人はいますか?

特に、TestUseAndAdd が失敗するときに TestInitializeAndConfigure_Fails が失敗する理由と、TestUseOrderChanged が失敗しないときに TestUse_Fails が失敗する理由。

ありがとう

コード

interface IResource {}
class TheFirstResource : IResource {}
class TheSecondResource : IResource {}

[TestFixture]
class Test
{
    [Test]
    public void TestUse_Fails()
    {
        ObjectFactory.Initialize(init =>
        {
            init.For<IResource>().Singleton().Use<TheFirstResource>();
            init.For<IResource>().Singleton().Use<TheSecondResource>().Named("test");
        });

        IResource r1 = ObjectFactory.GetInstance<IResource>();
        IResource r2 = ObjectFactory.GetNamedInstance<IResource>("test");

        Console.WriteLine(string.Format("TestUse_Fails \n{0}\n{1}", r1, r2));
    }

    [Test]
    public void TestUseOrderChanged()
    {
        ObjectFactory.Initialize(init =>
        {
            init.For<IResource>().Singleton().Use<TheSecondResource>().Named("test");
            init.For<IResource>().Singleton().Use<TheFirstResource>();
        });

        IResource r1 = ObjectFactory.GetInstance<IResource>();
        IResource r2 = ObjectFactory.GetNamedInstance<IResource>("test");

        Console.WriteLine(string.Format("TestUseOrderChanged \n{0}\n{1}", r1, r2));
    }

    [Test]
    public void TestUseAndAdd()
    {
        ObjectFactory.Initialize(init =>
        {
            init.For<IResource>().Singleton().Use<TheFirstResource>();
            init.For<IResource>().Singleton().Add<TheSecondResource>().Named("test");
        });

        IResource r1 = ObjectFactory.GetInstance<IResource>();
        IResource r2 = ObjectFactory.GetNamedInstance<IResource>("test");

        Console.WriteLine(string.Format("TestUseAndAdd \n{0}\n{1}", r1, r2));
    }

    [Test]
    public void TestInitializeAndConfigure_Fails()
    {
        ObjectFactory.Initialize(init =>
        {
            init.For<IResource>().Singleton().Use<TheFirstResource>();
        });

        ObjectFactory.Configure(init =>
        {
            init.For<IResource>().Singleton().Add<TheSecondResource>().Named("test");
        });

        IResource r1 = ObjectFactory.GetInstance<IResource>();
        IResource r2 = ObjectFactory.GetNamedInstance<IResource>("test");

        Console.WriteLine(string.Format("TestInitializeAndConfigure_Fails \n{0}\n{1}", r1, r2));
    }
}

出力

TestUse_Fails 
Smtesting.TheSecondResource 
Smtesting.TheSecondResource 

TestUseOrderChanged 
Smtesting.TheFirstResource 
Smtesting.TheSecondResource 

TestInitializeAndConfigure_Fails 
Smtesting.TheSecondResource 
Smtesting.TheSecondResource 

TestUseAndAdd 
Smtesting.TheFirstResource 
Smtesting.TheSecondResource 
4

2 に答える 2

2

これにつまずく人々を助けるために、ジャーミー自身からの答えがあります. 彼はここのブログで質問に答えました。


For().Use() は破壊的です。For().Use() を 1 回実行してデフォルトを取得し、For().Add() を 2 回呼び出して 2 番目の登録を取得します。これら 2 つの API 呼び出しの Xml コメントを見てください。


于 2012-01-22T17:53:43.283 に答える
1

TestUse_Failsは私には理にかなっています。なぜなら、Use <>()を呼び出すことは、基本的に、型のデフォルトインスタンスを指定する(そしてそれを追加する)ことを意味するからです。一般的に最後のものが勝ちます-これに関する明示的なドキュメントを見つけることはできませんが、それはほとんどのコンテナが機能する方法です。r1呼び出しはTheSecondResource(デフォルトに設定されている最後のもの)を取得し、r2呼び出しは指定されたリソースを取得します。

init / configの後のデフォルトはTheFirstResourceであるため、TestUseOrderChangedは機能しますが、TheSecondResourceはまだ名前でコンテナーに追加されています。したがって、r1はTheFirstResourceを取得し(最後にあったため、デフォルトであるため)、r2はTheSecondResourceを名前付きインスタンスとして正しく取得します。

TestInitializeAndConfigure_Failsは奇妙なものです。私が座っているところから、デフォルトが上書きされていないため、r1はTheFirstResourceを取得する必要があります--Use <>()は再度呼び出されていません。Initializeを呼び出した後にConfigureを呼び出しても、ドキュメントに従ってコンテナをリセットしないでください。ObjectFactory.WhatDoIHave()を呼び出して、Initialize()およびConfigure()の呼び出し後にTheFirstResourceが登録されているかどうかを確認します。

私にはこれはバグのように見えます。構造マップユーザーグループ(http://groups.google.com/group/structuremap-users)に送信することを検討します。

于 2011-09-21T19:36:16.460 に答える