0

Response と Request を処理するコードを少し書きます。どちらも XML の形式にすることも、変換とシリアル化によって作成された C# オブジェクトの形式にすることもできます。(これは .NET 2.0 です)

Response と Request は、より大きなメッセージ タイプの基本実装です。現在、GetEligibility と FindCandidates があります。

以下で使用される Model.MessageModel クラスの例:

public partial class GetEligibilityResponseMessage : ResponseMessage

public partial class ResponseMessage : Message

マッピング機能を複製したくないので、ジェネリックを使用してプロセスを簡素化することにしました。うまく機能しています。

基本クラス コード

    public virtual Model.MessageModel.Message MapToModel<T>(XmlDocument xml)
    {
        V3Mapper mapper = new V3Mapper();
        Model.MessageModel.Message message = mapper.MapToDomainModel<T>(xml, Environment) as Model.MessageModel.Message;
        return message;
    }

    public virtual XmlDocument MapToXml<T>(Model.MessageModel.Message message)
    {
        V3Mapper mapper = new V3Mapper();
        XmlDocument xml= mapper.MapToV3Message<T>(message, Environment);
        return xml;
    }

私のコードが最初に呼び出されたとき、XML ドキュメントが含まれています。このドキュメントがリクエストとしてマップされることはわかっているので、オーバーライドされた仮想メソッドを呼び出します (見苦しいと思います)。マッピングコードをベースに保持する理由は、コードを複製しないためですが、次のようにして回避したいことを正確に行っていることがわかりました。

GetEligibility : ベースクラス

   public override Model.MessageModel.Message MapToModel<T>(XmlDocument xml)
    {   
        if(typeof(T).IsAssignableFrom(typeof(GetEligibilityResponseMessage)))
        {
            return base.MapToModel<GetEligibilityResponseMessage>(xml);
        }
        else if (typeof(T).IsAssignableFrom(typeof(GetEligibilityRequestMessage))) 
        {
            return base.MapToModel<GetEligibilityRequestMessage>(xml);
        }
        return null;//because this is a quick code snippet
    }

これを行うよりエレガントな方法はありますか?応答または要求を処理しているかどうかは常にわかります。密結合になりすぎないように機能をオープンのままにしたいのですが、同時に機能的で高速にしたいと考えています。

これは、さまざまなメッセージ タイプによって実装される予定です。私は、コピー アンド ペースト スタイルのコーディングが本当に嫌いなので、洗練されたソリューションがあれば素晴らしいのですが、それがあるかどうかはわかりません。(.NET 2.0)

4

2 に答える 2

3

MethodInfo.MakeGenericMethod メソッドを使用すると、ジェネリック メソッドを呼び出す前に型をチェックする必要がなくなります。以下は、簡単な使用例です。

class Program
{
    public static void Generic<T>(T toDisplay)
    {
        Console.WriteLine("\r\nHere it is: {0}", toDisplay);
    }

    static void Main(string[] args)
    {
        MethodInfo mi = typeof(Program).GetMethod("Generic");
        MethodInfo miConstructed = mi.MakeGenericMethod(typeof(DateTime));

        DateTime now = DateTime.Now;
        miConstructed.Invoke(null, new object[] { now });
    }
}

typeof(DateTime)を使用したことに注意してください。ただし、あなたのケースでは、それをtypeof(T)に置き換えて、目的の疎結合ソリューションを実現できます。

于 2012-06-05T00:44:18.817 に答える
0

リクエストとレスポンスのタイプを検証したいだけなら、基本クラスにそれを知らせることができます:

public class BaseClass
{
    private readonly Type _requestType;
    private readonly Type _responseType;

    protected BaseClass(Type requestType, Type responseType)
    {
        _requestType = requestType;
        _responseType = responseType;
    }

    public T MapToModel<T>(XmlDocument xml)
    {
        if (typeof(T) != _requestType && typeof(T) != _responseType)
            throw new InvalidOperationException("Invalid type");

        var mapper = new V3Mapper();
        return mapper.MapToDomainModel<T>(xml, Environment);
    }
}

public GetEligibility : BaseClass
{
    public GetEligibility() 
        : base(typeof(GetEligibilityRequestMessage), typeof(GetEligibilityResponseMessage))
    {}
}

さらに一歩進んで、何を返すかを知っている専用およびメソッドを使用してBaseClass、ジェネリックにすることもできます。MapToRequestMapToResponse

public class BaseClass<TRequest, TResponse>
    where TRequest:RequestMessage,
          TResponse:ResponseMessage
{
    public TRequest MapToRequest(XmlDocument xml)
    { return MapToModel<TRequest>(xml); }

    public TResponse MapToResponse(XmlDocument xml)
    { return MapToModel<TResponse>(xml); }

    private T MapToModel<T>(XmlDocument xml)
    {
        var mapper = new V3Mapper();
        return mapper.MapToDomainModel<T>(xml, Environment);        
    }
}

public GetEligibility : BaseClass<GetEligibilityRequestMessage, GetEligibilityResponseMessage>
{}
于 2012-06-06T02:19:12.003 に答える