11

列挙型をパラメーターとして受け取る、このString.Splitオーバーロードについて質問を検討してください。StringSplitOptions

列挙型自体が公開されており、System 名前空間を含むすべてのものにアクセスできるのは悪くありませんか? つまり、列挙型はSplitメソッドのオプションに完全に固有ですが、そのスコープ外でも使用できます。

おそらく、これをモデル化するためのより良い方法があります。たとえば、列挙型を String クラス自体の中に入れて、String.SplitOptionsインスタンスを使用してアクセスするなどです。私はこれをめったに見ません(実際にそのようなケースを今は覚えていません)ので、何らかの理由で好まれていないと思います。一般に、いわば間違ったスコープでクラス/メンバーを使用することで問題が発生する可能性を下げるため、物事のスコープを縮小することがベストプラクティスだと思います。

Splitここでは例として使用していEnumますが、コード ベースでも a がメソッドまたはクラスによってのみ使用されることは非常に一般的です。私は通常、他のクラスと同様に、列挙型を別の cs ファイルでパブリック型として作成しますが、この「問題」に対する他のアプローチを聞きたいと思っています。

アップデート:

クラスと列挙型を使用してこの正確な問題を攻撃するこの記事を見つけましたが、その場合はより正しいと思われるものに逆らうようです(どういうわけか列挙型をクラス内に配置します)。そこにある ToddM からのコメントの 1 つ (たまたま同意します) は次のように述べています。FolderFilter

...

しかし、それでも、あなたの論理は間違っていると思います。クラス内に列挙型を埋め込むことに対する主な不満は、入力に時間がかかりすぎることです。C# がいかに冗長になる傾向があるかを考えると、これは実際には賢明な議論ではありません。VS では、CTRL+SPACE が友達です。

論理的には、クラス内に列挙型を配置する方がはるかに正しいと思います。あなたの例を見てみましょう: MyNameSpace.Filter とは何ですか? どこに適用されますか?名前空間のフィルターだと思いますか?特に名前空間が数十のクラスを含むように成長した場合は、わかりません。

ここで、MyNameSpace.Folder.Filter について考えてみましょう。私の考えでは、Filter が何らかの方法、形、または形式で Folder クラスに適用される方がはるかに直感的です。実際、別のクラスを名前空間に独自のフィルターの概念で追加できます。そのメンバーの 1 つは「ファイル」です。名前空間に新しいクラスを導入したからといって、その名前空間をさまざまな「ヘルパー」型で汚染する権利が与えられるわけではありません。大規模な開発チームの一員として開発している場合、あなたのスタイルは失礼です。

...

4

3 に答える 3

8

enumスコープが縮小されていることを示唆したり、より良いセマンティクスを与えたりするために、をネストするのは興味深いアイデアです。私が開発したポストコンパイラにエラーコードと警告コードの両方を含めるために、以前にこのアイデアを使用しました。このようにして、クラスまたはクラスCodeのいずれかにネストされた同じ列挙名を使用できます。ErrorWarning

一方、入れ子になった public 型は一般的に推奨されません。外部クラス名でそれらを修飾する必要があるクライアントを混乱させる可能性があります。MSDNの関連ガイドラインを参照してください。関連するもの:

public のネストされた型を論理的なグループ化構造として使用しないでください。これには名前空間を使用します。

入れ子になった型を公に公開することは避けてください。これに対する唯一の例外は、ネストされた型の変数を、サブクラス化やその他の高度なカスタマイズ シナリオなどのまれなシナリオでのみ宣言する必要がある場合です。

型が含まれている型の外部で参照される可能性が高い場合は、入れ子になった型を使用しないでください。

たとえば、クラスで定義されたメソッドに渡される列挙型は、クラスでネストされた型として定義されるべきではありません。

これらのガイドラインは、列挙型を開発するときに守らStringSplitOptionsれ、BCL の他のほとんどのガイドラインにも従ったと思います。

于 2013-10-18T13:40:54.693 に答える
0

String.Split()公開StringSplitOptionsされているため、公開する必要があります。と の両方が名前空間StringStringSplitOptions存在します。Systemどちらも公開範囲を持っています。どちらも「[相手の] 範囲外で利用可能」ではありません。

于 2013-10-18T13:34:52.233 に答える
0

理由の 1 つは、埋め込まれた列挙型を使用するすべての呼び出しが広くなるためだと思います (クラスの名前が必須のプレフィックスになります)。

ResultSetTransformer.ResultSetTransformerOptions私は個人的に、この列挙型を使用する必要があるたびに使用する必要があることに感謝しません.1行が恐ろしく長くなります.

しかし、他の人が指摘したように、おそらくこの理由で、列挙型をクラスに埋め込むことはフレームワークの標準ではないと思います。

于 2013-10-18T13:42:08.740 に答える