私はWinForms(または実際には問題なく動作する.NET)についてはわかりませんが、私が知っていること(または覚えていると思います)に基づいて提案します。
3つの変数Age、Amount、Hair Colorに基づいてリスクを計算する簡単なフォームクラスがあるとします。 [レート]ボタンをクリックすると、適切な文字列、「高」、「中」、および「低」でラベルが更新されます。
public void btnRate_click() {
var RiskScore = 0;
if(txtAge.Value < 25)
RiskScore += 2;
else if(txtAge.Value < 40)
RiskScore += 1;
if(txtAmount.Value < 2.00)
RiskScore += 10;
else if(txtAmount.Value < 10.00)
RiskScore += 3;
else if(txtAmount.Value < 50.00)
RiskScore += 5;
if(txtHairColor.Value == "Red")
RiskScore += 75;
if(RiskScore < 2)
lblResult.Value = "Low";
else if(RiskScore < 8)
lblResult.Value = "Medium";
else
lblResult.Value = "High";
}
このコードでは、いくつかのテストをレイアウトする前に、いくつかの簡単な「プリファクタリング」から始めます。私はReSharperのようなIDEが本当に安全であり、望ましくない副作用をほとんど残さないため、自動的に行うことができる標準的なリファクタリングを使用する傾向があります。
最初に行うことは、コード内の重複を削除することです。具体的には、extracting some local variables。
public void btnRate_click() {
var RiskScore = 0;
var Age = txtAge.Value;
if(Age < 25)
RiskScore += 2;
else if(Age < 40)
RiskScore += 1;
var Amount = txtAmount.Value;
if(Amount < 2.00)
RiskScore += 10;
else if(Amount < 10.00)
RiskScore += 3;
else if(Amount < 50.00)
RiskScore += 5;
var HairColor = txtHairColor.Value;
if(HairColor == "Red")
RiskScore += 75;
var Result = ""
if(RiskScore < 2)
Result = "Low";
else if(RiskScore < 8)
Result = "Medium";
else
Result = "High";
lblResult.Value = Result;
}
このリファクタリングは迅速だったと今は周りの変数宣言を移動し、少しのコードを整理する瞬間を取るよCtrl+Alt+V
を使用して自動的に行うことができます。
public void btnRate_click() {
var Age = txtAge.Value;
var Amount = txtAmount.Value;
var HairColor = txtHairColor.Value;
var RiskScore = 0;
var Result = ""
if(Age < 25)
RiskScore += 2;
else if(Age < 40)
RiskScore += 1;
if(Amount < 2.00)
RiskScore += 10;
else if(Amount < 10.00)
RiskScore += 3;
else if(Amount < 50.00)
RiskScore += 5;
if(HairColor == "Red")
RiskScore += 75;
if(RiskScore < 2)
Result = "Low";
else if(RiskScore < 8)
Result = "Medium";
else
Result = "High";
lblResult.Value = Result;
}
これまで達成してきたことは、ビジネスルール(リスク計算)をUIコンポーネント(フォームコントロール)から分離することでした。次のステップは、それらのビジネスルールをUIクラスから外して他の場所に取り出すことです。もう1つのリファクタリングが順調です。このコードを見ると、このメソッドでは4つの変数が操作されています。コードが同じ変数で動作するとき、それはしばしばそこにクラスが潜んでいるというサインです。ここでExtract Method Objectリファクタリングを使用しましょう...(このキーストロークは覚えていませんが、そこにあることは間違いありません)
このブロックの内容を見ると、この新しいクラスはRiskCalculator
と呼ばれます。リファクタリング後のコードは次のようになります。
public void btnRate_click() {
var Age = txtAge.Value;
var Amount = txtAmount.Value;
var HairColor = txtHairColor.Value;
var Result = new RiskCalculator(Age, Amount, HairColor).Invoke();
lblResult.Value = Result;
}
// In RiskCalculator.cs
public class RiskCalculator {
private int Age;
private double Amount;
private string HairColor;
public RiskCalculator(int Age, double Amount, string HairColor) {
this.Age = Age;
this.Amount = Amount;
this.HairColor = HairColor;
}
public string Invoke() {
var RiskScore = 0;
var Result = ""
if(Age < 25)
RiskScore += 2;
else if(Age < 40)
RiskScore += 1;
if(Amount < 2.00)
RiskScore += 10;
else if(Amount < 10.00)
RiskScore += 3;
else if(Amount < 50.00)
RiskScore += 5;
if(HairColor == "Red")
RiskScore += 75;
if(RiskScore < 2)
Result = "Low";
else if(RiskScore < 8)
Result = "Medium";
else
Result = "High";
return Result;
}
}
ここではどこかになっています。 RiskCalculator
にはビジネスロジックのみが含まれており、現在はテスト可能です。次のステップは、電卓の周りにいくつかの単体テストを書いて、すべてのビジネスルールを検証することです。これにより、実際の計算コードをリファクタリングしてクリーンアップすることができます。
テストを書くことによって、RiskCalculator
は本当にこのクラスの良い名前ではないことがわかります。つまり、コンストラクタに渡されているデータが実際にあなたのローンを表していると思います。あなたが現在のRiskCalculator
のテストの良い基盤を持っていることを考えると、いくつかのRenameリファクタリングを実行することができます。 Rename Methodから始めます。
Invoke
の方法は実際には名前として有益ではないので、名前を変更します。それは何ですか?私はそれが実際にリスク計算を行っていると言いたいので、それをcalculateRisk
としましょう。その後、リスクをどのように計算しているのかを自問しなければなりません。答えはローンなので、それが2番目のリファクタリングになります。名前変更クラスのリファクタリングを使用し、RiskCalculator
の名前をLoan
に変更します。これがシステムの最初のドメインオブジェクトになります。
// RiskCalculator.cs has now become Loan.cs
public class Loan {
// ...
public string CalculateRisk() {
// ...
}
}
これらの各リファクタリングの後、テストを実行して、引き続きテストを実行する必要があります。 CalculateRisk
メソッドでそのひどいビジネスロジックをクリーンアップすることで、引き続き続行できます。私はおそらくいくつかInline Temporary Variableをすることによって、これをクリーンアップするでしょう
public void btnRate_click() {
var Age = txtAge.Value;
var Amount = txtAmount.Value;
var HairColor = txtHairColor.Value;
var Result = new Loan(Age, Amount, HairColor).CalculateRisk();
lblResult.Value = Result;
}
と変数のリファクタリングを抽出します。今、私たちのドメインオブジェクトは、我々は次のようになりべき、そのイベントハンドラに戻って私たちの目を向けることができ、クリーンであることを
:
public void btnRate_click() {
var MicroLoan = new Loan(txtAge.Value, txtAmount.Value, txtHairColor.Value);
lblResult.Value = MicroLoan.CalculateRisk();
}
今はかなりきれいだし、台無しにそこに多くのコードが実際にそこではありませんので、この時点でのテストの必要性の多くはありません。
希望に役立ちます。私はリポジトリに関するあなたの質問に本当に答えなかったが、これはあなたに始めるための道を与えることを望んでいる。あなたのロジックをどこに置くべきかについては、Single Responsibility Principleを覚えておいてください。それはあなたのリポジトリに何が入っているのか、そうでないのかを決めるのに役立ちます。また、Loan
クラスを他の小さく集中したクラスに分割する可能性もあります。
Good Luck! ブランドン
あなたは、この既存の質問を見て持つことができ
私はすべてのビジネスロジックをクラスライブラリに入れたいと考えていますが、それを行うためのパターンや構造に関する提案を探しています。スケールの最悪の終わりには、すべての静的メソッドを持つ1つの大きなBusLogクラスを持つパブリックインターフェイスを持つことができました。理想主義的な終わりに、私は各エンティティ、コマンドなどのためにいくつかのクラスを持っています。 – ProfK