1

MethodInfo次のように、明示的に実装されたインターフェイスメソッドを表すオブジェクトがあります。

MethodInfo GetMethod()
{
    return typeof(List<>).GetMethod(
        "System.Collections.IEnumerable.GetEnumerator",
        BindingFlags.Instance | BindingFlags.NonPublic);
}

MethodInfoこのオブジェクトをクエリして、実装するインターフェイスタイプ(Typeオブジェクトを表す)を取得するにはどうすればよいSystem.Collections.IEnumerableですか?このInterfaceMapping構造は逆の操作を提供し、特定のインターフェイスを実装するタイプのオブジェクトを取得するMethodInfoため、機能しません。

この情報のメソッド名を明確に解析できるため、これは不自然な例であることに注意してください。できればこれは避けたいと思います。

4

3 に答える 3

4

これを行う直接的な方法はわかりませんが、明らかに InterfaceMapping を逆に使用できます。メソッドの宣言型によって実装されているすべてのインターフェイスを反復処理し、メソッドがそのインターフェイスのインターフェイス マップにあるかどうかを確認します。

foreach (Type itf in method.DeclaringType.GetInterfaces())
{
  if (method.DeclaringType.GetInterfaceMap(itf).TargetMethods.Any(m => m == method))
  {
    Console.WriteLine("match: " + itf.Name);
  }
}

これは少し非効率に思えるかもしれませんが、ほとんどの型は、大したことではないほど十分な数のインターフェイスを実装しています。ただし、それほどエレガントではないことに注意してください。

于 2009-12-26T02:04:40.127 に答える
1

最初の回答で申し訳ありませんが、最初は構造体を介してメソッドにアクセスしようとしましたがそのInterfaceMap構造体のメソッドは実際にはインターフェイスを. それから私はそれをいじって、あなたが投稿した方法を使用して微妙に壊れていることに気付かなかった.DeclaringTypeMethodInfo

ただし、利点は、この微妙な違いがMethodInfo、インターフェイス メソッドのMethodInfofor と実装メソッドの for が実際には同じメソッドではないという認識につながったことです。さらに考えてみると、あなたがやりたいことを確実に行うことは不可能であると私は確信しています。

C# での明示的なインターフェイスの実装は、CLR で実際に機能する方法よりも少し複雑な構文です。他の言語では、具象クラスが複数のインターフェイス タイプを実装できるのと同じように、1 つの具象メソッドで複数のインターフェイス メソッドを実装できます。たとえば、VB.NET では、これを行うことは完全に合法です。

Public Overrides Function Baz() As String Implements IFoo.Foo, IBar.Bar

ここでは、2 つのインターフェイス メソッドを明示的に実装する 1 つのメソッドがあります。元のインターフェイス クラス、または元のインターフェイス メソッドを取得できるとしたら、どれを取得しますか? あいまいさをどのように解決しますか?

私は CLR 内部の専門家ではありませんが、インターフェイス マップは一方向だと思います。インターフェイスまたはメソッドを暗黙的または明示的に実装すると、コンパイラはインターフェイスから実装のマップを作成します。インターフェイスに対するメソッド呼び出しを処理するために必要なのはそれだけです。

C# で生成されたメソッド名は、ほぼ偶然のものと考えてください。メソッド名は ですがSystem.Collections.IEnumerable.GetEnumerator、これは単なる名前であり、実際System.Collections.IEnumerableにはメソッド自体にエンコードに関する情報はありません。

于 2009-12-26T02:14:36.303 に答える
0

試してみてくださいMethodInfo.DeclaringType

于 2009-12-26T01:27:41.417 に答える