前回の記事でアジャイルサムライの感想を書きました。今回は少しでも読んだ内容を活かすため、テスト駆動開発ができるよう、テスト環境を構築してみることにします。
私はC++を主に使っているので、C++のテストフレームワークを色々探してみました。以下が見つけたC++用テストフレームワークの一例です。
色々探した中でよく名前が挙がっていたのが、CppUnit, googletest, Boost.Testあたりでした。今回はCppUnitを利用してみます。
ダウンロードとインストール
http://sourceforge.net/projects/cppunit/から、cppunit-1.12.1.tar.gzをダウンロードして、解凍&インストール。
$ tar zxvf cppunit-1.12.1.tar.gz
$ cd cppunit-1.12.1
$ ./configure
$ make
$ sudo make install
テストプログラムを書いてみる
テストプログラムを書くにあたって、テスト対象のプログラムが必要です。
今回は適当に、FizzBuzz問題のプログラムを書いてみました。
入力した数字によって対応した文字列を返すPrint関数を持つ、FizzBuzzクラスを作りました。
//FizzBuzz.h
#include <string>
class FizzBuzz {
public:
std::string Print(int n);
};
//FizzBuzz.cpp
#include <sstream>
#include "FizzBuzz.h"
using namespace std;
string FizzBuzz::Print(int n) {
ostringstream sout;
if(n % 3 == 0) sout << "Fizz";
if(n % 5 == 0) sout << "Buzz";
if(n % 3 != 0 && n % 5 != 0) sout << n;
return sout.str();
}
まず、テストプログラムのMain関数を用意します。
Main関数はテンプレなので、基本的には改変する必要がありません。
//TestMain.cpp
#include <cppunit/TestResult.h>
#include <cppunit/TestResultCollector.h>
#include <cppunit/BriefTestProgressListener.h>
#include <cppunit/TestRunner.h>
#include <cppunit/extensions/TestFactoryRegistry.h>
#include <cppunit/CompilerOutputter.h>
using namespace CPPUNIT_NS;
int main(int argc, char **argv) {
/* テストコントローラの生成 */
TestResult controller;
TestResultCollector result;
controller.addListener(&result);
BriefTestProgressListener progress;
controller.addListener(&progress);
/* テストを追加して、テストの実行 */
TestRunner runner;
runner.addTest(TestFactoryRegistry::getRegistry().makeTest());
runner.run(controller);
CompilerOutputter outputter(&result, stdCOut());
outputter.write();
return result.wasSuccessful() ? 0 : 1;
}
次に、テストクラスを用意します。
//FizzBuzzTest.cpp
#include "FizzBuzz.h"
#include <cppunit/extensions/HelperMacros.h>
using namespace CPPUNIT_NS;
class FizzBuzzTest : public TestFixture {
CPPUNIT_TEST_SUITE( FizzBuzzTest );
/* ここから、テストケースを設定 */
CPPUNIT_TEST( testFizz );
CPPUNIT_TEST( testBuzz );
CPPUNIT_TEST( testFizzBuzz );
CPPUNIT_TEST( testOther );
/* ここまで */
CPPUNIT_TEST_SUITE_END();
FizzBuzz* fb_;
void testFizz();
void testBuzz();
void testFizzBuzz();
void testOther();
public:
void setUp() {
this->fb_ = new FizzBuzz();
}
void tearDown() {
delete this->fb_;
}
};
/* ここから、テストケースを記述 */
void FizzBuzzTest::testFizz()
{
std::string s = "Fizz";
CPPUNIT_ASSERT_EQUAL(s, fb_->Print(3));
}
void FizzBuzzTest::testBuzz()
{
std::string s = "Buzz";
CPPUNIT_ASSERT_EQUAL(s, fb_->Print(5));
}
void FizzBuzzTest::testFizzBuzz()
{
std::string s = "FizzBuzz";
CPPUNIT_ASSERT_EQUAL(s, fb_->Print(15));
}
void FizzBuzzTest::testOther()
{
std::string s = "2";
CPPUNIT_ASSERT_EQUAL(s, fb_->Print(2));
}
/* ここまで、テストケースの記述 */
CPPUNIT_TEST_SUITE_REGISTRATION(FizzBuzzTest);
テストする関数を定義して、その関数をテストケースとして設定していくだけです。また、setUPとtearDownは、テストケースを実行する前後の処理を定義する関数です。このため、各テストケースは影響しあいません。今回のテストでは、3を引数としたときには"Fizz"を、5を引数にしたときには"Buzz"を、15を引数にしたときには "FizzBuzz"を、2を"2"を出力することを確認する4つのテストケースを作成しました。
$ g++ TestMain.cpp FizzBuzzTest.cpp FizzBuzz.cpp -lcppunit -o FizzBuzzTestできました!
$ ./FizzBuzzTest
FizzBuzzTest::testFizz : OK
FizzBuzzTest::testBuzz : OK
FizzBuzzTest::testFizzBuzz : OK
FizzBuzzTest::testOther : OK
OK (4)
大した内容でもありませんが、今回のソースコードはこちらにまとめましたので、参考にどうぞ。
さいごに
参考にしたサイトは以下です。
http://www.atmarkit.co.jp/fdotnet/cpptest/cpptest02/cpptest02_01.html
http://d.hatena.ne.jp/echizen_tm/20120127/1327675864
関連記事
C++のテストフレームワーク googletestを試してみた
0 件のコメント:
コメントを投稿