3

そのようなコードを考えると:

class ToBeTested {
public:
  void doForEach() {
    for (vector<Contained>::iterator it = m_contained.begin(); it != m_contained.end(); it++) {
       doOnce(*it);
       doTwice(*it);
       doTwice(*it);
    }
  }
  void doOnce(Contained & c) {
    // do something
  }
  void doTwice(Contained & c) {
    // do something
  }

  // other methods
private:
  vector<Contained> m_contained;
}

ベクトルに 3 つの値を入力すると、関数が適切な順序と数で呼び出されることをテストしたいと思います。たとえば、私のテストは次のようになります。

tobeTested.AddContained(one);
tobeTested.AddContained(two);
tobeTested.AddContained(three);

BEGIN_PROC_TEST()
SHOULD_BE_CALLED(doOnce, 1)
SHOULD_BE_CALLED(doTwice, 2)
SHOULD_BE_CALLED(doOnce, 1)
SHOULD_BE_CALLED(doTwice, 2)
SHOULD_BE_CALLED(doOnce, 1)
SHOULD_BE_CALLED(doTwice, 2)

tobeTested.doForEach()
END_PROC_TEST()

これをどのようにテストすることをお勧めしますか? CppUnit または GoogleTest フレームワークでこれを行う手段はありますか? たぶん、他のユニットテストフレームワークでそのようなテストを実行できるでしょうか?

これらの関数からデバッグ関数を呼び出さないとおそらくこれは不可能であることは理解していますが、少なくとも一部のテスト フレームワークでは自動的に実行できます。トレース ログをスキャンしてその正確性を確認するのは好きではありません。

UPD: I'm trying to check not only the state of an objects, but also the execution order to avoid performance issues on the earliest possible stage (and in general I want to know that my code is executed exactly as I expected).

4

7 に答える 7

2

連携するオブジェクトへの呼び出しが特定の順序で行われることを確認するには、適切なモック フレームワークを使用できる必要があります。

ただし、通常、あるメソッドが同じクラスの他のメソッドを呼び出すことをテストすることはありません...なぜですか?

一般に、クラスをテストするときは、一般に公開されている状態をテストすることだけを考えます。他の何かをテストすると、テストによって後でリファクタリングできなくなります。

もっと助けを提供できますが、あなたの例は一貫しているとは思いません (AddContained メソッドの実装はどこにありますか?)。

于 2008-09-17T01:04:13.493 に答える
1

パフォーマンスに関心がある場合は、パフォーマンスを測定するテストを作成することをお勧めします。

現在時刻を確認し、気になるメソッドを実行してから、再度時刻を確認してください。合計所要時間が特定の値未満であることをアサートします。

メソッドが特定の順序で呼び出されることを確認する際の問題は、コードを変更する必要があり、変更が発生したときにテストを更新する必要がないことです。要件を満たす実装の詳細をテストするのではなく、実際の要件をテストすることに集中する必要があります。

つまり、メソッドが特定の順序で呼び出されることを本当にテストしたい場合は、次のことを行う必要があります。

  1. それらを別のクラスに移動し、それを Collaborator と呼びます
  2. この他のクラスのインスタンスを ToBeTested クラスに追加します
  3. モック フレームワークを使用して、ToBeTested のインスタンス変数を Collborator クラスのモックに設定します。
  4. テスト中のメソッドを呼び出す
  5. モック フレームワークを使用して、モックでメソッドが正しい順序で呼び出されたことをアサートします。

私はネイティブの cpp スピーカーではないので、どのモッキング フレームワークを使用すべきかについてコメントすることはできませんが、他のコメンターがこの点について提案を追加していることを確認しています。

于 2008-09-17T02:05:36.497 に答える
1

mockppをチェックアウトできます。

于 2008-09-17T00:58:37.500 に答える
1

呼び出された関数の数とその順序を把握しようとする代わりに、正しい順序で呼び出した場合にのみ期待される出力を生成できる入力のセットを見つけます。

于 2008-09-17T01:22:56.210 に答える
0

一部のモッキング フレームワークでは、順序付けされた期待値を設定できます。これにより、特定の順序で期待される関数呼び出しを正確に指定できます。たとえば、C#のRhinoMocksではこれが可能です。

私は C++ コーダーではないので、C++ で何が利用できるかはわかりませんが、それはあなたがしようとしていることを可能にするツールの 1 つのタイプです。

于 2008-09-17T00:56:17.023 に答える
0

http://msdn.microsoft.com/en-au/magazine/cc301356.aspx

これは Context Bound Objects に関する良い記事です。非常に高度な内容が含まれていますが、怠け者ではなく、この種のことを本当に理解したい場合は、非常に役立ちます。

最後に、次のようなものを書くことができます: [CallTracingAttribute()] public class TraceMe : ContextBoundObject {...}

于 2008-09-17T01:13:15.127 に答える
0

ACE (または同様の) デバッグ フレームワークを使用して、テストでデバッグ オブジェクトをファイルにストリーミングするように構成できます。次に、ファイルを確認するだけです。

于 2008-09-17T01:23:25.320 に答える