2016-11-18 12 views
2

C#Newbie here。Max()関数のテストケースデザイン

私はそのテストケースがあるべき理解:

  • シンプルで透明
  • は、最小限の繰り返し
  • を持って、私はまた、境界値分析の基本を理解して、100%のコードカバレッジ

を確認してください等価パーティショニングを実行しますが、以下の機能を使用すると、基本的なテストケースはどのようになりますか?

static public int Max(int a, int b, int c) 
    { // Lines of code: 8, Maintainability Index: 70, Cyclomatic Complexity: 4, Class Coupling: 0 
     if (a > b) 
      if (a > c) 
       return a; 
      else 
       return c; 
     else 
      if (b > c) 
       return b; 
      else 
       return c; 
    } 

これは私がこれまで持っているものです。..

using Microsoft.VisualStudio.TestTools.UnitTesting; 
    using ConsoleApplication10; 
    using System; 
    using System.Collections.Generic; 
    using System.Linq; 
    using System.Text; 
    using System.Threading.Tasks; 

    namespace ConsoleApplication10.Tests 
    { 
     [TestClass()] 
     public class ProgramTests 
     { 
      [TestMethod()] 
      public void MaxTestNulls(int a, int b, int c) 
      { 
       Assert.IsNotNull(a, "The first parameter must be present."); 
       Assert.IsNotNull(b, "The second parameter must be present."); 
       Assert.IsNotNull(c, "The third parameter must be present."); 
      } 
      [TestMethod()] 
      public void MaxTestTypes(int a, int b, int c) 
      { 
       Assert.IsInstanceOfType(a, typeof(int)); 
       Assert.IsInstanceOfType(b, typeof(int)); 
       Assert.IsInstanceOfType(c, typeof(int)); 
      } 
      [TestMethod()] 
      public void MaxTestBasics(int a, int b, int c) 
      { 
       if (a > int.MaxValue || b > int.MaxValue || c > int.MaxValue) 
       { 
        Assert.Fail(); 
       } 

       if (a < int.MinValue || b < int.MinValue || c < int.MinValue) 
       { 
        Assert.Fail(); 
       } 
      } 
     } 
    } 

は、ここで私は完全オフベースのでしょうか?私の先生は膨らんでいないし、私に何かヒントを与えることはありません。

答えて

2

実行可能なテスト戦略の1つを分岐カバレッジと呼びます。ここでは、テスト対象のシステム内の各実行ブランチをカバーする単体テストを作成しようとします。下部のreturn areturn creturn bと再びreturn c:あなたのケースでは

は、明確な実行分岐がreturn命令です。

あなたはこれらのユースケース(それぞれ、a、b及びcの値)との関数全体をカバーすることができます

4, 2, 3 
4, 2, 5 
4, 2, 4 <-- boundary condition 
2, 4, 3 
2, 2, 3 <-- boundary condition 
2, 4, 5 
2, 4, 4 <-- boundary condition 

すべての分岐がカバーされることを保証している4つのテストケースが正確にあります。追加の3つのケースは、特定の支店でまだ終わる境界条件をカバーするためです。

以下は、xUnitでのこれらのテストケースの実装です。それはInlineData属性を使用して一つの試験方法のための複数のテストケースをサポートしているので、私はxUnitフレームを選択した:

[Theory] 
[InlineData(4, 2, 3, 4)] 
[InlineData(4, 2, 5, 5)] 
[InlineData(4, 2, 4, 4)] 
[InlineData(2, 4, 3, 4)] 
[InlineData(2, 2, 3, 3)] 
[InlineData(2, 4, 5, 5)] 
[InlineData(2, 4, 4, 4)] 
public void Max_ReturnsExpectedValue(int a, int b, int c, int expectedMax) 
{ 
    int actualMax = Program.Max(a, b, c); 
    Assert.Equal(expectedMax, actualMax); 
} 

念のために、7つすべてのテストケースは、上記の実装のために渡しています。

関連するノートでは、この種のテストをホワイトボックステストと呼びます。あなたは具体的な実装にアクセスして、その実装のテストを書いています。ブラックボックステストを実装したい場合、テストケースは関数からの期待に基づいているだけです。例えば、これらは、ブラックボックステストのための合法的なテストケースが考えられます。

1, 1, 1 -> 1 
1, 1, 2 -> 2 
1, 2, 1 -> 2 
1, 2, 2 -> 2 
1, 2, 3 -> 3 
1, 3, 1 -> 3 
1, 3, 2 -> 3 
1, 3, 3 -> 3 
2, 1, 1 -> 2 
... 

ここでの問題は、我々は境界条件が関連しているので、我々はカバーにそれらのかなり多くを追加する必要がありますかわからないということですすべてのオプション。あなたが同じ方向に進むと、テストの総数は3^3 = 27になります。

+0

これは非常に役に立ちます。ありがとうございます。もう1つの質問ですが、これを私のユニットテストの中でどのように実装するのでしょうか? TestMethods()内でMax()を呼び出そうとすると、エラーが発生します。 – dotKn0ck

+0

私は実装に混乱していると思います。 – dotKn0ck

+0

@ dotKn0ck上記のテスト方法の実装を参照してください。 –

0

最初の明白な追加は、3つの入力のいずれかが等しいかどうかテストする必要があるということです。

第2に、依存関係をテストする必要があります。つまり、入力の値が評価ごとに変化する関数の出力になる可能性があるため、テストクラスの入力のインスタンスを1つ取得してください1回)と私はC#のについて多くを知っているが、それはのように呼び出された場合、私は

public static TestFunction (int A, int B, int C) 
{ 
// Your test methods 
} 

あなたの一般的な例を示しましょういけない再評価しない入力

このローカルインスタンス上でテストを継続し、この

boolean Result = TestFunction((int)Math.sin(System.currentTimeMillis()),(int)Math.sin(System.currentTimeMillis()),(int)Math.sin(System.currentTimeMillis())); 

あなたの関数内のすべての時間をあなたのアクセスA、BまたはCの価値が、私はX = Aのような余分なテストを追加し再評価され、可能前回のテスト

の結果を失うことになり、Y = A、XY =再評価時にAが変化しないようにするために、時間依存性を考慮して時間遅延を追加し、プログラムが実行する速度が速すぎます(小さくて単純なコードを途切れることなく実行するためにナノ秒の解像度が必要)