ユニットテストの書き方は?


135

Javaクラスがあります。どうすればそれを単体テストでき ますか?


私の場合、私はクラスにバイナリ合計を行います。2つのbyte[]配列を受け取り、それらを合計して、新しいバイナリ配列を返します。


7
jUnitなどのツールを利用して、Javaクラスのテストケース(テストメソッド)を作成できます。次に、ビルドプロセス(ant / maven)の一部としてjUnitテストを呼び出します。jUnitを使用することは決して難しくありません。バグを早期かつ頻繁に検出できるように、考えられる限り多くのテストシナリオを考え出すのが難しい部分です。
CoolBeans 2012年

回答:


132
  1. 正しい入力を使用して、通常の場合の期待される出力と望ましい出力を定義します。

  2. 次に、クラスを宣言してテストを実装し、任意の名前を付け(通常はTestAddingModuleのようなもの)、それにtestAddメソッドを追加します(つまり、以下のようにします)。

    • メソッドを記述し、その上に@Testアノテーションを追加します。
    • メソッドで、バイナリ合計とを実行しますassertEquals(expectedVal,calculatedVal)
    • メソッドを実行してテストします(Eclipseで右クリックし、「実行」→「JUnitテスト」を選択します)。

      //for normal addition 
      @Test
      public void testAdd1Plus1() 
      {
          int x  = 1 ; int y = 1;
          assertEquals(2, myClass.add(x,y));
      }
  3. 必要に応じて他のケースを追加します。

    • 整数のオーバーフローがある場合、バイナリの合計が予期しない例外をスローしないことをテストします。
    • メソッドがNull入力を適切に処理することをテストします(以下の例)。

      //if you are using 0 as default for null, make sure your class works in that case.
      @Test
      public void testAdd1Plus1() 
      {
          int y = 1;
          assertEquals(0, myClass.add(null,y));
      }

1. @Test表記は必要ですか?2. assertNotNullでnull入力をテストしないのはなぜですか?3.単体テストの結果はどこに取り込まれますか?結果はユーザーにどのように示されますか?
user137717 2014年

10
はい、@Test表記が必要です。これは、このメソッドがユニットテストを表し、実行する必要があることをユニットテストランナーに通知するために行われます。アノテーションが付けられ@Testていないメソッドは、テストランナーによって実行されません。
Ali Shah Ahmed

2番目のテストのために- あなたに与えるnullためyだけに追加すべきではありませんyか?
Adjit

ありがとう!staticテストメソッドの修飾子に追加する必要がない理由を知りたいのですが。
梁張

103

この投稿はIntelliJEclipseの両方に提供します。

日食:

プロジェクトの単体テストを作成するには、次の手順に従ってください(このテストを作成するためにEclipseを使用しています)。

1- [新規]-> [Javaプロジェクト]をクリックします。

プロジェクトを作成する

2-プロジェクト名を書き留めて、完了をクリックします。

プロジェクトを作成する

3-プロジェクトを右クリックします。次に、[新規]-> [クラス]をクリックします。

クラスを作成する

4-クラス名を書き留めて、完了をクリックします。

クラスを作成する

次に、次のようにクラスを完成させます。

public class Math {
    int a, b;
    Math(int a, int b) {
        this.a = a;
        this.b = b;
    }
    public int add() {
        return a + b;
    }
}

5- [ファイル]-> [新規]-> [JUnitテストケース]をクリックします。

JUniteテストの作成

6- setUp()を確認して、完了をクリックします。SetUp()は、テストを初期化する場所です。

SetUp()を確認する

7- [OK]をクリックします。

JUnitを追加

8-ここでは、単純に7と10を追加します。したがって、答えは17になると予想します。次のようにテストクラスを完成させます。

import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
public class MathTest {
    Math math;
    @Before
    public void setUp() throws Exception {
        math = new Math(7, 10);
    }
    @Test
    public void testAdd() {
        Assert.assertEquals(17, math.add());
    }
}

9-パッケージエクスプローラーでテストクラスをクリックして書き込み、[別のユーザーとして実行]-> [JUnitテスト]をクリックします。

JUnitテストを実行する

10-これはテストの結果です。

テストの結果

IntelliJ: スクリーンショットにはIntelliJ IDEAコミュニティ2020.1を使用したことに注意してください。また、これらの手順の前にjreを設定する必要があります。JDK 11.0.4を使用しています。

1-プロジェクトのメインフォルダーを右クリックし、[新規]-> [ディレクトリ]をクリックします。これを「テスト」と呼ぶ必要があります。 ここに画像の説明を入力してください 2-テストフォルダーを右クリックし、適切なパッケージを作成します。元のクラスと同じパッケージ名を作成することをお勧めします。次に、テストディレクトリを右クリックして、ディレクトリにマークを付けます。 ここに画像の説明を入力してください 3-テストディレクトリの適切なパッケージで、Javaクラスを作成する必要があります(Test.javaの使用をお勧めします)。 ここに画像の説明を入力してください 4-作成されたクラスで、「@ Test」と入力します。次に、IntelliJが提供するオプションの中で、「JUnitxをクラスパスに追加」を選択します。 5-テストクラスにテストメソッドを記述します。メソッドのシグネチャは次のようなものです。ここに画像の説明を入力してください ここに画像の説明を入力してください

@Test
public void test<name of original method>(){
...
}

次のようにアサーションを実行できます。

Assertions.assertTrue(f.flipEquiv(node1_1, node2_1));

これらは私が追加したインポートです:

import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;

ここに画像の説明を入力してください

これは私が書いたテストです: ここに画像の説明を入力してください

以下のようにメソッドを確認できます:

Assertions.assertEquals(<Expected>,<actual>);
Assertions.assertTrue(<actual>);
...

単体テストを実行するには、テストを右クリックして[実行]をクリックします。 ここに画像の説明を入力してください

テストに合格すると、結果は次のようになります。 ここに画像の説明を入力してください

お役に立てば幸いです。GitHub https://github.com/m-vahidalizadeh/problem_solving_projectでプロジェクトの構造を確認できます


12
あなたの答えが大好きです、それは最高の「ハウツー」です!
アリサ2017

4
私の回答が役に立ったことを嬉しく思います。コメントありがとうございます。
Mohammad

1
これはチュートリアルがどのようになるかです。クリーンで簡潔な完全な例。とても良い。
Jack of Blades、2018

1
どうもありがとうございました。お役に立てて嬉しいです。
モハマド

18

これは非常に一般的な質問であり、答えられる方法はたくさんあります。

JUnitを使用してテストを作成する場合は、テストケースクラスを作成し、テスト中のクラス/モジュールの特定の機能をテストする個別のテストメソッドを作成する必要があります(単一のテストケースクラスは通常、テスト中)、これらのメソッド内でさまざまな操作を実行し、結果を正しいものと比較します。可能な限り多くのコーナーケースを試行してカバーすることが特に重要です。

特定の例では、たとえば次のことをテストできます。

  1. 2つの正の数の間の単純な加算。それらを追加し、結果が期待どおりであることを確認します。
  2. 正数と負数の加算(最初の引数の符号付きの結果を返します)。
  3. 正数と負数の加算(2番目の引数の符号付きの結果を返します)。
  4. 2つの負の数の間の加算。
  5. オーバーフローを引き起こす追加。

結果を確認するには、org.junit.AssertクラスのさまざまなassertXXXメソッドを使用できます(便宜上、「静的static org.junit.Assert。*」を実行できます)。これらのメソッドは、特定の条件をテストし、それが検証されない場合(オプションで、特定のメッセージを使用して)テストに失敗します。

あなたのケースのテストケースクラスの例(メソッドのコンテンツが定義されていない):

import static org.junit.Assert.*;

public class AdditionTests {
    @Test
    public void testSimpleAddition() { ... }


    @Test
    public void testPositiveNegativeAddition() { ... }


    @Test
    public void testNegativePositiveAddition() { ... }


    @Test
    public void testNegativeAddition() { ... }


    @Test
    public void testOverflow() { ... }
}

単体テストの作成に慣れておらず、代わりにアドホックテストを作成してコードをテストする場合は、「視覚的に」検証します(たとえば、キーボードを使用して入力された引数を受け入れ、結果を出力する簡単なメインメソッドを作成します) -そして、値を入力し続け、結果が正しい場合は自分で検証します)。次に、上記の形式でそのようなテストを記述し、手動で行う代わりに、正しいassertXXXメソッドで結果を検証することから始めます。この方法では、手動テストを行う必要があった場合よりもはるかに簡単にテストを再実行できます。



6

他の答えは、JUnitを使用してテストクラスを設定する方法を示しています。JUnitは唯一のJavaテストフレームワークではありません。ただし、フレームワークを使用する技術的な詳細に集中すると、アクションの指針となる最も重要な概念が損なわれるため、それらについて説明します。

  • (あらゆる種類のあらゆるものの)テストでは、何か(テスト中のシステム、SUT)の実際の動作を、予想される動作と比較します。

  • 自動テストは、コンピュータプログラムを使用して実行できます。この比較は柔軟性がなく、インテリジェントではないコンピュータプログラムによって行われるため、期待される動作は正確かつ明確に認識されている必要があります。

  • プログラムまたはプログラムの一部(クラスまたはメソッド)に期待されるのは、その仕様です。したがって、テストソフトウェアでは、SUTの仕様が必要です。これは、明示的な説明の場合もあれば、予想されるものの頭にある暗黙の仕様の場合もあります。

  • したがって、自動化された単体テストでは、テストするクラスまたはメソッドを正確かつ明確に指定する必要があります。

  • しかし、そのコードを書き始めるときに、その仕様が必要でした。したがって、SUTの1行を書く前に、テストの一部が実際に開始されます。テスト駆動開発(TDD)のテスト手法は、そのアイデアを極限まで引き出し、テストするコードを記述する前に単体テストコードを作成する必要があります。

  • ユニットテストフレームワークは、アサーションを使用してSUTをテストします。アサーションは、SUTが正しく動作している場合に存在する必要がある論理式(boolean結果タイプを伴う式、述語)ですtrue。したがって、仕様はアサーションとして表現(または再表現)する必要があります。

  • 仕様をアサーションとして表現するための便利な手法は、コントラクトによるプログラミングです。これらの仕様は事後条件に関するものです。事後条件とは、メソッドまたはコンストラクターから戻った後の、SUTの公に見える状態についての表明です。一部のメソッドには、不変条件である事後条件があります。これは、メソッドの実行前後に当てはまる述語です。クラスは、クラスのすべてのコンストラクタとメソッドの事後条件である、不変条件を持っていると言うことができるので、必要があり、常に真です。事後条件(および不変条件)は、宣伝の表示状態の観点でのみ表現されます:publicおよびprotectedフィールド、によって返される値publicprotectedメソッド(ゲッターなど)、メソッドに(参照によって)渡されたオブジェクトのパブリックに表示される状態。


多くの初心者は、いくつかのコードをテストする方法を尋ねる質問をここに投稿し、コードを提示しますが、そのコードの仕様を述べません。この議論が示すように、可能性のある回答者はせいぜい仕様を推測する必要があり、誤って行う可能性があるため、そのような質問にだれもが適切な回答をすることは不可能です。アスカー質問のは明らか仕様の重要性を理解していないので、私はここで説明してきた基本を理解する必要があり、初心者である前に、いくつかのテストコードを書くしようとしています。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.