自転車エリミネーター:再利用可能なコード

みなさんこんにちは! 昔、良い記事のシリーズがあったことを覚えていますか? だから私はそれを続けたいです。 ただし、今回は、ユビキタスな問題を解決する膨大な数のライブラリについては検討しませんが、膨大な問題を解決できるライブラリについてのみ検討します。 みなさんはかつて次の形式の行を書いたようです。



void SomeMethod(IEmployee lazyguy) { if(lazyguy == null) throw new ArgumentException(“lazyguy”); // Do something with lazy guy. Fire him, for example. }
      
      







誰かがこれを変えようとしました:



 void SomeMethod(IEmployee lazyguy) { UniversalValidator.CheckNotNull(lazyguy); // Meet with him and talk about motivations }
      
      







誰かがそれを似たようなものに変えました。 しかし、誰もが、間違いなく、何かが間違っていたという残留物がありました。 それはどういうわけか異なるでしょう。 結果は何ですか? 四角い車輪を備えた膨大な数の自転車! 別の方法でそれを行うには?



魂が幸せで、コードがきれいなときは異なります。これは次のように書くときです。

 void SomeMethod([NotNull] IEmployee lazyguy) { // Promote him to be head of department }
      
      





同意します 属性は記事のタグと同じであると言うことで私に反対することができます。誰も読んでいない限り、魔法は機能しません。 そして、あなたは正しいでしょう。 私が話したいプログラム-PostSharpを使用すると、このようなことができます。 メソッドのパラメーターに適用され、プログラムコードにnullチェックを挿入する属性を記述します。 nullの場合、例外をスローします。 これからは、すべての方法を捨てる必要はありません。 あとは、必要なメソッドを必要な属性でマークするだけです。



 public class LazyEmployee : IEmployee { string Name { get; } string LastName { get; } [GreaterThan(VeryCleverGuySalary)] int Salary { get; set; } [Only(true)] bool NeedsPersonalSecretary { get; set; } [TypeOf(typeof(IRoomWithSaunaAndPersonalPlayStation))] IRoom Room { get; set; } }
      
      







さて、何度も議論されてきた別の問題について話しましょう。しかし、人々は頑固にロガー、トレーサー、その他の自転車製造の楽しみをやっています(ところで、最近「 自動機 」で自転車を作ったことを知っていますか?)。 たとえば、log4netのような良いことをしました。 ただし、これは必ずしも必要な速度で動作するとは限りません。 私たちのプログラムでは、ロギングの実装は可能な限り迅速に動作し、ロギング自体は自己記述コードの速度で動作します。

 public class PerisherEmployee : IEmployee { [NotNull, StartingWithUpperCase] string Name { get; } [NotNull, StartingWithUpperCase] string Lastname { get; } [Tracing, WriteToDatabaseEachTransaction, CheckHistory] int Salary{ get; set; } [AbuseEachWhoTriesToBuySomething, Trace] int FreeMoney { get; set; } }
      
      







この例では、悲惨な人は自分のお金を使ってすべての行動をデータベースに記録し、操作の履歴を確認し、このお金で何かを購入しようとする人はすべて呪われます。 もちろん、この例は架空のものであり、これらの属性(トレースを除く)が必要になることはほとんどありませんが、発生している可能性を明確に示しています。 ここで、データベースを操作し、範囲の値をトレースして確認する必要があります。 あなたは異議を唱えることができます:ここで、属性の奇妙な雲を作り、スペースを混乱させます! ただし、ペアにしようとします。このようなコードは簡単に見えますか?



 public class PerisherEmployee : IEmployee { string _name, _lastname; int _salary, _freemoney; string Name { set { if(value == null) throw new ArgumentNullException("value"); if(!IsStartsFromUpperCase(value)) throw new ArgumentOutOfRangeException("value"); _name = value; } get { return _name; } } string Lastname { set { if(value == null) throw new ArgumentNullException("value"); if(!IsStartsFromUpperCase(value)) throw new ArgumentOutOfRangeException("value"); _surname = value; } get { return _surname; } } [Tracing, WriteToDatabaseEachTransaction, CheckHistory] int Salary { get { return _salary; } set { Console.WriteLine("value: {0}", value); DatabaseEngine.SaveSalary(value); _salary = value; if(!CheckHistory(this)) throw new WrongOperationException(); } } int FreeMoney { get { return _freememory; } set { if(value < _freememory) throw new OutOfRangeException(); Console.WriteLine("value: {0}", value); } } }
      
      





まったくありませんが、それはあなた次第です:)これがうまく機能する場合、多くのオプションもあります! 5点のうち10点で機能する場合。たとえば、Webサイトが既に機能しているときにASP.NETで開発者のコ​​ンソールにメッセージをトレースする場合... Webページの操作中はいつでもスタックトレースの履歴を確認できます。 どうやって? スタックをどこかに保持し、アセンブリ上に置くアスペクトを記述するだけです。 または、一見したところ、奇妙なことです。 それらについては、後ほどお話します...当面は、このプログラムで実装されている機能について既にお話しした記事へのリンクをいくつかご紹介します。






All Articles