需求

qt 如何单元测试高级特性

解决

创建项目

  • new project -> other project -> subdirs project: 用于创建包含多个测试项目的父项目
  • new project -> other project -> qt unit test: 单个的测试项目,提供更多的选项

数据驱动

添加数据

在测试函数的后面添加 _data 后缀的同名私有槽函数,然后通过 QTest::addColumn 添加列, QTest::newRow 添加行.

void TestCalculator::testDiff_data()
{
    QTest::addColumn<int>("a");
    QTest::addColumn<int>("b");
    QTest::addColumn<int>("result");
    QTest::newRow("all 0") << 0 << 0 << 0;
    QTest::newRow("same number") << 10 << 10 << 0;
    // ... more data ...
}
INDEX NAME a b result
0 “all 0” 0 0 0
1 “same number” 10 10 0

使用数据

使用 QFETCH 来提取数据

void TestCalculator::testDiff()
{
    // retrieve data
    QFETCH(int, a);
    QFETCH(int, b);
    QFETCH(int, result);
    // set value
    mCalc.SetA(a);
    mCalc.SetB(b);
    // test
    QCOMPARE(mCalc.Diff(), result);
}

会自动的按照数据的行,进行多次测试。

额外的宏

QFAIL

让测试失败,并结束

void TestIntBitset::initTestCase()
{
    if(sizeof(int) != 4)
      QFAIL("Int size is not 4 on this platform.");
}

QEXPECT_FAIL

在预估某个特定的 QVERIFY, QCOMPARE 单次测试会失败,仍然想继续测试,需要在测试语句前增加这个宏。

void TestIntBitset::testSetOff()
{
  mBS.setAllOn();
  unsigned int bitsOff = 0;
  mBS.setBitOff(BITS_IN_BYTE * bitsOff++);
  mBS.setBitOff(BITS_IN_BYTE * bitsOff++);
  QEXPECT_FAIL("", "isAnyOff not implemented yet", Continue);
  QVERIFY(mBS.isAnyOff());
  // ... more test code ...
}

QSKIP

跳过部分测试

void TestIntBitset::testOperators()
{
    QSKIP("Operators have not been implemented yet...");
}

QWARN

打印警告信息

void TestIntBitset::testSetOff()
{
  mBS.setAllOn();
  unsigned int bitsOff = 0;
  mBS.setBitOff(BITS_IN_BYTE * bitsOff++);
  // ... more test code ...
  // this test will trigger a warning
  if((BITS_IN_BYTE * bitsOff) < BITS_IN_INT)
    QVERIFY(!mBS.isBitOff(BITS_IN_BYTE * bitsOff));
  else
    QWARN("trying to verify bit out of set bounds");
  // ... more test code ...
}

参考