#include #include #include #include "array.hpp" template void test_operation(unsigned int test, std::string description, T&& operation) { std::cout << "Test " << std::setw(2) << std::right << test << ": "; std::cout << std::setw(30) << std::left << std::move(description) << " "; try { operation(); std::cout << "ok" << std::endl; } catch (std::exception& e) { std::cout << "exception: " << e.what() << std::endl; } catch (...) { std::cout << "unknown exception" << std::endl; } } struct FailingObject { class Exception: public std::exception { const char* what() const noexcept override { return "FailingObject exception"; } }; FailingObject() { throw Exception(); } FailingObject(const FailingObject& other) { throw Exception(); } FailingObject(int i) { if (i < 0) throw Exception(); } FailingObject& operator=(const FailingObject& other) { throw Exception(); } }; int main() { unsigned int test = 0; test_operation(++test, "Array()", []() { Array(); }); test_operation(++test, "Array(0)", []() { Array(0); }); test_operation(++test, "Array(1)", []() { Array(1); }); test_operation(++test, "Array(1, FailingObject(1))", []() { Array(1, FailingObject(1)); }); test_operation(++test, "Array(it1, it2) from {1, 2}", []() { int values[] = {1, 2, 3}; Array(values, values + sizeof(values)/sizeof(values[0])); }); test_operation(++test, "Array(it1, it2) from {1, -2}", []() { int values[] = {1, -2}; Array(values, values + sizeof(values)/sizeof(values[0])); }); test_operation(++test, "Array{1, 2}", []() { Array{1, 2}; }); test_operation(++test, "Array{1, -2}", []() { Array{1, -2}; }); test_operation(++test, "Array copy constructor", []() { int values[] = {1, 2}; Array array(values, values + sizeof(values)/sizeof(values[0])); Array array2(array); }); test_operation(++test, "Array move constructor", []() { int values[] = {1, 2}; Array array(values, values + sizeof(values)/sizeof(values[0])); Array(std::move(array)); }); test_operation(++test, "Array swap", []() { int values[] = {1, 2}; Array array1(values, values + sizeof(values)/sizeof(values[0])); Array array2(values, values + sizeof(values)/sizeof(values[0])); using std::swap; swap(array1, array2); }); test_operation(++test, "Array assignment", []() { int values[] = {1, 2}; Array array1(values, values + sizeof(values)/sizeof(values[0])); Array array2; array2 = std::move(array1); }); test_operation(++test, "Array get_size", []() { int values[] = {1, 2}; Array array(values, values + sizeof(values)/sizeof(values[0])); array.get_size(); }); test_operation(++test, "Array access by index", []() { int values[] = {1, 2}; Array array(values, values + sizeof(values)/sizeof(values[0])); array(1); }); test_operation(++test, "Array access by index const", []() { int values[] = {1, 2}; const Array array(values, values + sizeof(values)/sizeof(values[0])); array(1); }); test_operation(++test, "Array out of range", []() { int values[] = {1, 2}; Array array(values, values + sizeof(values)/sizeof(values[0])); array(2); }); test_operation(++test, "Array const out of range", []() { int values[] = {1, 2}; const Array array(values, values + sizeof(values)/sizeof(values[0])); array(2); }); test_operation(++test, "Array iterators", []() { int values[] = {1, 2}; Array array(values, values + sizeof(values)/sizeof(values[0])); for (auto& object: array) { } }); test_operation(++test, "Array const iterators", []() { int values[] = {1, 2}; const Array array(values, values + sizeof(values)/sizeof(values[0])); for (auto& object: array) { } }); std::cout << test << " tests survived." << std::endl; }