メソッドを拡張可能にする属性

この記事では、メソッドの拡張性機能を制御するために使用できるさまざまな属性について説明します。

次の表は、メソッドの拡張性およびアクセシビリティの既定のサポートの概要を提供します。 さらに、メソッド シグネチャの変更に関するガイダンスも提供します。

特性 フック可能 折り返し可能 置き換え可能 Accessibility Signature
private いいえ N/A N/A 定義されているクラス内からアクセスできます。 シグネチャは変更可能
保護された内部 いいえ はい。プラットフォーム更新 25 以降から いいえ 定義されているクラス、派生クラス、および同じモデル内のクラスからアクセスできます。 シグネチャでは互換性が維持されている必要があります
内部 いいえ いいえ いいえ 同じモデルでアクセスできます。 シグネチャは変更可能
を保護した いいえ はい。最終とマークされている場合以外 いいえ 定義されているクラスと派生クラスからアクセスできます。 シグネチャでは互換性が維持されている必要があります
public イエス はい。最終とマークされている場合以外 いいえ 定義されているクラス、派生クラス、および定義クラスにアクセスできるその他のクラス内からアクセスできます。 シグネチャでは互換性が維持されている必要があります

フック可能

メソッドがフック可能な場合、拡張担当者はプリイベントとポストイベントにサブスクライブできます。

パブリック メソッドの場合、メソッドに Hookable(false) を追加することでオプトアウトできます。

[Hookable(true)] をメソッドに追加して、プライベートおよび保護されたメソッドをオプトインできます。

メソッドが明示的に [Hookable(false)] としてマークされている場合、ラップできません。

コードの作成時のベスト プラクティス

メソッドがフック可能な場合、コンパイラは拡張ポイントでメソッドを有効にするために特別な中間言語 (IL) コードを生成します。 余分なコードにはパフォーマンスのオーバーヘッドがありますが、このオーバーヘッドはほとんどの場合は無視できます。 ただし、パフォーマンスが重要なメソッドの場合は、メソッドをフック不可としてマークすることを検討してください。

折り返し可能

メソッドが折り返し可能な場合は、拡張担当者はコマンド チェーン (CoC) を使用して折り返すことができます。 拡張担当者は、CoC を中断することが許可されていないため、次を呼び出す必要があります。

保護されたパブリック メソッドの場合、メソッドに [Wrappable(false)] を追加することでオプトアウトできます。

プライベート メソッドをオプトインすることはできません。

コードの作成時のベスト プラクティス

CoC は、さまざまな点で継承に似ています。 通常、他のユーザーが変更するのではなくメソッドを呼び出すことができるようにするには、最終としてメソッドをマークします。 これらのメソッドをラップ不可またはフック不可としてマークすることを検討してください。

置き換え可能

メソッドが置き換え可能な場合は、拡張担当者は CoC を使用して折り返しできますが、無条件に次を呼び出す必要はありません。 エクステンダーは CoC を中断できますが、条件付きで中断するだけであることが期待されます。 コンパイラは、次の呼び出しを強制しません。

置き換え可能にするには、メソッドも折り返し可能である必要があります。

折り返し可能なメソッドの場合、メソッドに [Replaceable] を追加することでオプトインできます。

コードの作成時のベスト プラクティス

メソッドの置き換え可能な場合、CoC を使用して拡張することができ、次の実行をスキップできます。 メソッドを置き換え可能にできるようにする前に、拡張担当者がメソッドの実行をスキップした場合の機能への影響を十分に評価する必要があります。

  • [Replaceable] を持つメソッドに、メソッドの責任を説明する XML ドキュメントがあることを確認します

  • 顧客が置き換えられたロジックをスキップして何もしないようにするには、[Replaceable]使用しません

  • SysExtension を代わりに使用可能な場合は、ファクトリ メソッドに [Replaceable]使用しません

  • メソッドがデータベースまたはクラスの状態を変更する場合、[Replaceable] の使用を回避します

  • メソッドが複数の工程を実行し、複数の責任を持つ場合、[Replaceable] の使用を回避します。 代わりに、それぞれが単一の責任を持つ別個のメソッドにメソッドをリファクタリングし、どのメソッドを実際に置き換え可能にする必要があるかを検討します。

  • 変換を解決するために、[Replaceable] の使用を検討します

    例: 既定のブロックがスローを持つ列挙値より切り替えステートメントを使う列挙変換。

  • ルックアップと jumpref をオーバーライドするために [Replaceable] を使用することを検討します

拡張担当者のベスト プラクティス

  • 置き換えられるロジックとは異なる責任を持つロジックを記述しないでください
  • 置き換えロジックが適用されない場合、基本機能を呼び出します (次を呼び出し)。
  • 基本機能 (次を呼び出し) を呼び出さずにロジックを完全に置き換えることを回避します