<Method> 要素 (.NET ネイティブ)
コンストラクターまたはメソッドにランタイム リフレクション ポリシーを適用します。
構文
<Method Name="method_name"
Signature="method_signature"
Browse="policy_type"
Dynamic="policy_type" />
属性および要素
以降のセクションでは、属性、子要素、および親要素について説明します。
属性
属性 | 属性の型 | 説明 |
---|---|---|
Name |
全般 | 必須の属性です。 メソッド名を指定します。 |
Signature |
全般 | 省略可能な属性です。 メソッド シグネチャを指定します。 複数のパラメーターが存在する場合はコンマで区切られます。 たとえば、次の <Method> 要素は ToString(String, IFormatProvider) メソッドのポリシーを定義します。<Type Name="System.DateTime"> <Method Name="ToString" Signature="System.String,System.IFormatProvider" Dynamic="Required" /> </Type> 属性が存在しない場合、ランタイム ディレクティブは、メソッドのすべてのオーバーロードに適用されます。 |
Browse |
リフレクション | 省略可能な属性です。 メソッドに関する情報の照会やメソッドの列挙を制御しますが、実行時の動的呼び出しは有効にしません。 |
Dynamic |
リフレクション | 省略可能な属性です。 コンストラクターまたはメソッドへの実行時アクセスを制御して、動的プログラミングを有効にします。 このポリシーにより、実行時にメンバーを動的に呼び出すことができます。 |
Name 属性
[値] | 説明 |
---|---|
method_name | メソッド名。 このメソッドの型は、親 <Type> または <TypeInstantiation> 要素によって定義されます。 |
シグネチャ属性
[値] | 説明 |
---|---|
method_signature | メソッド シグネチャを形成するパラメーター型です。 複数のパラメーターは、"System.String,System.Int32,System.Int32)" のようにコンマで区切ります。 パラメーターの型名は完全修飾されている必要があります。 |
その他すべての属性
[値] | 説明 |
---|---|
policy_setting | このポリシーの種類に適用する設定です。 指定できる値は、Auto 、Excluded 、Included 、および Required です。 詳細については、「ランタイム ディレクティブのポリシー設定」を参照してください。 |
子要素
要素 | 説明 |
---|---|
<パラメーター> | メソッドに渡された引数の型にポリシーを適用します。 |
<GenericParameter> | ジェネリック型またはメソッドのパラメーターの型にポリシーを適用します。 |
<ImpliesType> | 型にポリシーを適用します (含んでいる <Method> 要素によって表されるメソッドにそのポリシーが適用されている場合)。 |
<TypeParameter> | メソッドに渡された Type 引数によって表される型にポリシーを適用します。 |
親要素
要素 | 内容 |
---|---|
<種類> | 型とそのすべてのメンバーにリフレクション ポリシーを適用します。 |
<TypeInstantiation> | 構築されたジェネリック型とそのすべてのメンバーにリフレクション ポリシーを適用します。 |
解説
ジェネリック メソッドの <Method>
要素は、独自のポリシーを持たないインスタンス化すべてにそのポリシーを適用します。
Signature
属性を使用して、特定のメソッド オーバーロードのポリシーを指定できます。 そうしない場合、Signature
属性が存在しないと、メソッドのすべてのオーバーロードにランタイム ディレクティブが適用されます。
<Method>
要素を使用してコンストラクターのランタイム リフレクション ポリシーを定義することはできません。 代わりに、<Assembly>、<Namespace>、<Type>、または <TypeInstantiation> 要素の Activate
属性を使用します。
例
次の例の Stringify
メソッドは、リフレクションを使用してオブジェクトを文字列形式に変換する汎用書式設定メソッドです。 オブジェクトの既定の ToString
メソッドを呼び出すことに加えて、このメソッドでは、オブジェクトの ToString
メソッドに書式文字列、IFormatProvider 実装、またはその両方を渡して、書式設定された結果文字列を生成できます。 また、数値をバイナリ、16 進数、または 8 進数形式に変換するいずれかの Convert.ToString オーバーロードを呼び出すこともできます。
public class Stringify
{
public static string ConvertToString(Object[] obj)
{
if (obj == null)
throw new NullReferenceException("The obj parameter cannot be null.");
if (obj.Length == 0) return String.Empty;
if (obj[0].GetType() == typeof(String))
return obj[0] as string;
if (obj.Length == 1) return obj[0].ToString();
if (obj.Length > 3)
throw new ArgumentOutOfRangeException("The array can have from zero to three elements.");
string retval = "";
// Parameters indicate either a format specifier, numeric base, or format provider,
// or a format specifier with an IFormatProvider.
// A string as the first parameter indicates a format specifier.
if (obj[1].GetType() == typeof(String)) {
Type t = obj[0].GetType();
if (obj.Length == 2)
{
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { typeof(String) });
retval = m.Invoke(obj[0], new object[] { obj[1] }).ToString();
}
else
{
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { typeof(String), obj[2].GetType() });
retval = m.Invoke(obj[0], new object[] { obj[1], obj[2] }).ToString();
}
}
else if (obj[1] is IFormatProvider)
{
Type t = obj[0].GetType();
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { obj[1].GetType() } );
retval = m.Invoke(obj[0], new object[] { obj[1] }).ToString();
}
// The second parameter is a base, so call Convert.ToString(number, int).
else {
Type t = typeof(Convert);
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { obj[0].GetType(), obj[1].GetType() } );
retval = m.Invoke(null, obj).ToString();
}
return retval;
}
}
Stringify
メソッドは、次のようなコードによって呼び出すことができます。
public class Stringify
{
public static string ConvertToString(Object[] obj)
{
if (obj == null)
throw new NullReferenceException("The obj parameter cannot be null.");
if (obj.Length == 0) return String.Empty;
if (obj[0].GetType() == typeof(String))
return obj[0] as string;
if (obj.Length == 1) return obj[0].ToString();
if (obj.Length > 3)
throw new ArgumentOutOfRangeException("The array can have from zero to three elements.");
string retval = "";
// Parameters indicate either a format specifier, numeric base, or format provider,
// or a format specifier with an IFormatProvider.
// A string as the first parameter indicates a format specifier.
if (obj[1].GetType() == typeof(String)) {
Type t = obj[0].GetType();
if (obj.Length == 2)
{
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { typeof(String) });
retval = m.Invoke(obj[0], new object[] { obj[1] }).ToString();
}
else
{
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { typeof(String), obj[2].GetType() });
retval = m.Invoke(obj[0], new object[] { obj[1], obj[2] }).ToString();
}
}
else if (obj[1] is IFormatProvider)
{
Type t = obj[0].GetType();
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { obj[1].GetType() } );
retval = m.Invoke(obj[0], new object[] { obj[1] }).ToString();
}
// The second parameter is a base, so call Convert.ToString(number, int).
else {
Type t = typeof(Convert);
MethodInfo m = t.GetRuntimeMethod("ToString", new Type[] { obj[0].GetType(), obj[1].GetType() } );
retval = m.Invoke(null, obj).ToString();
}
return retval;
}
}
ただし、.NET ネイティブでコンパイルすると、NullReferenceExceptionや MissingRuntimeArtifactException 例外など、実行時に多数の例外がスローされる可能性があります。これは、Stringify
メソッドが主に .NET Framework クラス ライブラリのプリミティブ型の動的な書式設定をサポートすることを目的としているために発生します。 ただし、既定のディレクティブ ファイルではそのメタデータを使用できません。 メタデータが使用できたとしても、適切な ToString
の実装がネイティブ コードに含まれていないため、この例は MissingRuntimeArtifactException 例外をスローします。
これらの例外はすべて、<Type> 要素を使用してメタデータが存在する必要がある型を定義し、<Method>
要素を追加して動的に呼び出せるメソッド オーバーロードの実装も必ず存在するようにすることで排除できます。 これらの例外を排除し、例をエラーなしで実行できるようにした default.rd.xml ファイルを次に示します。
<Directives xmlns="http://schemas.microsoft.com/netfx/2013/01/metadata">
<Application>
<Assembly Name="*Application*" Dynamic="Required All" />
<Type Name = "System.Convert" Browse="Required Public" Dynamic="Required Public" >
<Method Name="ToString" Dynamic ="Required" />
</Type>
<Type Name="System.Double" Browse="Required Public">
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name ="System.Int32" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name ="System.Int64" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Namespace Name="System" >
<Type Name="Byte" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="DateTime" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="Decimal" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="Guid" Browse ="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="Int16" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="SByte" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="Single" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="TimeSpan" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="UInt16" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="UInt32" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
<Type Name="UInt64" Browse="Required Public" >
<Method Name="ToString" Dynamic="Required" />
</Type>
</Namespace>
</Application>
</Directives>