• Как реализовывается функцию(main), которая будет производить проверку?

    @Mercury13
    Программист на «си с крестами» и не только
    Мы пишем модульный тест собственными силами, без фреймворка. Это значит, что нам надо каким-то образом сымитировать работу фреймворка, но собственными силами и минимумом строчек.

    Для удобства нам потребуется одна функция — и немного препроцессорной магии.
    #include <iostream>
    #include <cstring>
    
    void doAssert(bool condition, int line)
    {
        if (condition) {
            std::cout << "Line " << line << " ok" << std::endl;
        } else {
            std::cout << "Line " << line << " FAILED" << std::endl;
        }
    }
    
    #define ASSERT(x) doAssert(x, __LINE__)
    #define ASSERT_STREQ(x, y) doAssert((std::strcmp(x, y) == 0), __LINE__)


    А теперь что-нибудь протестируем. Например, создание строки. Для простоты я проверю не вашу строку, а std::string.
    void testStringCreation()
    {
        std::string s;
        ASSERT(s.length() == 0);
        ASSERT(s.empty());
        ASSERT_STREQ("", s.c_str());
    }

    Проверим ещё операцию +=.
    void testPlusEq()
    {
        std::string s1 = "Alpha";
        std::string s2 = "Bravo";
        s1 += s2;
        ASSERT_STREQ("AlphaBravo", s1.c_str());
    }
    
    int main()
    {
        testStringCreation();
        testPlusEq();
        return 0;
    }

    Нужны ещё тесты — создавай новую функцию и вызывай её из main.
    Если какой-то тест не проходит — уничтожаем из main все вызовы, кроме несработавшего, и начинаем отладку.

    А теперь немного о том, какие должны быть модульные тесты.
    1. Изолированные. Если уничтожить часть тестов или запустить их в другом порядке, ничего не должно меняться — при условии, конечно, что никто не обращается к чужой памяти.
    2. Каждый модульный тест проверяет одну концепцию, которая указана в его названии. Например: строка создаётся, работает операция +=, и т.д. Будет очень много дублей кода, просто смиритесь с этим.
    3. Но нет ничего зазорного, что какой-то тест полагается на концепции, испытанные в других тестах. Если мы испытываем +=, то полагаем, что конструктор копирования работает, и не будем испытывать это.
    4. Модульным тестам иногда приходится иметь дело с внутренним поведением объекта. В таком случае объект должен выдавать наружу некоторую информацию — например, соответствующие функции обычно private, но по какой-то препроцессорной команде они становятся public.
    5. Модульные тесты обычно имеют дело с простейшим поведением объекта. Это не нагрузочные тесты, надо с этим просто смириться.
    6. Принцип работы теста таков. Создать исходные объекты, убедиться в том, что их ВНУТРЕННЕЕ (неспецифицированное, зависящее от реализации) состояние верное, провести некое действие, убедиться, что действие проведено правильно. Например, пусть строка выделяет память с запасом, и надо проверить, как она расширяется — тогда при присваивании "Alpha" мы убеждаемся, что выделено менее 10 символов, затем проводим s1 += "Bravo", затем убеждаемся, что выделено, например, 16 символов.
    7. Но заранее не нужно проверять, верно ли ВНЕШНЕЕ (заспецифицированное) состояние. Если мы пишем s1 = "Alpha", значит, строка равна "Alpha", и точка. Все случаи, возможные в операции string = char*, разумеется, покрыты другими тестами.
    8. Если вдруг в «боевом» коде обнаружится ошибка, надо сделать юнит-тест, её повторяющий, затем исправить ошибку и констатировать, что тест проходит и остальные тесты не «упали».
    9. То же самое, если ошибка случилась, когда проверяли другую концепцию. Проверяем +=, а глюк в конструкторе копирования — заводи новый тест, покрывающий эту ошибку.
    10. В проверках на равенство принят порядок ASSERT_EQ(что_должно_быть, что_реально_есть).
    Ответ написан
    Комментировать
  • Как подключить PYLAB (PYHTON)?

    sim3x
    @sim3x
    pip install numpy scipy matplotlib

    stackoverflow.com/questions/10965336/python-error-...
    Ответ написан
    Комментировать