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++
184 lines
5.0 KiB
C++
|
|
#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);
|
|
}
|