You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

184 lines
5.0 KiB
C++

1 month ago
#include <chrono>
#include <cstdlib>
#include <future>
#include <iostream>
#include <memory>
#include <thread>
#include <vector>
#include <catch.hpp>
#include <SurfaceGrid.h>
TEST_CASE("Matrix", "Test1")
{
ais::Matrix<int> a0 = {{1, 2}, {3, 4}};
ais::Matrix<int> a1 = {{1, 2}, {3, 4}, {5, 6}};
a1.reshape(2, 3); //{{1, 2}, {3, 4}, {5, 6}} ==> {{1,2,3}, {4,5,6}}
REQUIRE(a1.at(1, 1) == 5);
auto a2 = a1.astype<double>();
// Initializers
auto a3 = ais::Matrix<int>(3, 4) = 0;
REQUIRE(a3.min()[0] == 0);
auto a4 = ais::Matrix<int>(3, 4) = 1;
REQUIRE(a4.max()[0] == 1);
auto a5 = ais::Matrix<double>(3, 4) = std::nan("1");
REQUIRE(a3.none()[0]);
auto a6 = ais::Matrix<int>({{1, 2, 3}, {4, 5, 6}});
REQUIRE(a6.cumsum()[-1] == 21);
// fill and thread functions
ais::Matrix<int> a7(10000, 10000);
auto tb = std::chrono::system_clock::now();
a7.fill_random(0, a7.size());
auto te = std::chrono::system_clock::now();
std::chrono::duration<double> delta = te - tb;
std::cerr << "Signal thread elapsed time: " << delta.count() << "s" << std::endl;
auto multi_exec = [&](int threads)
{
// clean up values in matrix
a7.zeros();
auto size = a7.size();
auto count = size_t(size / threads);
auto tb = std::chrono::system_clock::now();
std::vector<std::future<uint64_t>> execs;
// std::future<uint64_t> execs[threads];
for (int i = 0; i < threads; i++)
{
auto begin = count * i;
// the last thread need fill all rest
auto end = (i == (threads - 1)) ? size : begin + count;
execs.push_back(std::async(std::launch::async, [&a7, &begin, &end]()
{
a7.fill_random(begin, end);
return end - begin; }));
}
uint64_t filled = 0;
for (auto &e : execs)
{
e.wait();
filled += e.get();
}
auto te = std::chrono::system_clock::now();
std::chrono::duration<double> delta = te - tb;
std::cerr << threads << " threads elapsed time: " << delta.count() << "s, filled: " << filled << std::endl;
return filled;
};
CHECK(multi_exec(4) == a7.size());
CHECK(multi_exec(10) == a7.size());
CHECK(multi_exec(20) == a7.size());
// Slicing/Broadcasting
auto value = a7(100, 100);
auto slice = a7({2, 5}, {2, 5});
auto rowSlice = a7(a7.row_slice(), 7);
auto values = a7[a7 > 50];
a7.put_mask(a7 > 50, 666);
// Concatenation
auto a = ais::random::rand_matrix<int>({1, 4}, 0, 10);
auto b = ais::random::rand_matrix<int>({1, 4}, 0, 10);
auto c = ais::random::rand_matrix<int>({1, 4}, 0, 10);
auto a8 = ais::stack({a, b, c}, ais::Axis::ROW);
auto a9 = ais::vstack({a, b, c});
auto a10 = ais::hstack({a, b, c});
auto a11 = ais::append(a, b, ais::Axis::COLUMN);
// Diagonal, Traingular, and Flip
auto d = ais::random::rand_matrix<int>({5, 5}, 0, 30);
auto a12 = ais::diagonal(d);
auto a13 = ais::triu(a);
auto a14 = ais::tril(a);
auto a15 = ais::flip(d, ais::Axis::ROW);
auto a16 = ais::flipud(d);
auto a17 = ais::fliplr(d);
// iteration
for (auto it = a.begin(); it < a.end(); ++it)
{
std::cout << *it << " ";
}
std::cout << std::endl;
for (auto &arrayValue : a)
{
std::cout << arrayValue << " ";
}
std::cout << std::endl;
auto t = std::make_shared<ais::Matrix<double>>();
t->resize_fast(1, 3);
std::vector<double> ds = {555.0, 213.2, 561.22};
std::vector<double> ds2 = {222.33, 12.9};
t->putMany(size_t(0), ds);
CHECK(t->sum()[0] > 1000);
t->putMany(0, 1, ds2);
CHECK(t->sum()[0] < 1000);
auto t2 = std::make_shared<ais::Matrix<ais::PointXYZ>>();
t2->resize_fast(1, 3);
t2->emptys();
auto p1 = t2->at(2);
CHECK(!p1.has_value());
std::vector<ais::PointXYZ> points = {{115.2, 558.5, 448}, {555.0, 213.2, 561.22}, {234, 231.32, 444}};
t2->putMany(size_t(0), points);
auto p = t2->max();
CHECK(p[0] == ais::PointXYZ(555.0, 213.2, 561.22));
auto a18 = ais::FMatrix(10, 10);
a18.nans();
for (auto i = 2; i <= 7; ++i)
{
auto random_sub = ais::random::rand_matrix<int>({1, 6}, 0, 10);
a18.putMany(i * 10 + 2, random_sub);
}
a18.print();
auto da = a18.data_area();
auto ti = a18.begin() + 55;
auto ps = a18.get_pos(ti);
CHECK(ps.first == ps.second);
}
TEST_CASE("Matrix_APoints", "TEST2")
{
auto m = ais::Matrix<ais::MCI_APoints>(2, 2);
// m[0] = ais::MCI_APoints();
m.print();
m.emptys();
m.print();
m[0][0] = 1;
m[0][1] = 2;
}
TEST_CASE("Matrix_Slice", "TEST3")
{
ais::Matrix<int> a(10, 10);
for (int i = 0; i < a.size(); i++)
a.put(i, i);
a.print();
auto cs = a({0, 4}, 2);
cs.print();
cs.reshape(1, 4);
cs.print();
ais::GridInterpolatorBlock block(a, 7, 6);
block.print();
CHECK(block(0, 0) == 76);
}