Функция add_first (int n) добавляет число в связанный список и возвращает 0 в случае успеха и -1 в противном случае.

Тест хорош, но я хотел бы протестировать более широкий спектр ситуаций, чтобы протестировать больше одной и той же функции с разными параметрами.

Если я изменю test_add_first и добавлю параметр, это даст мне ошибку, потому что MY_RUN_TEST и RUN_TEST будут принимать только «myfunction (void)». Поэтому мне приходится создавать индивидуальные функции для каждого номера.

У меня есть этот код в моем файле test.c, и я использую модульное тестирование - Unity, как сказано в заголовке.

#define MY_RUN_TEST(func) RUN_TEST(func, 0)

ITEM *list = NULL;

void printList(struct ITEM *node) 
{
  if(node == NULL)
  {
    printf("list is empty");
  } 
    while (node != NULL) 
    { 
        printf("%d ", node -> value); 
        node = node->next; 
    } 
} 

void test_add_first_1()
{
  int ret;
  ret = add_first(&list, 1);
  TEST_ASSERT_EQUAL(0, ret);
}

void setUp(void)
{
    // This is run before EACH test
}

void tearDown(void)
{
  // This is run after EACH test
  printList(list);
  printf("\n");
}

int main (int argc, char * argv[])
{
    
    
    UnityBegin();
   
    MY_RUN_TEST(test_add_first_1);
    
    return UnityEnd();
}

Итак, мой вопрос, чтобы быть более конкретным, есть ли способ проверить их как что-то вроде - MY_RUN_TEST (test_add_first (n)); - n целое число?

Если вы обнаружите, что в этом фрагменте кода что-то еще не так, скажите, что я только начинаю с модульного тестирования. :)

Спасибо!

0
Bujigh 17 Окт 2020 в 18:32

1 ответ

Лучший ответ

Вы не сможете передать функцию с другой подписью в RUN_TEST, но, к счастью, это не обязательно.

Что вы можете сделать, это просто создать более общий тестовый пример, который пытается вставить несколько элементов:

void add_some_items_at_head()
{
    size_t i = 0;
    
    for (i = 0; i < 10; i++)
    {
        TEST_ASSERT_EQUAL(0, add_first(&list, i));
    }   
}

Если вы хотите проверить определенные числа, вы можете поместить их в массив констант и пройти через этот массив, проверяя каждое из этих чисел.

Кстати, если вы спросили об общих улучшениях, которые вы можете здесь сделать, я могу предложить несколько вещей:

  • Даже если вы проверили код возврата функции, возможно, она не добавила полученный элемент или сделала это плохо. Поэтому я бы сделал служебную функцию, чтобы просмотреть список и убедиться, что элементы вставлены в правильном порядке. Это может выглядеть примерно так:

     void validate_items_order(int expected_order[], int len)
     {
         size_t i = 0;
         struct ITEM *node = list;
    
         for (i = 0; i < len; i++)
         {
             TEST_ASSERT_NOT_NULL(node);
             TEST_ASSERT_EQUAL(expected_order[i], node->value);
             node = node->next;
         }
     }
    

    Затем вызывайте эту функцию после каждого теста, чтобы убедиться, что все работает нормально.

  • Используйте тестовые группы, чтобы сделать тестовый код более организованным и читаемым. Вы можете просто создать группу тестов для каждой тестируемой функции и включить в нее все тесты для этой конкретной функции:

      static void RunAllTests(void)
      {
          RUN_TEST_GROUP(add_first);
          RUN_TEST_GROUP(add_last);
          RUN_TEST_GROUP(remove_last);
      }
    
      int main(int argc, const char * argv[])
      {
          return UnityMain(argc, argv, RunAllTests);
      }
    
      TEST_GROUP_RUNNER(add_first)
      {
          RUN_TEST_CASE(add_first, add_some_items_at_head);
          RUN_TEST_CASE(add_first, another_test_for_that_function);
      }
    
      TEST_GROUP_RUNNER(add_last)
      {
          ...
      }
    
      TEST_GROUP_RUNNER(remove_last)
      {
          ...
      }
    
2
Tal Avraham 17 Окт 2020 в 19:47