Removed sw directory
This commit is contained in:
@@ -1,28 +0,0 @@
|
|||||||
BasedOnStyle: LLVM
|
|
||||||
Language: Cpp
|
|
||||||
|
|
||||||
IndentWidth: 4
|
|
||||||
UseTab: Never
|
|
||||||
#NamespaceIndentation: All
|
|
||||||
|
|
||||||
PointerAlignment: Left
|
|
||||||
AccessModifierOffset: -4
|
|
||||||
AlwaysBreakTemplateDeclarations: true
|
|
||||||
LambdaBodyIndentation: Signature
|
|
||||||
|
|
||||||
MaxEmptyLinesToKeep: 3
|
|
||||||
# ColumnLimit: 128
|
|
||||||
|
|
||||||
CompactNamespaces: true
|
|
||||||
FixNamespaceComments: true
|
|
||||||
|
|
||||||
AllowShortFunctionsOnASingleLine: false
|
|
||||||
AllowShortIfStatementsOnASingleLine: true
|
|
||||||
|
|
||||||
AlignConsecutiveAssignments: true
|
|
||||||
AlignConsecutiveBitFields: true
|
|
||||||
AlignConsecutiveDeclarations: true
|
|
||||||
AlignConsecutiveMacros: true
|
|
||||||
|
|
||||||
#BraceWrapping:
|
|
||||||
# BeforeElse: true
|
|
||||||
@@ -1,37 +0,0 @@
|
|||||||
cmake_minimum_required (VERSION 3.0)
|
|
||||||
project(cpp_decoders)
|
|
||||||
|
|
||||||
|
|
||||||
if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
|
|
||||||
message(STATUS "Setting build type to 'Release' as none was specified.")
|
|
||||||
set(CMAKE_BUILD_TYPE
|
|
||||||
Release
|
|
||||||
CACHE STRING "Choose the type of build." FORCE)
|
|
||||||
set_property(
|
|
||||||
CACHE CMAKE_BUILD_TYPE
|
|
||||||
PROPERTY STRINGS
|
|
||||||
"Debug"
|
|
||||||
"Release")
|
|
||||||
endif()
|
|
||||||
|
|
||||||
set(CMAKE_CXX_STANDARD 23)
|
|
||||||
|
|
||||||
find_package(Eigen3 3.3 REQUIRED NO_MODULE)
|
|
||||||
find_package(pybind11 CONFIG REQUIRED)
|
|
||||||
|
|
||||||
include_directories(${pybind11_INCLUDE_DIRS})
|
|
||||||
|
|
||||||
|
|
||||||
find_package(OpenMP REQUIRED)
|
|
||||||
|
|
||||||
#add_compile_options(-ffast-math)
|
|
||||||
|
|
||||||
pybind11_add_module(cpp_decoders src/python_interface.cpp)
|
|
||||||
target_link_libraries(cpp_decoders PRIVATE Eigen3::Eigen OpenMP::OpenMP_CXX)
|
|
||||||
|
|
||||||
set(INSTALL_DIR ${CMAKE_CURRENT_SOURCE_DIR}/../cpp_modules)
|
|
||||||
|
|
||||||
install(TARGETS cpp_decoders ARCHIVE DESTINATION ${INSTALL_DIR}
|
|
||||||
LIBRARY DESTINATION ${INSTALL_DIR}
|
|
||||||
RUNTIME DESTINATION ${INSTALL_DIR})
|
|
||||||
|
|
||||||
@@ -1,277 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include <Eigen/Dense>
|
|
||||||
#include <bit>
|
|
||||||
#include <cstdlib>
|
|
||||||
#include <iostream>
|
|
||||||
#include <stdexcept>
|
|
||||||
|
|
||||||
#include <pybind11/eigen.h>
|
|
||||||
#include <pybind11/stl.h>
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
*
|
|
||||||
* Using declarations
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
template <int t_rows, int t_cols>
|
|
||||||
using MatrixiR = Eigen::Matrix<int, t_rows, t_cols, Eigen::RowMajor>;
|
|
||||||
|
|
||||||
template <int t_rows, int t_cols>
|
|
||||||
using MatrixdR = Eigen::Matrix<double, t_rows, t_cols, Eigen::RowMajor>;
|
|
||||||
|
|
||||||
template <int t_size>
|
|
||||||
using RowVectori = Eigen::RowVector<int, t_size>;
|
|
||||||
|
|
||||||
template <int t_size>
|
|
||||||
using RowVectord = Eigen::RowVector<double, t_size>;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
*
|
|
||||||
* Proximal decoder implementation
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Class implementing the Proximal Decoding algorithm. See "Proximal
|
|
||||||
* Decoding for LDPC Codes" by Tadashi Wadayama, and Satoshi Takabe.
|
|
||||||
* @tparam t_m Number of rows of the H Matrix
|
|
||||||
* @tparam t_n Number of columns of the H Matrix
|
|
||||||
*/
|
|
||||||
template <int t_m, int t_n>
|
|
||||||
class ProximalDecoder {
|
|
||||||
public:
|
|
||||||
/**
|
|
||||||
* @brief Constructor
|
|
||||||
* @param H Parity-Check Matrix
|
|
||||||
* @param K Number of iterations to run while decoding
|
|
||||||
* @param omega Step size
|
|
||||||
* @param gamma Positive constant. Arises in the approximation of the prior
|
|
||||||
* PDF
|
|
||||||
* @param eta Positive constant slightly larger than one. See 3.2, p. 3
|
|
||||||
*/
|
|
||||||
ProximalDecoder(const Eigen::Ref<const MatrixiR<t_m, t_n>>& H, int K,
|
|
||||||
double omega, double gamma, double eta)
|
|
||||||
: mK(K), mOmega(omega), mGamma(gamma), mEta(eta), mH(H),
|
|
||||||
mH_zero_indices(find_zero(H)) {
|
|
||||||
|
|
||||||
Eigen::setNbThreads(8);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Decode a received signal. The algorithm is detailed in 3.2, p.3.
|
|
||||||
* This function assumes a BPSK modulated signal and an AWGN channel.
|
|
||||||
* @param y Vector of received values. (y = x + w, where 'x' is element of
|
|
||||||
* [-1, 1]^n and 'w' is noise)
|
|
||||||
* @return \b std::pair of the form (x_hat, num_iter), x_hat is the most
|
|
||||||
* probably sent codeword and num_iter is the number of iterations that were
|
|
||||||
* performed. If the parity check fails and no valid codeword is reached,
|
|
||||||
* num_iter is -1
|
|
||||||
*/
|
|
||||||
std::pair<RowVectori<t_n>, int>
|
|
||||||
decode(const Eigen::Ref<const RowVectord<t_n>>& y) {
|
|
||||||
if (y.size() != mH.cols())
|
|
||||||
throw std::runtime_error("Length of vector must match H matrix");
|
|
||||||
|
|
||||||
RowVectord<t_n> s = RowVectord<t_n>::Zero(t_n);
|
|
||||||
RowVectori<t_n> x_hat;
|
|
||||||
RowVectord<t_n> r;
|
|
||||||
|
|
||||||
for (std::size_t i = 0; i < mK; ++i) {
|
|
||||||
r = s - mOmega * L_awgn(s, y);
|
|
||||||
|
|
||||||
s = projection(r - mGamma * grad_H(r));
|
|
||||||
|
|
||||||
x_hat = s.unaryExpr([](double d) {
|
|
||||||
uint64_t bits = std::bit_cast<uint64_t>(d);
|
|
||||||
// Return the sign bit: 1 for negative, 0 for positive
|
|
||||||
return (bits >> 63);
|
|
||||||
}).template cast<int>();
|
|
||||||
|
|
||||||
if (check_parity(x_hat)) {
|
|
||||||
return {x_hat, i + 1};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return {x_hat, -1};
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Decode a received signal an measure error value (x - sign(x_hat))
|
|
||||||
* @param x Transmitted word
|
|
||||||
* @param y Received signal
|
|
||||||
* @return \b std::vector of error values. Each element corresponds to one
|
|
||||||
* iteration of the algorithm
|
|
||||||
*/
|
|
||||||
std::vector<double>
|
|
||||||
get_error_values(const Eigen::Ref<const RowVectori<t_n>>& x,
|
|
||||||
const Eigen::Ref<const RowVectord<t_n>>& y) {
|
|
||||||
|
|
||||||
if (y.size() != mH.cols())
|
|
||||||
throw std::runtime_error("Length of vector must match H matrix");
|
|
||||||
|
|
||||||
std::vector<double> error_values;
|
|
||||||
error_values.reserve(mK);
|
|
||||||
|
|
||||||
RowVectord<t_n> s = RowVectord<t_n>::Zero(t_n);
|
|
||||||
RowVectori<t_n> x_hat;
|
|
||||||
RowVectord<t_n> r;
|
|
||||||
|
|
||||||
for (std::size_t i = 0; i < mK; ++i) {
|
|
||||||
r = s - mOmega * L_awgn(s, y);
|
|
||||||
|
|
||||||
s = projection(r - mGamma * grad_H(r));
|
|
||||||
|
|
||||||
x_hat = s.unaryExpr([](double d) {
|
|
||||||
uint64_t bits = std::bit_cast<uint64_t>(d);
|
|
||||||
// Return the sign bit: 1 for negative, 0 for positive
|
|
||||||
return (bits >> 63);
|
|
||||||
}).template cast<int>();
|
|
||||||
|
|
||||||
RowVectord<t_n> x_hat_bpsk =
|
|
||||||
-1 * ((2 * x_hat.template cast<double>()).array() - 1).matrix();
|
|
||||||
error_values.push_back(
|
|
||||||
(x.template cast<double>() - x_hat_bpsk).norm());
|
|
||||||
|
|
||||||
if (check_parity(x_hat)) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return error_values;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Decode a received signal and measure the norm of the two gradients
|
|
||||||
* at each iteration
|
|
||||||
* @param y
|
|
||||||
* @return \b std::vector of \b std::pair of gradient values. Each element corresponds to
|
|
||||||
* one iteration. Result is of the form [(grad_H_1, grad_L_1), ...]
|
|
||||||
*/
|
|
||||||
std::vector<std::pair<double, double>>
|
|
||||||
get_gradient_values(const Eigen::Ref<const RowVectord<t_n>>& y) {
|
|
||||||
|
|
||||||
if (y.size() != mH.cols())
|
|
||||||
throw std::runtime_error("Length of vector must match H matrix");
|
|
||||||
|
|
||||||
std::vector<std::pair<double, double>> gradient_values;
|
|
||||||
gradient_values.reserve(mK);
|
|
||||||
|
|
||||||
RowVectord<t_n> s = RowVectord<t_n>::Zero(t_n);
|
|
||||||
RowVectori<t_n> x_hat;
|
|
||||||
RowVectord<t_n> r;
|
|
||||||
|
|
||||||
for (std::size_t i = 0; i < mK; ++i) {
|
|
||||||
RowVectord<t_n> gradl = L_awgn(s, y);
|
|
||||||
r = s - mOmega * gradl;
|
|
||||||
|
|
||||||
RowVectord<t_n> gradh = grad_H(r);
|
|
||||||
s = projection(r - mGamma * gradh);
|
|
||||||
|
|
||||||
gradient_values.push_back({gradh.norm(), gradl.norm()});
|
|
||||||
|
|
||||||
x_hat = s.unaryExpr([](double d) {
|
|
||||||
uint64_t bits = std::bit_cast<uint64_t>(d);
|
|
||||||
// Return the sign bit: 1 for negative, 0 for positive
|
|
||||||
return (bits >> 63);
|
|
||||||
}).template cast<int>();
|
|
||||||
|
|
||||||
if (check_parity(x_hat)) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return gradient_values;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Get the values of all member variables necessary to recreate an
|
|
||||||
* exact copy of this class. Used for pickling
|
|
||||||
* @return \b std::tuple
|
|
||||||
*/
|
|
||||||
auto get_decoder_state() const {
|
|
||||||
return std::tuple(mH, mK, mOmega, mGamma, mEta);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
const int mK;
|
|
||||||
const double mOmega;
|
|
||||||
const double mGamma;
|
|
||||||
const double mEta;
|
|
||||||
|
|
||||||
const MatrixiR<t_m, t_n> mH;
|
|
||||||
const std::vector<Eigen::Index> mH_zero_indices;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Variation of the negative log-likelihood for the special case of AWGN
|
|
||||||
* noise. See 4.1, p. 4.
|
|
||||||
*/
|
|
||||||
static Eigen::RowVectorXd L_awgn(const RowVectord<t_n>& s,
|
|
||||||
const RowVectord<t_n>& y) {
|
|
||||||
return s.array() - y.array();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Find all indices of a matrix, where the corresponding value is
|
|
||||||
* zero
|
|
||||||
* @return \b std::vector of indices
|
|
||||||
*/
|
|
||||||
static std::vector<Eigen::Index> find_zero(MatrixiR<t_m, t_n> mat) {
|
|
||||||
std::vector<Eigen::Index> indices;
|
|
||||||
|
|
||||||
for (Eigen::Index i = 0; i < mat.size(); ++i)
|
|
||||||
if (mat(i) == 0) indices.push_back(i);
|
|
||||||
|
|
||||||
return indices;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gradient of the code-constraint polynomial. See 2.3, p. 2.
|
|
||||||
*/
|
|
||||||
RowVectord<t_n> grad_H(const RowVectord<t_n>& x) {
|
|
||||||
MatrixdR<t_m, t_n> A_prod_matrix = x.replicate(t_m, 1);
|
|
||||||
|
|
||||||
for (const auto& index : mH_zero_indices)
|
|
||||||
A_prod_matrix(index) = 1;
|
|
||||||
RowVectord<t_m> A_prods = A_prod_matrix.rowwise().prod();
|
|
||||||
|
|
||||||
RowVectord<t_m> B_terms =
|
|
||||||
(A_prods.array().pow(2) - A_prods.array()).matrix().transpose();
|
|
||||||
|
|
||||||
RowVectord<t_n> B_sums = B_terms * mH.template cast<double>();
|
|
||||||
|
|
||||||
RowVectord<t_n> result = 4 * (x.array().pow(2) - 1) * x.array() +
|
|
||||||
(2 * x.array().inverse()) * B_sums.array();
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Perform a parity check for a given codeword.
|
|
||||||
* @param x_hat: codeword to be checked (element of [0, 1]^n)
|
|
||||||
* @return \b True if the parity check passes, i.e. the codeword is valid.
|
|
||||||
* False otherwise
|
|
||||||
*/
|
|
||||||
bool check_parity(const RowVectori<t_n>& x_hat) {
|
|
||||||
RowVectori<t_m> syndrome =
|
|
||||||
(mH * x_hat.transpose()).unaryExpr([](int i) { return i % 2; });
|
|
||||||
|
|
||||||
return !(syndrome.count() > 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Project a vector onto [-eta, eta]^n in order to avoid numerical
|
|
||||||
* instability. Detailed in 3.2, p. 3 (Equation (15)).
|
|
||||||
* @param v Vector to project
|
|
||||||
* @return v clipped to [-eta, eta]^n
|
|
||||||
*/
|
|
||||||
RowVectord<t_n> projection(const RowVectord<t_n>& v) {
|
|
||||||
return v.cwiseMin(mEta).cwiseMax(-mEta);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,58 +0,0 @@
|
|||||||
#define EIGEN_STACK_ALLOCATION_LIMIT 1048576
|
|
||||||
|
|
||||||
#include "proximal.h"
|
|
||||||
|
|
||||||
#include <pybind11/pybind11.h>
|
|
||||||
|
|
||||||
|
|
||||||
namespace py = pybind11;
|
|
||||||
using namespace pybind11::literals;
|
|
||||||
|
|
||||||
|
|
||||||
#define DEF_PROXIMAL_DECODER(name, m, n) \
|
|
||||||
py::class_<ProximalDecoder<m, n>>(proximal, name) \
|
|
||||||
.def(py::init<MatrixiR<m, n>, int, double, double, double>(), \
|
|
||||||
"H"_a.noconvert(), "K"_a = 100, "omega"_a = 0.0002, \
|
|
||||||
"gamma"_a = .05, "eta"_a = 1.5) \
|
|
||||||
.def("decode", &ProximalDecoder<m, n>::decode, "y"_a.noconvert()) \
|
|
||||||
.def("get_error_values", &ProximalDecoder<m, n>::get_error_values, \
|
|
||||||
"x"_a.noconvert(), "y"_a.noconvert()) \
|
|
||||||
.def("get_gradient_values", \
|
|
||||||
&ProximalDecoder<m, n>::get_gradient_values, "y"_a.noconvert()) \
|
|
||||||
.def(py::pickle( \
|
|
||||||
[](const ProximalDecoder<m, n>& a) { \
|
|
||||||
auto state = a.get_decoder_state(); \
|
|
||||||
\
|
|
||||||
MatrixiR<m, n> H = std::get<0>(state); \
|
|
||||||
int K = std::get<1>(state); \
|
|
||||||
double omega = std::get<2>(state); \
|
|
||||||
double gamma = std::get<3>(state); \
|
|
||||||
double eta = std::get<4>(state); \
|
|
||||||
\
|
|
||||||
return py::make_tuple(H, K, omega, gamma, eta); \
|
|
||||||
}, \
|
|
||||||
[](py::tuple t) { \
|
|
||||||
return ProximalDecoder<m, n>{ \
|
|
||||||
t[0].cast<MatrixiR<m, n>>(), t[1].cast<int>(), \
|
|
||||||
t[2].cast<double>(), t[3].cast<double>(), \
|
|
||||||
t[4].cast<double>()}; \
|
|
||||||
}));
|
|
||||||
|
|
||||||
|
|
||||||
PYBIND11_MODULE(cpp_decoders, proximal) {
|
|
||||||
proximal.doc() = "Proximal decoder";
|
|
||||||
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_7_3", 3, 7)
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_31_20", 20, 31)
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_31_5", 5, 31)
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_96_48", 48, 96)
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_204_102", 102, 204)
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_408_204", 204, 408)
|
|
||||||
DEF_PROXIMAL_DECODER("ProximalDecoder_Dynamic", Eigen::Dynamic,
|
|
||||||
Eigen::Dynamic)
|
|
||||||
|
|
||||||
py::register_exception<std::runtime_error>(
|
|
||||||
proximal, "CppException: std::runtime_error");
|
|
||||||
py::register_exception<std::bad_alloc>(proximal,
|
|
||||||
"CppException: std::bad_alloc");
|
|
||||||
}
|
|
||||||
@@ -1,24 +0,0 @@
|
|||||||
# Bachelorarbeit
|
|
||||||
|
|
||||||
## Software
|
|
||||||
|
|
||||||
Warning: At least a `Python 3.9` or higher is required to properly run the
|
|
||||||
scripts in this project
|
|
||||||
|
|
||||||
### Create a python virtual environment
|
|
||||||
|
|
||||||
In the root directory of this repository run
|
|
||||||
|
|
||||||
```bash
|
|
||||||
$ python3 -m venv venv
|
|
||||||
$ source venv/bin/activate
|
|
||||||
$ pip3 install -r requirements.txt
|
|
||||||
```
|
|
||||||
|
|
||||||
### Run the unit tests
|
|
||||||
|
|
||||||
In the root directory of this repository run
|
|
||||||
|
|
||||||
```bash
|
|
||||||
$ python -m unittest discover test
|
|
||||||
```
|
|
||||||
Binary file not shown.
@@ -1,2 +0,0 @@
|
|||||||
"""This package contains a number of different decoder implementations for
|
|
||||||
LDPC codes."""
|
|
||||||
@@ -1,52 +0,0 @@
|
|||||||
import numpy as np
|
|
||||||
import itertools
|
|
||||||
|
|
||||||
|
|
||||||
class MLDecoder:
|
|
||||||
"""This class naively implements a soft decision decoder. The decoder
|
|
||||||
calculates the correlation between the received signal and each codeword
|
|
||||||
and then chooses the one with the largest correlation.
|
|
||||||
"""
|
|
||||||
|
|
||||||
def __init__(self, G: np.array, H: np.array):
|
|
||||||
"""Construct a new SoftDecisionDecoder object.
|
|
||||||
|
|
||||||
:param G: Generator matrix
|
|
||||||
:param H: Parity check matrix
|
|
||||||
"""
|
|
||||||
self._G = G
|
|
||||||
self._H = H
|
|
||||||
self._datawords, self._codewords = self._gen_codewords()
|
|
||||||
|
|
||||||
# The codewords, but mapped to [-1, 1]^n
|
|
||||||
self._codewords_bpsk = 1 - 2 * self._codewords
|
|
||||||
|
|
||||||
def _gen_codewords(self) -> np.array:
|
|
||||||
"""Generate a list of all possible codewords.
|
|
||||||
|
|
||||||
:return: Numpy array of the form [[codeword_1], [codeword_2], ...]
|
|
||||||
(Each generated codeword is an element of [0, 1]^n)
|
|
||||||
"""
|
|
||||||
k, n = self._G.shape
|
|
||||||
|
|
||||||
# Generate a list of all possible data words
|
|
||||||
u_lst = [list(i) for i in itertools.product([0, 1], repeat=k)]
|
|
||||||
u_lst = np.array(u_lst)
|
|
||||||
|
|
||||||
# Map each data word onto a codeword
|
|
||||||
c_lst = np.dot(u_lst, self._G) % 2
|
|
||||||
|
|
||||||
return u_lst, c_lst
|
|
||||||
|
|
||||||
def decode(self, y: np.array) -> np.array:
|
|
||||||
"""Decode a received signal.
|
|
||||||
|
|
||||||
This function assumes a BPSK modulated signal.
|
|
||||||
|
|
||||||
:param y: Vector of received values. (y = x + w, where 'x' is
|
|
||||||
element of [-1, 1]^n and 'w' is noise)
|
|
||||||
:return: Most probably sent codeword (element of [0, 1]^k)
|
|
||||||
"""
|
|
||||||
correlations = np.dot(self._codewords_bpsk, y)
|
|
||||||
|
|
||||||
return self._codewords[np.argmax(correlations)]
|
|
||||||
@@ -1,97 +0,0 @@
|
|||||||
import numpy as np
|
|
||||||
|
|
||||||
|
|
||||||
class ProximalDecoder:
|
|
||||||
"""Class implementing the Proximal Decoding algorithm. See "Proximal
|
|
||||||
Decoding for LDPC Codes"
|
|
||||||
by Tadashi Wadayama, and Satoshi Takabe.
|
|
||||||
"""
|
|
||||||
|
|
||||||
def __init__(self, H: np.array, K: int = 1000, omega: float = 0.0002,
|
|
||||||
gamma: float = 0.05, eta: float = 1.5):
|
|
||||||
"""Construct a new ProximalDecoder Object.
|
|
||||||
|
|
||||||
:param H: Parity Check Matrix
|
|
||||||
:param K: Max number of iterations to perform when decoding
|
|
||||||
:param omega: Step size for the gradient descent process
|
|
||||||
:param gamma: Positive constant. Arises in the approximation of the
|
|
||||||
prior PDF
|
|
||||||
:param eta: Positive constant slightly larger than one. See 3.2, p. 3
|
|
||||||
"""
|
|
||||||
self._H = H
|
|
||||||
self._K = K
|
|
||||||
self._step_size = omega
|
|
||||||
self._gamma = gamma
|
|
||||||
self._eta = eta
|
|
||||||
|
|
||||||
self._k, self._n = self._H.shape
|
|
||||||
self._H_ne_0 = H != 0
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def _L_awgn(s: np.array, y: np.array) -> np.array:
|
|
||||||
"""Variation of the negative log-likelihood for the special case of
|
|
||||||
AWGN noise. See 4.1, p. 4.
|
|
||||||
"""
|
|
||||||
return s - y
|
|
||||||
|
|
||||||
def _grad_h(self, x: np.array) -> np.array:
|
|
||||||
"""Gradient of the code-constraint polynomial. See 2.3, p. 2."""
|
|
||||||
# Pre-computations
|
|
||||||
|
|
||||||
A_prod_matrix = np.tile(x, (self._k, 1))
|
|
||||||
A_prods = np.prod(A_prod_matrix, axis=1, where=self._H_ne_0)
|
|
||||||
|
|
||||||
# Calculate gradient
|
|
||||||
|
|
||||||
sums = np.dot(A_prods ** 2 - A_prods, self._H)
|
|
||||||
|
|
||||||
result = 4 * (x ** 2 - 1) * x + (2 / x) * sums
|
|
||||||
|
|
||||||
return result
|
|
||||||
|
|
||||||
def _projection(self, v):
|
|
||||||
"""Project a vector onto [-eta, eta]^n in order to avoid numerical
|
|
||||||
instability. Detailed in 3.2, p. 3 (Equation (15)).
|
|
||||||
|
|
||||||
:param v: Vector to project
|
|
||||||
:return: x clipped to [-eta, eta]^n
|
|
||||||
"""
|
|
||||||
return np.clip(v, -self._eta, self._eta)
|
|
||||||
|
|
||||||
def _check_parity(self, x_hat: np.array) -> bool:
|
|
||||||
"""Perform a parity check for a given codeword.
|
|
||||||
|
|
||||||
:param x_hat: codeword to be checked (element of [0, 1]^n)
|
|
||||||
:return: True if the parity check passes, i.e. the codeword is
|
|
||||||
valid. False otherwise
|
|
||||||
"""
|
|
||||||
syndrome = np.dot(self._H, x_hat) % 2
|
|
||||||
return not np.any(syndrome)
|
|
||||||
|
|
||||||
def decode(self, y: np.array) -> np.array:
|
|
||||||
"""Decode a received signal. The algorithm is detailed in 3.2, p.3.
|
|
||||||
|
|
||||||
This function assumes a BPSK modulated signal and an AWGN channel.
|
|
||||||
|
|
||||||
:param y: Vector of received values. (y = x + w, where 'x' is
|
|
||||||
element of [-1, 1]^n and 'w' is noise)
|
|
||||||
:return: Most probably sent codeword (element of [0, 1]^n). If
|
|
||||||
decoding fails, the returned value is 'None'
|
|
||||||
"""
|
|
||||||
s = np.zeros(self._n)
|
|
||||||
x_hat = np.zeros(self._n)
|
|
||||||
for k in range(self._K):
|
|
||||||
r = s - self._step_size * self._L_awgn(s, y)
|
|
||||||
|
|
||||||
s = r - self._gamma * self._grad_h(r)
|
|
||||||
s = self._projection(s) # Equation (15)
|
|
||||||
|
|
||||||
x_hat = np.sign(s)
|
|
||||||
|
|
||||||
# Map the codeword from [ -1, 1]^n to [0, 1]^n
|
|
||||||
x_hat = (x_hat == -1) * 1
|
|
||||||
|
|
||||||
if self._check_parity(x_hat):
|
|
||||||
return x_hat
|
|
||||||
|
|
||||||
return None
|
|
||||||
@@ -1,4 +0,0 @@
|
|||||||
matplotlib==3.6.2
|
|
||||||
pandas==1.5.2
|
|
||||||
seaborn==0.12.1
|
|
||||||
tqdm==4.64.1
|
|
||||||
@@ -1,310 +0,0 @@
|
|||||||
204 102
|
|
||||||
3 6
|
|
||||||
3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3
|
|
||||||
6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
|
|
||||||
73 84 81
|
|
||||||
63 45 26
|
|
||||||
17 77 55
|
|
||||||
74 47 24
|
|
||||||
9 10 52
|
|
||||||
62 63 44
|
|
||||||
38 39 35
|
|
||||||
60 4 100
|
|
||||||
82 98 63
|
|
||||||
40 80 68
|
|
||||||
91 81 18
|
|
||||||
86 88 99
|
|
||||||
77 71 65
|
|
||||||
29 9 33
|
|
||||||
15 41 34
|
|
||||||
75 11 22
|
|
||||||
48 24 95
|
|
||||||
22 44 60
|
|
||||||
5 19 41
|
|
||||||
31 22 43
|
|
||||||
21 18 56
|
|
||||||
83 51 49
|
|
||||||
79 7 88
|
|
||||||
36 67 5
|
|
||||||
84 75 32
|
|
||||||
1 79 38
|
|
||||||
43 82 75
|
|
||||||
2 1 23
|
|
||||||
33 61 83
|
|
||||||
69 3 30
|
|
||||||
28 5 77
|
|
||||||
8 56 4
|
|
||||||
53 76 36
|
|
||||||
96 28 102
|
|
||||||
44 17 48
|
|
||||||
92 26 74
|
|
||||||
56 69 11
|
|
||||||
18 68 50
|
|
||||||
72 34 37
|
|
||||||
25 37 76
|
|
||||||
23 30 21
|
|
||||||
7 29 40
|
|
||||||
71 78 39
|
|
||||||
13 2 96
|
|
||||||
55 33 51
|
|
||||||
49 64 16
|
|
||||||
37 66 54
|
|
||||||
50 36 89
|
|
||||||
45 15 57
|
|
||||||
88 35 15
|
|
||||||
57 102 78
|
|
||||||
98 27 71
|
|
||||||
27 52 94
|
|
||||||
68 20 87
|
|
||||||
89 38 8
|
|
||||||
24 94 53
|
|
||||||
11 50 19
|
|
||||||
14 83 98
|
|
||||||
76 55 2
|
|
||||||
41 70 62
|
|
||||||
78 86 14
|
|
||||||
3 21 59
|
|
||||||
64 23 46
|
|
||||||
47 43 45
|
|
||||||
95 31 1
|
|
||||||
85 59 84
|
|
||||||
94 54 101
|
|
||||||
93 6 31
|
|
||||||
59 95 61
|
|
||||||
58 73 47
|
|
||||||
54 87 7
|
|
||||||
52 97 79
|
|
||||||
12 90 28
|
|
||||||
30 99 97
|
|
||||||
42 100 73
|
|
||||||
101 62 20
|
|
||||||
80 96 85
|
|
||||||
100 58 91
|
|
||||||
19 16 6
|
|
||||||
99 49 72
|
|
||||||
70 92 17
|
|
||||||
90 93 69
|
|
||||||
10 40 25
|
|
||||||
39 72 82
|
|
||||||
67 74 12
|
|
||||||
4 65 27
|
|
||||||
20 85 90
|
|
||||||
102 13 92
|
|
||||||
46 8 9
|
|
||||||
35 46 10
|
|
||||||
97 53 93
|
|
||||||
66 48 42
|
|
||||||
87 89 64
|
|
||||||
26 25 58
|
|
||||||
6 57 67
|
|
||||||
65 12 3
|
|
||||||
61 91 66
|
|
||||||
81 101 29
|
|
||||||
51 60 86
|
|
||||||
16 14 80
|
|
||||||
34 32 70
|
|
||||||
32 42 13
|
|
||||||
72 17 45
|
|
||||||
52 14 22
|
|
||||||
49 53 2
|
|
||||||
95 76 60
|
|
||||||
39 57 26
|
|
||||||
32 60 48
|
|
||||||
2 78 8
|
|
||||||
92 3 54
|
|
||||||
71 55 42
|
|
||||||
23 5 62
|
|
||||||
35 99 50
|
|
||||||
37 31 18
|
|
||||||
24 84 12
|
|
||||||
14 97 56
|
|
||||||
94 40 44
|
|
||||||
22 74 63
|
|
||||||
63 49 28
|
|
||||||
42 96 78
|
|
||||||
101 27 85
|
|
||||||
55 75 99
|
|
||||||
40 9 67
|
|
||||||
61 28 97
|
|
||||||
76 101 16
|
|
||||||
88 95 33
|
|
||||||
5 33 37
|
|
||||||
68 61 27
|
|
||||||
65 52 38
|
|
||||||
20 42 15
|
|
||||||
60 23 84
|
|
||||||
67 73 52
|
|
||||||
25 66 53
|
|
||||||
51 77 21
|
|
||||||
81 62 1
|
|
||||||
66 21 96
|
|
||||||
75 56 83
|
|
||||||
8 13 19
|
|
||||||
30 19 51
|
|
||||||
102 90 58
|
|
||||||
97 11 68
|
|
||||||
89 15 98
|
|
||||||
44 20 35
|
|
||||||
74 35 5
|
|
||||||
26 72 59
|
|
||||||
10 88 94
|
|
||||||
46 69 100
|
|
||||||
16 54 77
|
|
||||||
91 6 74
|
|
||||||
13 64 101
|
|
||||||
47 32 40
|
|
||||||
50 24 90
|
|
||||||
38 48 46
|
|
||||||
86 85 47
|
|
||||||
6 51 34
|
|
||||||
7 68 36
|
|
||||||
56 7 31
|
|
||||||
69 92 61
|
|
||||||
48 39 43
|
|
||||||
31 71 64
|
|
||||||
33 8 93
|
|
||||||
79 4 17
|
|
||||||
98 37 95
|
|
||||||
77 87 25
|
|
||||||
19 67 49
|
|
||||||
87 2 69
|
|
||||||
1 22 10
|
|
||||||
64 29 88
|
|
||||||
70 91 65
|
|
||||||
84 25 102
|
|
||||||
99 45 66
|
|
||||||
58 18 57
|
|
||||||
4 1 70
|
|
||||||
12 30 72
|
|
||||||
82 89 32
|
|
||||||
15 47 55
|
|
||||||
18 59 24
|
|
||||||
21 81 13
|
|
||||||
54 100 29
|
|
||||||
57 50 4
|
|
||||||
90 94 23
|
|
||||||
34 10 79
|
|
||||||
93 44 89
|
|
||||||
73 102 41
|
|
||||||
80 26 82
|
|
||||||
11 65 92
|
|
||||||
45 41 87
|
|
||||||
28 83 71
|
|
||||||
85 34 39
|
|
||||||
9 82 14
|
|
||||||
3 36 20
|
|
||||||
83 86 76
|
|
||||||
29 70 80
|
|
||||||
43 12 9
|
|
||||||
78 63 73
|
|
||||||
27 46 30
|
|
||||||
59 16 86
|
|
||||||
62 58 6
|
|
||||||
41 98 91
|
|
||||||
96 93 11
|
|
||||||
53 43 81
|
|
||||||
36 79 75
|
|
||||||
17 38 3
|
|
||||||
100 80 7
|
|
||||||
26 167 28 173 65 135
|
|
||||||
28 109 44 166 59 105
|
|
||||||
62 191 30 110 96 203
|
|
||||||
86 173 8 162 32 180
|
|
||||||
19 127 31 112 24 144
|
|
||||||
95 155 68 149 79 198
|
|
||||||
42 156 23 157 71 204
|
|
||||||
32 138 89 161 55 109
|
|
||||||
5 190 14 123 89 194
|
|
||||||
83 146 5 182 90 167
|
|
||||||
57 186 16 141 37 200
|
|
||||||
73 174 96 194 85 115
|
|
||||||
44 150 88 138 102 178
|
|
||||||
58 116 100 104 61 190
|
|
||||||
15 176 49 142 50 130
|
|
||||||
100 148 79 197 46 125
|
|
||||||
3 203 35 103 81 162
|
|
||||||
38 177 21 172 11 114
|
|
||||||
79 165 19 139 57 138
|
|
||||||
87 130 54 143 76 191
|
|
||||||
21 178 62 136 41 134
|
|
||||||
18 118 20 167 16 104
|
|
||||||
41 112 63 131 28 181
|
|
||||||
56 115 17 152 4 177
|
|
||||||
40 133 94 170 83 164
|
|
||||||
94 145 36 185 2 107
|
|
||||||
53 196 52 121 86 128
|
|
||||||
31 188 34 124 73 119
|
|
||||||
14 193 42 168 98 179
|
|
||||||
74 139 41 174 30 196
|
|
||||||
20 160 65 114 68 157
|
|
||||||
102 108 101 151 25 175
|
|
||||||
29 161 45 127 14 126
|
|
||||||
101 182 39 189 15 155
|
|
||||||
90 113 50 144 7 143
|
|
||||||
24 202 48 191 33 156
|
|
||||||
47 114 40 163 39 127
|
|
||||||
7 153 55 203 26 129
|
|
||||||
84 107 7 159 43 189
|
|
||||||
10 123 83 117 42 151
|
|
||||||
60 199 15 187 19 184
|
|
||||||
75 120 102 130 92 111
|
|
||||||
27 194 64 201 20 159
|
|
||||||
35 143 18 183 6 117
|
|
||||||
49 187 2 171 64 103
|
|
||||||
89 147 90 196 63 153
|
|
||||||
64 151 4 176 70 154
|
|
||||||
17 159 92 153 35 108
|
|
||||||
46 105 80 119 22 165
|
|
||||||
48 152 57 180 38 113
|
|
||||||
99 134 22 155 45 139
|
|
||||||
72 104 53 129 5 132
|
|
||||||
33 201 91 105 56 133
|
|
||||||
71 179 67 148 47 110
|
|
||||||
45 122 59 111 3 176
|
|
||||||
37 157 32 137 21 116
|
|
||||||
51 180 95 107 49 172
|
|
||||||
70 172 78 198 94 140
|
|
||||||
69 197 66 177 62 145
|
|
||||||
8 131 99 108 18 106
|
|
||||||
97 124 29 128 69 158
|
|
||||||
6 198 76 135 60 112
|
|
||||||
2 119 6 195 9 118
|
|
||||||
63 168 46 150 93 160
|
|
||||||
96 129 86 186 13 169
|
|
||||||
92 136 47 133 97 171
|
|
||||||
85 132 24 165 95 123
|
|
||||||
54 128 38 156 10 141
|
|
||||||
30 158 37 147 82 166
|
|
||||||
81 169 60 193 101 173
|
|
||||||
43 111 13 160 52 188
|
|
||||||
39 103 84 145 80 174
|
|
||||||
1 184 70 132 75 195
|
|
||||||
4 144 85 118 36 149
|
|
||||||
16 137 25 122 27 202
|
|
||||||
59 125 33 106 40 192
|
|
||||||
13 164 3 134 31 148
|
|
||||||
61 195 43 109 51 120
|
|
||||||
23 162 26 202 72 182
|
|
||||||
77 185 10 204 100 193
|
|
||||||
98 135 11 178 1 201
|
|
||||||
9 175 27 190 84 185
|
|
||||||
22 192 58 188 29 137
|
|
||||||
25 170 1 115 66 131
|
|
||||||
66 189 87 154 77 121
|
|
||||||
12 154 61 192 99 197
|
|
||||||
93 166 71 164 54 187
|
|
||||||
50 126 12 146 23 168
|
|
||||||
55 142 93 175 48 183
|
|
||||||
82 181 73 140 87 152
|
|
||||||
11 149 97 169 78 199
|
|
||||||
36 110 81 158 88 186
|
|
||||||
68 183 82 200 91 161
|
|
||||||
67 117 56 181 53 146
|
|
||||||
65 106 69 126 17 163
|
|
||||||
34 200 77 120 44 136
|
|
||||||
91 141 72 116 74 124
|
|
||||||
52 163 9 199 58 142
|
|
||||||
80 171 74 113 12 122
|
|
||||||
78 204 75 179 8 147
|
|
||||||
76 121 98 125 67 150
|
|
||||||
88 140 51 184 34 170
|
|
||||||
@@ -1,310 +0,0 @@
|
|||||||
204 102
|
|
||||||
3 6
|
|
||||||
3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3
|
|
||||||
6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
|
|
||||||
76 98 67
|
|
||||||
67 36 11
|
|
||||||
17 44 4
|
|
||||||
44 66 94
|
|
||||||
79 24 34
|
|
||||||
95 69 6
|
|
||||||
82 87 12
|
|
||||||
87 60 41
|
|
||||||
3 8 45
|
|
||||||
14 2 95
|
|
||||||
31 79 96
|
|
||||||
99 62 46
|
|
||||||
98 6 48
|
|
||||||
45 29 30
|
|
||||||
84 33 39
|
|
||||||
23 35 13
|
|
||||||
4 23 84
|
|
||||||
92 91 74
|
|
||||||
64 77 20
|
|
||||||
75 99 60
|
|
||||||
57 100 77
|
|
||||||
58 59 36
|
|
||||||
56 12 40
|
|
||||||
51 80 32
|
|
||||||
50 54 21
|
|
||||||
19 37 56
|
|
||||||
54 86 24
|
|
||||||
36 48 43
|
|
||||||
5 70 47
|
|
||||||
93 38 98
|
|
||||||
11 78 54
|
|
||||||
25 71 102
|
|
||||||
16 88 1
|
|
||||||
8 61 19
|
|
||||||
42 40 14
|
|
||||||
94 13 51
|
|
||||||
32 49 31
|
|
||||||
9 56 59
|
|
||||||
74 20 26
|
|
||||||
62 43 92
|
|
||||||
63 75 66
|
|
||||||
38 34 83
|
|
||||||
72 65 93
|
|
||||||
71 55 23
|
|
||||||
18 22 78
|
|
||||||
97 96 53
|
|
||||||
52 31 29
|
|
||||||
2 27 99
|
|
||||||
85 42 86
|
|
||||||
90 28 79
|
|
||||||
59 85 27
|
|
||||||
21 15 73
|
|
||||||
27 45 5
|
|
||||||
91 5 87
|
|
||||||
29 53 3
|
|
||||||
66 17 81
|
|
||||||
101 74 2
|
|
||||||
88 46 55
|
|
||||||
49 97 42
|
|
||||||
15 51 18
|
|
||||||
100 63 16
|
|
||||||
68 41 10
|
|
||||||
47 82 35
|
|
||||||
26 68 101
|
|
||||||
22 57 9
|
|
||||||
13 19 58
|
|
||||||
83 89 15
|
|
||||||
55 73 61
|
|
||||||
35 10 38
|
|
||||||
43 39 37
|
|
||||||
69 7 89
|
|
||||||
61 16 70
|
|
||||||
53 64 17
|
|
||||||
10 25 82
|
|
||||||
89 26 22
|
|
||||||
39 101 91
|
|
||||||
65 1 75
|
|
||||||
30 14 72
|
|
||||||
41 92 100
|
|
||||||
37 47 7
|
|
||||||
70 81 62
|
|
||||||
86 76 88
|
|
||||||
28 50 63
|
|
||||||
20 95 90
|
|
||||||
102 72 76
|
|
||||||
12 11 25
|
|
||||||
80 3 57
|
|
||||||
6 67 8
|
|
||||||
73 9 44
|
|
||||||
96 4 28
|
|
||||||
34 21 80
|
|
||||||
78 58 97
|
|
||||||
60 90 71
|
|
||||||
24 18 85
|
|
||||||
40 94 33
|
|
||||||
46 102 65
|
|
||||||
48 93 68
|
|
||||||
81 83 50
|
|
||||||
7 30 49
|
|
||||||
33 52 69
|
|
||||||
77 84 52
|
|
||||||
1 32 64
|
|
||||||
99 95 33
|
|
||||||
66 76 62
|
|
||||||
41 102 80
|
|
||||||
9 99 13
|
|
||||||
25 45 35
|
|
||||||
2 91 90
|
|
||||||
16 89 53
|
|
||||||
88 39 6
|
|
||||||
42 11 38
|
|
||||||
11 49 84
|
|
||||||
35 51 39
|
|
||||||
102 60 27
|
|
||||||
57 14 26
|
|
||||||
27 80 42
|
|
||||||
101 42 50
|
|
||||||
70 34 44
|
|
||||||
30 92 5
|
|
||||||
39 79 65
|
|
||||||
92 29 101
|
|
||||||
64 28 82
|
|
||||||
53 67 21
|
|
||||||
93 8 17
|
|
||||||
76 43 23
|
|
||||||
40 10 76
|
|
||||||
67 84 41
|
|
||||||
3 98 7
|
|
||||||
36 52 63
|
|
||||||
58 18 71
|
|
||||||
33 88 11
|
|
||||||
55 75 78
|
|
||||||
23 56 29
|
|
||||||
72 23 92
|
|
||||||
4 57 94
|
|
||||||
5 2 85
|
|
||||||
15 70 49
|
|
||||||
28 40 83
|
|
||||||
61 71 99
|
|
||||||
54 9 91
|
|
||||||
63 19 4
|
|
||||||
80 35 72
|
|
||||||
10 12 48
|
|
||||||
50 82 32
|
|
||||||
71 83 100
|
|
||||||
79 86 47
|
|
||||||
26 48 52
|
|
||||||
73 3 28
|
|
||||||
65 101 97
|
|
||||||
29 26 86
|
|
||||||
38 66 12
|
|
||||||
74 97 56
|
|
||||||
75 7 36
|
|
||||||
77 27 69
|
|
||||||
14 63 74
|
|
||||||
95 16 55
|
|
||||||
47 4 73
|
|
||||||
62 24 19
|
|
||||||
86 73 59
|
|
||||||
51 61 30
|
|
||||||
84 47 88
|
|
||||||
90 65 61
|
|
||||||
48 72 2
|
|
||||||
60 77 31
|
|
||||||
87 94 77
|
|
||||||
44 59 3
|
|
||||||
13 36 1
|
|
||||||
78 13 60
|
|
||||||
56 54 45
|
|
||||||
100 58 89
|
|
||||||
17 74 15
|
|
||||||
97 81 34
|
|
||||||
6 87 64
|
|
||||||
96 6 40
|
|
||||||
19 17 16
|
|
||||||
43 44 18
|
|
||||||
89 62 67
|
|
||||||
91 93 24
|
|
||||||
1 100 68
|
|
||||||
85 33 98
|
|
||||||
31 37 20
|
|
||||||
81 96 43
|
|
||||||
94 41 95
|
|
||||||
46 15 57
|
|
||||||
45 32 14
|
|
||||||
8 64 9
|
|
||||||
59 21 10
|
|
||||||
32 53 79
|
|
||||||
49 25 75
|
|
||||||
22 1 58
|
|
||||||
52 22 25
|
|
||||||
18 50 87
|
|
||||||
34 68 66
|
|
||||||
82 20 93
|
|
||||||
12 5 54
|
|
||||||
37 78 70
|
|
||||||
21 30 37
|
|
||||||
68 85 8
|
|
||||||
69 31 102
|
|
||||||
7 38 81
|
|
||||||
24 69 51
|
|
||||||
20 46 96
|
|
||||||
98 55 22
|
|
||||||
83 90 46
|
|
||||||
102 179 77 190 33 167
|
|
||||||
48 108 10 136 57 163
|
|
||||||
9 128 87 148 55 166
|
|
||||||
17 135 90 157 3 141
|
|
||||||
29 136 54 195 53 119
|
|
||||||
88 173 13 174 6 110
|
|
||||||
99 200 71 153 80 128
|
|
||||||
34 186 9 124 88 198
|
|
||||||
38 106 89 140 65 186
|
|
||||||
74 143 69 126 62 187
|
|
||||||
31 112 86 111 2 131
|
|
||||||
86 195 23 143 7 151
|
|
||||||
66 167 36 168 16 106
|
|
||||||
10 155 78 115 35 185
|
|
||||||
60 137 52 184 67 171
|
|
||||||
33 109 72 156 61 175
|
|
||||||
3 171 56 175 73 124
|
|
||||||
45 192 94 130 60 176
|
|
||||||
26 175 66 141 34 158
|
|
||||||
84 202 39 194 19 181
|
|
||||||
52 197 91 187 25 123
|
|
||||||
65 190 45 191 75 203
|
|
||||||
16 133 17 134 44 125
|
|
||||||
94 201 5 158 27 178
|
|
||||||
32 107 74 189 86 191
|
|
||||||
64 147 75 150 39 115
|
|
||||||
53 116 48 154 51 114
|
|
||||||
83 138 50 122 90 148
|
|
||||||
55 150 14 121 47 133
|
|
||||||
78 119 99 197 14 160
|
|
||||||
11 181 47 199 37 164
|
|
||||||
37 188 102 185 24 144
|
|
||||||
100 131 15 180 95 103
|
|
||||||
91 193 42 118 5 172
|
|
||||||
69 113 16 142 63 107
|
|
||||||
28 129 2 167 22 153
|
|
||||||
80 196 26 181 70 197
|
|
||||||
42 151 30 200 69 111
|
|
||||||
76 120 70 110 15 113
|
|
||||||
95 126 35 138 23 174
|
|
||||||
79 105 62 183 8 127
|
|
||||||
35 111 49 117 59 116
|
|
||||||
70 176 40 125 28 182
|
|
||||||
4 166 3 176 89 118
|
|
||||||
14 185 53 107 9 169
|
|
||||||
96 184 58 202 12 204
|
|
||||||
63 157 80 161 29 146
|
|
||||||
97 163 28 147 13 143
|
|
||||||
59 189 37 112 99 137
|
|
||||||
25 144 83 192 98 117
|
|
||||||
24 160 60 113 36 201
|
|
||||||
47 191 100 129 101 147
|
|
||||||
73 123 55 188 46 109
|
|
||||||
27 140 25 169 31 195
|
|
||||||
68 132 44 203 58 156
|
|
||||||
23 169 38 133 26 152
|
|
||||||
21 115 65 135 87 184
|
|
||||||
22 130 92 170 66 190
|
|
||||||
51 187 22 166 38 159
|
|
||||||
93 164 8 114 20 168
|
|
||||||
72 139 34 160 68 162
|
|
||||||
40 158 12 177 81 104
|
|
||||||
41 141 61 155 83 129
|
|
||||||
19 122 73 186 102 173
|
|
||||||
77 149 43 162 96 120
|
|
||||||
56 104 4 151 41 193
|
|
||||||
2 127 88 123 1 177
|
|
||||||
62 198 64 193 97 179
|
|
||||||
71 199 6 201 100 154
|
|
||||||
81 118 29 137 72 196
|
|
||||||
44 145 32 139 93 130
|
|
||||||
43 134 85 163 78 142
|
|
||||||
89 148 68 159 52 157
|
|
||||||
39 152 57 171 18 155
|
|
||||||
20 153 41 132 77 189
|
|
||||||
1 125 82 104 85 126
|
|
||||||
101 154 19 164 21 165
|
|
||||||
92 168 31 196 45 132
|
|
||||||
5 146 11 120 50 188
|
|
||||||
87 142 24 116 91 105
|
|
||||||
98 182 81 172 56 200
|
|
||||||
7 194 63 144 74 122
|
|
||||||
67 204 98 145 42 138
|
|
||||||
15 161 101 127 17 112
|
|
||||||
49 180 51 198 94 136
|
|
||||||
82 159 27 146 49 150
|
|
||||||
8 165 7 173 54 192
|
|
||||||
58 110 33 131 82 161
|
|
||||||
75 177 67 109 71 170
|
|
||||||
50 162 93 204 84 108
|
|
||||||
54 178 18 108 76 140
|
|
||||||
18 121 79 119 40 134
|
|
||||||
30 124 97 178 43 194
|
|
||||||
36 183 95 165 4 135
|
|
||||||
6 156 84 103 10 183
|
|
||||||
90 174 46 182 11 202
|
|
||||||
46 172 59 152 92 149
|
|
||||||
13 203 1 128 30 180
|
|
||||||
12 103 20 106 48 139
|
|
||||||
61 170 21 179 79 145
|
|
||||||
57 117 76 149 64 121
|
|
||||||
85 114 96 105 32 199
|
|
||||||
@@ -1,310 +0,0 @@
|
|||||||
204 102
|
|
||||||
5 10
|
|
||||||
5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5 5
|
|
||||||
10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10
|
|
||||||
1 12 41 20 52
|
|
||||||
2 41 28 40 34
|
|
||||||
3 55 98 89 102
|
|
||||||
4 16 64 6 13
|
|
||||||
5 93 58 37 25
|
|
||||||
6 91 62 67 68
|
|
||||||
7 43 30 34 62
|
|
||||||
8 87 53 48 50
|
|
||||||
9 85 81 43 74
|
|
||||||
10 82 26 77 44
|
|
||||||
11 42 72 82 33
|
|
||||||
12 98 83 54 65
|
|
||||||
13 65 48 41 77
|
|
||||||
14 10 71 47 92
|
|
||||||
15 17 74 2 49
|
|
||||||
16 100 63 81 24
|
|
||||||
17 6 36 55 5
|
|
||||||
18 80 59 98 1
|
|
||||||
19 101 11 80 70
|
|
||||||
20 47 32 56 90
|
|
||||||
21 89 49 60 93
|
|
||||||
22 19 27 87 86
|
|
||||||
23 7 19 91 10
|
|
||||||
24 59 25 70 66
|
|
||||||
25 49 96 72 12
|
|
||||||
26 64 76 11 48
|
|
||||||
27 63 35 1 26
|
|
||||||
28 54 75 57 11
|
|
||||||
29 31 93 35 91
|
|
||||||
30 95 66 32 98
|
|
||||||
31 56 3 22 14
|
|
||||||
32 88 21 3 23
|
|
||||||
33 79 88 13 8
|
|
||||||
34 13 46 96 37
|
|
||||||
35 36 80 62 40
|
|
||||||
36 81 101 83 97
|
|
||||||
37 8 55 19 4
|
|
||||||
38 37 97 102 60
|
|
||||||
39 94 52 88 72
|
|
||||||
40 14 90 26 9
|
|
||||||
41 9 39 75 101
|
|
||||||
42 3 5 24 27
|
|
||||||
43 40 42 51 79
|
|
||||||
44 22 17 90 63
|
|
||||||
45 84 43 52 76
|
|
||||||
46 97 47 85 80
|
|
||||||
47 33 18 84 95
|
|
||||||
48 29 73 36 84
|
|
||||||
49 92 50 78 73
|
|
||||||
50 27 13 95 20
|
|
||||||
51 20 102 49 88
|
|
||||||
52 71 65 66 89
|
|
||||||
53 99 10 30 85
|
|
||||||
54 52 85 50 69
|
|
||||||
55 78 60 25 81
|
|
||||||
56 96 70 38 43
|
|
||||||
57 69 67 65 19
|
|
||||||
58 74 68 14 30
|
|
||||||
59 60 69 16 41
|
|
||||||
60 35 54 53 39
|
|
||||||
61 90 87 23 46
|
|
||||||
62 48 99 21 18
|
|
||||||
63 28 95 45 71
|
|
||||||
64 73 86 31 53
|
|
||||||
65 76 23 93 78
|
|
||||||
66 72 51 46 57
|
|
||||||
67 25 79 28 16
|
|
||||||
68 51 100 15 96
|
|
||||||
69 61 37 29 83
|
|
||||||
70 75 15 71 58
|
|
||||||
71 68 34 4 17
|
|
||||||
72 5 92 101 21
|
|
||||||
73 24 8 17 7
|
|
||||||
74 32 61 27 99
|
|
||||||
75 4 84 44 2
|
|
||||||
76 34 33 39 38
|
|
||||||
77 46 24 69 31
|
|
||||||
78 39 6 58 32
|
|
||||||
79 45 29 64 82
|
|
||||||
80 2 7 94 56
|
|
||||||
81 57 45 33 87
|
|
||||||
82 1 94 100 54
|
|
||||||
83 86 44 7 47
|
|
||||||
84 77 91 74 64
|
|
||||||
85 26 4 18 67
|
|
||||||
86 102 2 12 35
|
|
||||||
87 83 77 5 15
|
|
||||||
88 11 9 63 59
|
|
||||||
89 50 57 97 22
|
|
||||||
90 53 78 68 29
|
|
||||||
91 58 56 86 51
|
|
||||||
92 38 16 9 42
|
|
||||||
93 18 40 10 61
|
|
||||||
94 30 31 76 28
|
|
||||||
95 44 14 42 100
|
|
||||||
96 62 82 59 75
|
|
||||||
97 67 12 99 45
|
|
||||||
98 21 22 73 94
|
|
||||||
99 23 20 79 55
|
|
||||||
100 70 89 8 36
|
|
||||||
101 15 38 61 3
|
|
||||||
102 66 1 92 6
|
|
||||||
1 89 69 9 62
|
|
||||||
2 95 87 69 99
|
|
||||||
3 46 50 93 70
|
|
||||||
4 20 38 65 100
|
|
||||||
5 94 10 86 74
|
|
||||||
6 27 84 82 12
|
|
||||||
7 15 33 41 89
|
|
||||||
8 44 93 11 52
|
|
||||||
9 82 73 61 4
|
|
||||||
10 101 54 66 55
|
|
||||||
11 62 94 97 15
|
|
||||||
12 4 40 70 69
|
|
||||||
13 85 42 89 32
|
|
||||||
14 86 11 96 29
|
|
||||||
15 31 37 42 66
|
|
||||||
16 90 58 95 7
|
|
||||||
17 99 41 64 93
|
|
||||||
18 72 74 71 87
|
|
||||||
19 2 85 14 63
|
|
||||||
20 78 66 18 43
|
|
||||||
21 84 35 38 79
|
|
||||||
22 12 100 47 101
|
|
||||||
23 18 89 16 39
|
|
||||||
24 21 82 50 19
|
|
||||||
25 45 30 4 77
|
|
||||||
26 47 70 102 61
|
|
||||||
27 70 62 88 85
|
|
||||||
28 1 19 78 72
|
|
||||||
29 19 16 51 94
|
|
||||||
30 41 23 72 47
|
|
||||||
31 23 25 75 51
|
|
||||||
32 64 68 63 57
|
|
||||||
33 66 44 74 40
|
|
||||||
34 69 64 98 97
|
|
||||||
35 57 13 90 10
|
|
||||||
36 16 34 53 65
|
|
||||||
37 36 78 45 54
|
|
||||||
38 30 52 13 67
|
|
||||||
39 79 22 5 2
|
|
||||||
40 65 39 24 84
|
|
||||||
41 68 88 19 81
|
|
||||||
42 91 2 76 46
|
|
||||||
43 37 24 68 49
|
|
||||||
44 13 18 36 24
|
|
||||||
45 24 92 26 23
|
|
||||||
46 55 45 40 83
|
|
||||||
47 48 49 58 35
|
|
||||||
48 97 28 52 59
|
|
||||||
49 32 77 54 16
|
|
||||||
50 59 56 23 68
|
|
||||||
51 80 90 84 3
|
|
||||||
52 58 21 33 27
|
|
||||||
53 33 75 91 26
|
|
||||||
54 56 8 99 42
|
|
||||||
55 53 97 44 41
|
|
||||||
56 40 76 100 5
|
|
||||||
57 3 47 29 34
|
|
||||||
58 81 26 22 13
|
|
||||||
59 38 12 17 95
|
|
||||||
60 6 101 30 56
|
|
||||||
61 52 95 77 36
|
|
||||||
62 74 4 101 50
|
|
||||||
63 50 6 15 25
|
|
||||||
64 35 14 94 75
|
|
||||||
65 10 80 31 6
|
|
||||||
66 7 36 21 64
|
|
||||||
67 22 71 20 37
|
|
||||||
68 11 98 27 38
|
|
||||||
69 28 86 92 88
|
|
||||||
70 76 57 55 82
|
|
||||||
71 102 91 8 9
|
|
||||||
72 83 48 6 14
|
|
||||||
73 39 63 10 102
|
|
||||||
74 29 65 60 22
|
|
||||||
75 49 7 85 1
|
|
||||||
76 25 3 7 71
|
|
||||||
77 73 20 59 33
|
|
||||||
78 88 15 56 44
|
|
||||||
79 96 9 32 18
|
|
||||||
80 34 67 87 78
|
|
||||||
81 54 59 34 31
|
|
||||||
82 93 102 67 90
|
|
||||||
83 92 99 25 91
|
|
||||||
84 67 96 81 92
|
|
||||||
85 98 51 28 60
|
|
||||||
86 63 79 49 80
|
|
||||||
87 51 55 35 30
|
|
||||||
88 60 31 1 17
|
|
||||||
89 77 81 2 11
|
|
||||||
90 8 43 12 28
|
|
||||||
91 61 5 80 48
|
|
||||||
92 17 32 43 53
|
|
||||||
93 100 27 48 45
|
|
||||||
94 71 61 57 96
|
|
||||||
95 5 60 46 8
|
|
||||||
96 87 17 39 98
|
|
||||||
97 9 72 3 86
|
|
||||||
98 26 29 62 20
|
|
||||||
99 43 46 73 58
|
|
||||||
100 75 83 79 73
|
|
||||||
101 14 1 37 76
|
|
||||||
102 42 53 83 21
|
|
||||||
1 103 82 130 102 203 27 190 18 177
|
|
||||||
2 104 80 121 86 144 15 191 75 141
|
|
||||||
3 105 42 159 31 178 32 199 101 153
|
|
||||||
4 106 75 114 85 164 71 127 37 111
|
|
||||||
5 107 72 197 42 193 87 141 17 158
|
|
||||||
6 108 17 162 78 165 4 174 102 167
|
|
||||||
7 109 23 168 80 177 83 178 73 118
|
|
||||||
8 110 37 192 73 156 100 173 33 197
|
|
||||||
9 111 41 199 88 181 92 103 40 173
|
|
||||||
10 112 14 167 53 107 93 175 23 137
|
|
||||||
11 113 88 170 19 116 26 110 28 191
|
|
||||||
12 114 1 124 97 161 86 192 25 108
|
|
||||||
13 115 34 146 50 137 33 140 4 160
|
|
||||||
14 116 40 203 95 166 58 121 31 174
|
|
||||||
15 117 101 109 70 180 68 165 87 113
|
|
||||||
16 118 4 138 92 131 59 125 67 151
|
|
||||||
17 119 15 194 44 198 73 161 71 190
|
|
||||||
18 120 93 125 47 146 85 122 62 181
|
|
||||||
19 121 22 131 23 130 37 143 57 126
|
|
||||||
20 122 51 106 99 179 1 169 50 200
|
|
||||||
21 123 98 126 32 154 62 168 72 204
|
|
||||||
22 124 44 169 98 141 31 160 89 176
|
|
||||||
23 125 99 133 65 132 61 152 32 147
|
|
||||||
24 126 73 147 77 145 42 142 16 146
|
|
||||||
25 127 67 178 24 133 55 185 5 165
|
|
||||||
26 128 85 200 10 160 40 147 27 155
|
|
||||||
27 129 50 108 22 195 74 170 42 154
|
|
||||||
28 130 63 171 2 150 67 187 94 192
|
|
||||||
29 131 48 176 79 200 69 159 90 116
|
|
||||||
30 132 94 140 7 127 53 162 58 189
|
|
||||||
31 133 29 117 94 190 64 167 77 183
|
|
||||||
32 134 74 151 20 194 30 181 78 115
|
|
||||||
33 135 47 155 76 109 81 154 11 179
|
|
||||||
34 136 76 182 71 138 7 183 2 159
|
|
||||||
35 137 60 166 27 123 29 189 86 149
|
|
||||||
36 138 35 139 17 168 48 146 100 163
|
|
||||||
37 139 38 145 69 117 5 203 34 169
|
|
||||||
38 140 92 161 101 106 56 123 76 170
|
|
||||||
39 141 78 175 41 142 76 198 60 125
|
|
||||||
40 142 43 158 93 114 2 148 35 135
|
|
||||||
41 143 2 132 1 119 13 109 59 157
|
|
||||||
42 144 11 204 43 115 95 117 92 156
|
|
||||||
43 145 7 201 45 192 9 194 56 122
|
|
||||||
44 146 95 110 83 135 75 157 10 180
|
|
||||||
45 147 79 127 81 148 63 139 97 195
|
|
||||||
46 148 77 105 34 201 66 197 61 144
|
|
||||||
47 149 20 128 46 159 14 124 83 132
|
|
||||||
48 150 62 149 13 174 8 195 26 193
|
|
||||||
49 151 25 177 21 149 51 188 15 145
|
|
||||||
50 152 89 165 49 105 54 126 8 164
|
|
||||||
51 153 68 189 66 187 43 131 91 133
|
|
||||||
52 154 54 163 39 140 45 150 1 110
|
|
||||||
53 155 90 157 8 204 60 138 64 194
|
|
||||||
54 156 28 183 60 112 12 151 82 139
|
|
||||||
55 157 3 148 37 189 17 172 99 112
|
|
||||||
56 158 31 156 91 152 20 180 80 162
|
|
||||||
57 159 81 137 89 172 28 196 66 134
|
|
||||||
58 160 91 154 5 118 78 149 70 201
|
|
||||||
59 161 24 152 18 183 96 179 88 150
|
|
||||||
60 162 59 190 55 197 21 176 38 187
|
|
||||||
61 163 69 193 74 196 101 111 93 128
|
|
||||||
62 164 96 113 6 129 35 200 7 103
|
|
||||||
63 165 27 188 16 175 88 134 44 121
|
|
||||||
64 166 26 134 4 136 79 119 84 168
|
|
||||||
65 167 13 142 52 176 57 106 12 138
|
|
||||||
66 168 102 135 30 122 52 112 24 117
|
|
||||||
67 169 97 186 57 182 6 184 85 140
|
|
||||||
68 170 71 143 58 134 90 145 6 152
|
|
||||||
69 171 57 136 59 103 77 104 54 114
|
|
||||||
70 172 100 129 56 128 24 114 19 105
|
|
||||||
71 173 52 196 14 169 70 120 63 178
|
|
||||||
72 174 66 120 11 199 25 132 39 130
|
|
||||||
73 175 64 179 48 111 98 201 49 202
|
|
||||||
74 176 58 164 15 120 84 135 9 107
|
|
||||||
75 177 70 202 28 155 41 133 96 166
|
|
||||||
76 178 65 172 26 158 94 144 45 203
|
|
||||||
77 179 84 191 87 151 10 163 13 127
|
|
||||||
78 180 55 122 90 139 49 130 65 182
|
|
||||||
79 181 33 141 67 188 99 202 43 123
|
|
||||||
80 182 18 153 35 167 19 193 46 188
|
|
||||||
81 183 36 160 9 191 16 186 55 143
|
|
||||||
82 184 10 111 96 126 11 108 79 172
|
|
||||||
83 185 87 174 12 202 36 204 69 148
|
|
||||||
84 186 45 123 75 108 47 153 48 142
|
|
||||||
85 187 9 115 54 121 46 177 53 129
|
|
||||||
86 188 83 116 64 171 91 107 22 199
|
|
||||||
87 189 8 198 61 104 22 182 81 120
|
|
||||||
88 190 32 180 33 143 39 129 51 171
|
|
||||||
89 191 21 103 100 125 3 115 52 109
|
|
||||||
90 192 61 118 40 153 44 137 20 184
|
|
||||||
91 193 6 144 84 173 23 155 29 185
|
|
||||||
92 194 49 185 72 147 102 171 14 186
|
|
||||||
93 195 5 184 29 110 65 105 21 119
|
|
||||||
94 196 39 107 82 113 80 166 98 131
|
|
||||||
95 197 30 104 63 163 50 118 47 161
|
|
||||||
96 198 56 181 25 186 34 116 68 196
|
|
||||||
97 199 46 150 38 157 89 113 36 136
|
|
||||||
98 200 12 187 3 170 18 136 30 198
|
|
||||||
99 201 53 119 62 185 97 156 74 104
|
|
||||||
100 202 16 195 68 124 82 158 95 106
|
|
||||||
101 203 19 112 36 162 72 164 41 124
|
|
||||||
102 204 86 173 51 184 38 128 3 175
|
|
||||||
@@ -1,616 +0,0 @@
|
|||||||
408 204
|
|
||||||
3 6
|
|
||||||
3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3
|
|
||||||
6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
|
|
||||||
27 43 140
|
|
||||||
88 42 106
|
|
||||||
71 80 202
|
|
||||||
158 129 15
|
|
||||||
125 149 93
|
|
||||||
13 158 180
|
|
||||||
166 146 23
|
|
||||||
12 65 153
|
|
||||||
147 199 17
|
|
||||||
4 180 99
|
|
||||||
84 113 103
|
|
||||||
146 51 150
|
|
||||||
75 30 160
|
|
||||||
163 49 87
|
|
||||||
29 192 2
|
|
||||||
159 74 104
|
|
||||||
18 95 157
|
|
||||||
86 116 132
|
|
||||||
102 166 81
|
|
||||||
121 60 185
|
|
||||||
156 203 56
|
|
||||||
63 32 36
|
|
||||||
191 106 196
|
|
||||||
107 128 21
|
|
||||||
177 48 181
|
|
||||||
151 71 80
|
|
||||||
119 12 69
|
|
||||||
134 145 164
|
|
||||||
69 54 25
|
|
||||||
111 39 33
|
|
||||||
114 204 187
|
|
||||||
93 38 188
|
|
||||||
168 105 8
|
|
||||||
122 98 163
|
|
||||||
67 36 5
|
|
||||||
43 186 18
|
|
||||||
202 66 131
|
|
||||||
162 107 126
|
|
||||||
85 163 137
|
|
||||||
72 41 48
|
|
||||||
170 27 149
|
|
||||||
126 79 179
|
|
||||||
99 25 161
|
|
||||||
34 122 63
|
|
||||||
144 22 146
|
|
||||||
157 150 183
|
|
||||||
79 175 62
|
|
||||||
80 40 192
|
|
||||||
90 33 75
|
|
||||||
161 46 73
|
|
||||||
81 108 34
|
|
||||||
62 2 19
|
|
||||||
77 144 54
|
|
||||||
21 73 53
|
|
||||||
197 72 195
|
|
||||||
40 156 78
|
|
||||||
50 92 138
|
|
||||||
36 4 184
|
|
||||||
155 23 42
|
|
||||||
65 26 177
|
|
||||||
47 187 6
|
|
||||||
153 3 27
|
|
||||||
57 134 127
|
|
||||||
28 200 14
|
|
||||||
184 137 154
|
|
||||||
39 117 128
|
|
||||||
94 13 39
|
|
||||||
145 21 122
|
|
||||||
92 82 57
|
|
||||||
59 174 200
|
|
||||||
2 11 125
|
|
||||||
186 119 109
|
|
||||||
58 148 169
|
|
||||||
109 55 1
|
|
||||||
175 8 145
|
|
||||||
44 132 32
|
|
||||||
98 191 83
|
|
||||||
140 138 156
|
|
||||||
46 56 123
|
|
||||||
169 87 28
|
|
||||||
22 96 203
|
|
||||||
37 152 112
|
|
||||||
174 37 12
|
|
||||||
20 29 197
|
|
||||||
32 20 29
|
|
||||||
53 19 143
|
|
||||||
61 88 90
|
|
||||||
8 75 35
|
|
||||||
181 198 55
|
|
||||||
115 126 10
|
|
||||||
10 159 98
|
|
||||||
203 115 85
|
|
||||||
171 161 191
|
|
||||||
135 10 7
|
|
||||||
31 103 134
|
|
||||||
26 85 141
|
|
||||||
173 1 114
|
|
||||||
128 197 198
|
|
||||||
7 64 118
|
|
||||||
103 141 76
|
|
||||||
108 86 61
|
|
||||||
74 17 116
|
|
||||||
101 196 22
|
|
||||||
19 91 105
|
|
||||||
6 167 45
|
|
||||||
190 123 129
|
|
||||||
117 31 108
|
|
||||||
130 97 155
|
|
||||||
14 151 92
|
|
||||||
127 50 88
|
|
||||||
131 184 170
|
|
||||||
106 125 101
|
|
||||||
138 136 120
|
|
||||||
66 93 144
|
|
||||||
82 70 38
|
|
||||||
55 157 107
|
|
||||||
150 176 82
|
|
||||||
204 58 37
|
|
||||||
15 133 91
|
|
||||||
97 15 44
|
|
||||||
83 140 130
|
|
||||||
142 135 95
|
|
||||||
104 77 52
|
|
||||||
194 59 199
|
|
||||||
35 104 142
|
|
||||||
17 139 11
|
|
||||||
110 162 9
|
|
||||||
176 142 148
|
|
||||||
120 57 47
|
|
||||||
60 62 124
|
|
||||||
116 188 51
|
|
||||||
48 194 162
|
|
||||||
11 9 194
|
|
||||||
24 118 77
|
|
||||||
188 124 110
|
|
||||||
198 61 74
|
|
||||||
89 47 68
|
|
||||||
192 45 113
|
|
||||||
5 16 72
|
|
||||||
136 5 102
|
|
||||||
118 155 71
|
|
||||||
56 153 182
|
|
||||||
9 181 96
|
|
||||||
149 202 84
|
|
||||||
199 63 4
|
|
||||||
164 114 172
|
|
||||||
100 170 117
|
|
||||||
137 110 97
|
|
||||||
165 24 151
|
|
||||||
96 185 26
|
|
||||||
112 69 168
|
|
||||||
113 6 67
|
|
||||||
132 164 13
|
|
||||||
189 165 41
|
|
||||||
180 147 176
|
|
||||||
167 121 60
|
|
||||||
179 7 89
|
|
||||||
148 177 173
|
|
||||||
139 183 186
|
|
||||||
183 67 20
|
|
||||||
73 172 50
|
|
||||||
30 168 193
|
|
||||||
87 179 59
|
|
||||||
68 131 58
|
|
||||||
129 154 64
|
|
||||||
160 112 46
|
|
||||||
33 18 16
|
|
||||||
123 160 121
|
|
||||||
172 89 147
|
|
||||||
185 44 3
|
|
||||||
78 94 43
|
|
||||||
154 81 119
|
|
||||||
200 127 189
|
|
||||||
52 68 66
|
|
||||||
51 143 201
|
|
||||||
70 99 100
|
|
||||||
38 53 94
|
|
||||||
152 83 49
|
|
||||||
178 111 135
|
|
||||||
201 173 24
|
|
||||||
64 178 30
|
|
||||||
187 182 139
|
|
||||||
45 76 159
|
|
||||||
41 78 31
|
|
||||||
195 189 70
|
|
||||||
23 109 79
|
|
||||||
133 34 175
|
|
||||||
91 100 174
|
|
||||||
49 130 111
|
|
||||||
42 90 158
|
|
||||||
3 190 165
|
|
||||||
95 28 86
|
|
||||||
1 101 178
|
|
||||||
76 102 152
|
|
||||||
124 14 204
|
|
||||||
25 84 65
|
|
||||||
54 169 136
|
|
||||||
143 171 190
|
|
||||||
16 201 167
|
|
||||||
196 52 115
|
|
||||||
182 120 133
|
|
||||||
105 193 40
|
|
||||||
141 195 171
|
|
||||||
193 35 166
|
|
||||||
84 69 187
|
|
||||||
27 150 193
|
|
||||||
201 8 124
|
|
||||||
71 9 28
|
|
||||||
192 181 95
|
|
||||||
146 151 62
|
|
||||||
20 128 83
|
|
||||||
91 20 9
|
|
||||||
15 88 185
|
|
||||||
18 202 133
|
|
||||||
89 142 37
|
|
||||||
198 170 189
|
|
||||||
77 71 159
|
|
||||||
101 156 183
|
|
||||||
120 126 34
|
|
||||||
130 122 197
|
|
||||||
43 144 33
|
|
||||||
121 189 45
|
|
||||||
62 26 74
|
|
||||||
196 168 19
|
|
||||||
180 58 117
|
|
||||||
173 149 90
|
|
||||||
92 89 203
|
|
||||||
187 24 127
|
|
||||||
75 104 64
|
|
||||||
134 4 88
|
|
||||||
124 38 3
|
|
||||||
169 83 161
|
|
||||||
190 93 198
|
|
||||||
159 201 195
|
|
||||||
151 124 93
|
|
||||||
57 43 147
|
|
||||||
40 153 170
|
|
||||||
6 194 57
|
|
||||||
154 65 160
|
|
||||||
50 154 23
|
|
||||||
79 135 141
|
|
||||||
145 91 108
|
|
||||||
109 19 130
|
|
||||||
85 130 162
|
|
||||||
106 90 135
|
|
||||||
117 166 144
|
|
||||||
66 49 47
|
|
||||||
140 191 89
|
|
||||||
164 101 110
|
|
||||||
150 197 101
|
|
||||||
125 87 188
|
|
||||||
141 73 65
|
|
||||||
11 78 24
|
|
||||||
97 164 131
|
|
||||||
37 48 94
|
|
||||||
32 127 164
|
|
||||||
107 64 16
|
|
||||||
152 79 2
|
|
||||||
58 173 6
|
|
||||||
29 3 139
|
|
||||||
21 161 70
|
|
||||||
165 167 129
|
|
||||||
166 136 148
|
|
||||||
155 177 7
|
|
||||||
22 34 167
|
|
||||||
193 118 174
|
|
||||||
73 119 17
|
|
||||||
51 172 27
|
|
||||||
103 11 118
|
|
||||||
64 115 140
|
|
||||||
72 121 109
|
|
||||||
26 47 128
|
|
||||||
83 184 55
|
|
||||||
131 169 11
|
|
||||||
175 45 59
|
|
||||||
69 30 132
|
|
||||||
13 178 31
|
|
||||||
170 75 21
|
|
||||||
5 86 20
|
|
||||||
94 31 143
|
|
||||||
111 56 84
|
|
||||||
110 42 168
|
|
||||||
135 174 184
|
|
||||||
68 41 152
|
|
||||||
167 112 40
|
|
||||||
33 29 97
|
|
||||||
168 175 169
|
|
||||||
186 10 155
|
|
||||||
46 61 32
|
|
||||||
139 55 116
|
|
||||||
137 195 172
|
|
||||||
203 187 58
|
|
||||||
204 17 201
|
|
||||||
45 53 69
|
|
||||||
149 200 71
|
|
||||||
179 114 5
|
|
||||||
47 109 102
|
|
||||||
8 70 22
|
|
||||||
127 145 35
|
|
||||||
4 94 173
|
|
||||||
184 85 46
|
|
||||||
44 186 125
|
|
||||||
163 157 200
|
|
||||||
93 77 26
|
|
||||||
19 12 100
|
|
||||||
61 62 181
|
|
||||||
52 25 15
|
|
||||||
100 105 87
|
|
||||||
30 40 61
|
|
||||||
42 193 115
|
|
||||||
176 46 126
|
|
||||||
136 76 73
|
|
||||||
142 50 190
|
|
||||||
7 183 199
|
|
||||||
147 84 98
|
|
||||||
1 147 52
|
|
||||||
54 33 158
|
|
||||||
99 106 165
|
|
||||||
3 97 166
|
|
||||||
12 159 138
|
|
||||||
195 125 25
|
|
||||||
144 1 85
|
|
||||||
105 32 41
|
|
||||||
104 72 157
|
|
||||||
200 141 105
|
|
||||||
188 103 80
|
|
||||||
38 39 77
|
|
||||||
56 140 178
|
|
||||||
31 165 43
|
|
||||||
133 160 48
|
|
||||||
98 57 150
|
|
||||||
14 110 49
|
|
||||||
132 14 119
|
|
||||||
25 66 86
|
|
||||||
34 132 137
|
|
||||||
108 123 14
|
|
||||||
86 198 114
|
|
||||||
171 44 142
|
|
||||||
95 7 120
|
|
||||||
35 22 76
|
|
||||||
55 133 186
|
|
||||||
82 36 8
|
|
||||||
76 52 54
|
|
||||||
181 28 176
|
|
||||||
90 185 67
|
|
||||||
119 176 112
|
|
||||||
24 82 91
|
|
||||||
78 81 50
|
|
||||||
174 192 146
|
|
||||||
16 188 149
|
|
||||||
162 199 30
|
|
||||||
88 18 81
|
|
||||||
67 107 175
|
|
||||||
197 37 4
|
|
||||||
191 35 122
|
|
||||||
189 203 99
|
|
||||||
81 152 180
|
|
||||||
178 163 121
|
|
||||||
59 63 154
|
|
||||||
17 131 78
|
|
||||||
113 108 63
|
|
||||||
63 137 153
|
|
||||||
143 21 38
|
|
||||||
65 117 194
|
|
||||||
74 67 1
|
|
||||||
60 23 111
|
|
||||||
153 102 134
|
|
||||||
2 74 39
|
|
||||||
53 51 103
|
|
||||||
9 113 51
|
|
||||||
28 92 82
|
|
||||||
194 179 182
|
|
||||||
158 100 92
|
|
||||||
199 13 56
|
|
||||||
118 16 79
|
|
||||||
156 95 36
|
|
||||||
36 2 145
|
|
||||||
126 5 202
|
|
||||||
128 134 44
|
|
||||||
185 138 75
|
|
||||||
114 120 177
|
|
||||||
183 98 179
|
|
||||||
80 15 66
|
|
||||||
115 96 12
|
|
||||||
102 116 60
|
|
||||||
129 182 10
|
|
||||||
202 180 171
|
|
||||||
48 171 68
|
|
||||||
10 162 42
|
|
||||||
148 155 53
|
|
||||||
161 60 136
|
|
||||||
177 204 72
|
|
||||||
123 148 13
|
|
||||||
172 129 196
|
|
||||||
112 68 104
|
|
||||||
39 196 123
|
|
||||||
157 80 204
|
|
||||||
160 158 96
|
|
||||||
138 6 191
|
|
||||||
41 139 151
|
|
||||||
96 111 107
|
|
||||||
122 190 106
|
|
||||||
23 54 192
|
|
||||||
116 143 29
|
|
||||||
49 27 18
|
|
||||||
182 59 163
|
|
||||||
87 99 113
|
|
||||||
70 146 156
|
|
||||||
193 316 97 322 74 365
|
|
||||||
71 368 52 377 15 258
|
|
||||||
191 319 62 260 170 231
|
|
||||||
10 300 58 230 145 354
|
|
||||||
139 279 140 378 35 296
|
|
||||||
105 238 152 399 61 259
|
|
||||||
99 314 157 339 94 264
|
|
||||||
88 298 75 207 33 342
|
|
||||||
143 370 133 208 127 212
|
|
||||||
91 389 94 288 90 386
|
|
||||||
133 253 71 269 126 274
|
|
||||||
8 320 27 305 83 384
|
|
||||||
6 277 67 374 153 393
|
|
||||||
109 332 195 333 64 336
|
|
||||||
119 213 120 383 4 307
|
|
||||||
199 350 139 375 167 257
|
|
||||||
126 360 102 293 9 267
|
|
||||||
17 214 167 352 36 405
|
|
||||||
104 305 86 243 52 224
|
|
||||||
84 211 85 212 160 279
|
|
||||||
54 261 68 363 24 278
|
|
||||||
81 265 45 340 103 298
|
|
||||||
186 403 59 366 7 240
|
|
||||||
134 347 149 228 180 253
|
|
||||||
196 334 43 307 29 321
|
|
||||||
96 272 60 223 150 304
|
|
||||||
1 206 41 405 62 268
|
|
||||||
64 371 192 344 80 208
|
|
||||||
15 260 84 286 85 404
|
|
||||||
162 309 13 276 181 351
|
|
||||||
95 329 107 280 184 277
|
|
||||||
85 256 22 323 76 289
|
|
||||||
167 286 49 317 30 221
|
|
||||||
44 335 187 265 51 219
|
|
||||||
125 340 204 355 88 299
|
|
||||||
58 377 35 342 22 376
|
|
||||||
82 255 83 354 118 215
|
|
||||||
177 327 32 231 115 363
|
|
||||||
66 396 30 327 67 368
|
|
||||||
56 237 48 309 202 285
|
|
||||||
184 400 40 284 154 323
|
|
||||||
190 310 2 282 59 389
|
|
||||||
36 221 1 236 171 329
|
|
||||||
76 302 170 338 120 379
|
|
||||||
183 294 138 275 105 222
|
|
||||||
79 289 50 311 166 301
|
|
||||||
61 297 137 272 129 247
|
|
||||||
132 388 25 255 40 330
|
|
||||||
189 405 14 247 178 332
|
|
||||||
57 240 110 313 161 348
|
|
||||||
175 268 12 369 131 370
|
|
||||||
174 307 200 343 123 316
|
|
||||||
86 369 177 294 54 390
|
|
||||||
197 317 29 403 53 343
|
|
||||||
116 341 74 290 89 273
|
|
||||||
142 328 79 281 21 374
|
|
||||||
63 236 129 331 69 238
|
|
||||||
73 259 118 225 164 292
|
|
||||||
70 359 124 406 163 275
|
|
||||||
130 366 20 391 156 385
|
|
||||||
87 306 136 289 101 309
|
|
||||||
52 223 130 306 47 210
|
|
||||||
22 362 145 359 44 361
|
|
||||||
181 270 99 257 165 229
|
|
||||||
60 364 8 239 196 252
|
|
||||||
114 247 37 334 174 383
|
|
||||||
35 353 160 365 152 345
|
|
||||||
164 284 174 395 137 388
|
|
||||||
29 276 151 205 27 294
|
|
||||||
176 408 115 298 185 261
|
|
||||||
3 208 26 217 141 295
|
|
||||||
40 271 55 324 139 392
|
|
||||||
161 267 54 252 50 312
|
|
||||||
102 365 16 368 136 223
|
|
||||||
13 229 88 278 49 380
|
|
||||||
194 343 183 312 100 340
|
|
||||||
53 217 123 304 134 327
|
|
||||||
171 348 184 253 56 360
|
|
||||||
47 241 42 258 186 375
|
|
||||||
48 383 3 397 26 326
|
|
||||||
51 357 172 348 19 352
|
|
||||||
115 342 69 347 117 371
|
|
||||||
121 273 178 232 77 211
|
|
||||||
11 205 196 315 144 281
|
|
||||||
39 244 96 301 92 322
|
|
||||||
18 337 101 279 192 334
|
|
||||||
163 407 80 251 14 308
|
|
||||||
2 352 87 213 110 230
|
|
||||||
137 215 169 227 157 248
|
|
||||||
49 345 190 245 87 226
|
|
||||||
188 212 104 242 119 347
|
|
||||||
69 227 57 371 109 373
|
|
||||||
32 304 114 233 5 235
|
|
||||||
67 280 171 300 177 255
|
|
||||||
192 339 17 376 122 209
|
|
||||||
150 401 81 384 143 398
|
|
||||||
120 254 108 319 148 286
|
|
||||||
77 331 34 382 91 315
|
|
||||||
43 318 176 407 10 356
|
|
||||||
147 308 188 373 176 305
|
|
||||||
103 218 193 249 112 250
|
|
||||||
19 385 194 367 140 297
|
|
||||||
100 269 95 326 11 369
|
|
||||||
123 324 125 229 16 395
|
|
||||||
202 323 33 308 104 325
|
|
||||||
112 245 23 318 2 402
|
|
||||||
24 257 38 353 116 401
|
|
||||||
101 336 51 361 107 242
|
|
||||||
74 243 186 297 72 271
|
|
||||||
127 282 148 332 135 249
|
|
||||||
30 281 179 401 189 366
|
|
||||||
151 395 166 285 82 346
|
|
||||||
152 361 11 370 138 407
|
|
||||||
31 381 146 296 97 337
|
|
||||||
90 384 92 270 200 310
|
|
||||||
131 404 18 385 102 290
|
|
||||||
107 246 66 364 147 225
|
|
||||||
141 375 134 266 99 269
|
|
||||||
27 346 72 267 172 333
|
|
||||||
129 219 201 381 113 339
|
|
||||||
20 222 156 271 168 358
|
|
||||||
34 402 44 220 68 355
|
|
||||||
168 393 106 336 79 396
|
|
||||||
195 231 135 235 130 207
|
|
||||||
5 251 112 321 71 302
|
|
||||||
42 378 90 219 38 311
|
|
||||||
110 299 173 256 63 228
|
|
||||||
98 379 24 211 66 272
|
|
||||||
165 386 4 394 106 262
|
|
||||||
108 220 189 244 121 243
|
|
||||||
111 274 164 360 37 254
|
|
||||||
153 333 76 335 18 276
|
|
||||||
187 330 119 341 201 214
|
|
||||||
28 230 63 379 95 367
|
|
||||||
94 283 122 241 179 245
|
|
||||||
140 312 113 263 197 391
|
|
||||||
148 291 65 362 39 335
|
|
||||||
113 399 78 380 57 320
|
|
||||||
159 290 126 400 182 260
|
|
||||||
78 248 121 328 1 270
|
|
||||||
203 252 100 325 96 241
|
|
||||||
122 313 128 215 125 338
|
|
||||||
198 363 175 404 86 280
|
|
||||||
45 322 53 221 114 246
|
|
||||||
68 242 28 299 75 377
|
|
||||||
12 210 7 408 45 349
|
|
||||||
9 315 155 316 169 236
|
|
||||||
158 390 73 393 128 263
|
|
||||||
144 295 5 226 41 350
|
|
||||||
117 250 46 206 12 331
|
|
||||||
26 235 109 210 149 400
|
|
||||||
178 258 82 357 194 284
|
|
||||||
62 367 142 237 8 362
|
|
||||||
172 239 165 240 65 359
|
|
||||||
59 264 141 390 108 288
|
|
||||||
21 376 56 218 78 408
|
|
||||||
46 397 116 303 17 324
|
|
||||||
4 373 6 398 190 317
|
|
||||||
16 234 91 320 183 217
|
|
||||||
166 398 168 330 13 239
|
|
||||||
50 391 93 261 43 232
|
|
||||||
38 351 127 389 132 244
|
|
||||||
14 303 39 358 34 406
|
|
||||||
146 249 153 254 28 256
|
|
||||||
149 262 154 329 191 318
|
|
||||||
7 263 19 246 204 319
|
|
||||||
156 285 105 262 199 265
|
|
||||||
33 287 162 224 151 282
|
|
||||||
80 232 197 274 73 287
|
|
||||||
41 278 147 216 111 237
|
|
||||||
93 338 198 388 203 387
|
|
||||||
169 394 161 268 146 291
|
|
||||||
97 226 180 259 158 300
|
|
||||||
83 349 70 283 188 266
|
|
||||||
75 275 47 287 187 353
|
|
||||||
128 311 117 346 155 344
|
|
||||||
25 392 158 264 60 381
|
|
||||||
179 358 181 277 193 328
|
|
||||||
157 296 163 372 42 382
|
|
||||||
155 225 10 387 6 357
|
|
||||||
89 344 143 209 25 306
|
|
||||||
201 406 182 386 142 372
|
|
||||||
160 382 159 314 46 218
|
|
||||||
65 301 111 273 58 283
|
|
||||||
170 380 150 345 20 213
|
|
||||||
72 288 36 302 159 341
|
|
||||||
182 228 61 292 31 205
|
|
||||||
135 326 131 350 32 251
|
|
||||||
154 356 185 222 173 216
|
|
||||||
106 233 191 402 198 313
|
|
||||||
23 355 77 248 93 399
|
|
||||||
138 209 15 349 48 403
|
|
||||||
204 266 202 310 162 206
|
|
||||||
124 372 132 238 133 364
|
|
||||||
185 321 203 291 55 234
|
|
||||||
200 224 103 396 23 394
|
|
||||||
55 354 98 250 84 220
|
|
||||||
136 216 89 337 98 233
|
|
||||||
145 374 9 351 124 314
|
|
||||||
173 325 64 295 70 303
|
|
||||||
180 207 199 234 175 293
|
|
||||||
37 387 144 214 3 378
|
|
||||||
92 292 21 356 81 227
|
|
||||||
118 293 31 392 195 397
|
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -1,148 +0,0 @@
|
|||||||
96 48
|
|
||||||
3 6
|
|
||||||
3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3
|
|
||||||
6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
|
|
||||||
14 28 39
|
|
||||||
2 24 43
|
|
||||||
9 23 33
|
|
||||||
15 27 36
|
|
||||||
12 20 37
|
|
||||||
8 18 47
|
|
||||||
13 21 40
|
|
||||||
3 17 42
|
|
||||||
5 30 44
|
|
||||||
10 19 48
|
|
||||||
7 32 34
|
|
||||||
11 29 45
|
|
||||||
1 25 38
|
|
||||||
6 22 41
|
|
||||||
4 26 46
|
|
||||||
16 31 35
|
|
||||||
1 23 45
|
|
||||||
5 24 48
|
|
||||||
14 19 34
|
|
||||||
7 27 35
|
|
||||||
8 22 46
|
|
||||||
2 28 40
|
|
||||||
10 17 36
|
|
||||||
3 32 33
|
|
||||||
4 29 44
|
|
||||||
11 20 47
|
|
||||||
15 30 39
|
|
||||||
9 18 41
|
|
||||||
13 31 43
|
|
||||||
16 25 42
|
|
||||||
6 21 37
|
|
||||||
12 26 38
|
|
||||||
6 32 40
|
|
||||||
11 26 37
|
|
||||||
14 25 48
|
|
||||||
12 31 36
|
|
||||||
3 19 43
|
|
||||||
15 24 45
|
|
||||||
9 30 35
|
|
||||||
13 29 39
|
|
||||||
1 22 34
|
|
||||||
4 20 41
|
|
||||||
16 21 47
|
|
||||||
10 23 46
|
|
||||||
8 17 44
|
|
||||||
2 27 38
|
|
||||||
7 28 33
|
|
||||||
5 18 42
|
|
||||||
1 28 46
|
|
||||||
14 26 42
|
|
||||||
7 23 47
|
|
||||||
12 19 44
|
|
||||||
3 21 45
|
|
||||||
5 29 33
|
|
||||||
6 27 39
|
|
||||||
10 30 34
|
|
||||||
8 24 38
|
|
||||||
11 22 48
|
|
||||||
13 20 35
|
|
||||||
4 32 37
|
|
||||||
16 17 40
|
|
||||||
2 31 41
|
|
||||||
15 18 43
|
|
||||||
9 25 36
|
|
||||||
8 32 43
|
|
||||||
6 20 33
|
|
||||||
2 22 42
|
|
||||||
13 27 44
|
|
||||||
3 25 39
|
|
||||||
14 29 37
|
|
||||||
9 31 40
|
|
||||||
7 30 41
|
|
||||||
5 23 38
|
|
||||||
16 19 45
|
|
||||||
4 21 48
|
|
||||||
10 28 47
|
|
||||||
15 17 46
|
|
||||||
11 18 34
|
|
||||||
1 26 36
|
|
||||||
12 24 35
|
|
||||||
13 32 41
|
|
||||||
7 29 36
|
|
||||||
14 30 38
|
|
||||||
8 23 42
|
|
||||||
1 18 33
|
|
||||||
11 19 35
|
|
||||||
10 26 44
|
|
||||||
16 20 43
|
|
||||||
5 28 34
|
|
||||||
15 25 47
|
|
||||||
3 31 37
|
|
||||||
2 21 39
|
|
||||||
9 24 46
|
|
||||||
12 22 45
|
|
||||||
4 27 40
|
|
||||||
6 17 48
|
|
||||||
13 17 41 49 79 85
|
|
||||||
2 22 46 62 67 92
|
|
||||||
8 24 37 53 69 91
|
|
||||||
15 25 42 60 75 95
|
|
||||||
9 18 48 54 73 89
|
|
||||||
14 31 33 55 66 96
|
|
||||||
11 20 47 51 72 82
|
|
||||||
6 21 45 57 65 84
|
|
||||||
3 28 39 64 71 93
|
|
||||||
10 23 44 56 76 87
|
|
||||||
12 26 34 58 78 86
|
|
||||||
5 32 36 52 80 94
|
|
||||||
7 29 40 59 68 81
|
|
||||||
1 19 35 50 70 83
|
|
||||||
4 27 38 63 77 90
|
|
||||||
16 30 43 61 74 88
|
|
||||||
8 23 45 61 77 96
|
|
||||||
6 28 48 63 78 85
|
|
||||||
10 19 37 52 74 86
|
|
||||||
5 26 42 59 66 88
|
|
||||||
7 31 43 53 75 92
|
|
||||||
14 21 41 58 67 94
|
|
||||||
3 17 44 51 73 84
|
|
||||||
2 18 38 57 80 93
|
|
||||||
13 30 35 64 69 90
|
|
||||||
15 32 34 50 79 87
|
|
||||||
4 20 46 55 68 95
|
|
||||||
1 22 47 49 76 89
|
|
||||||
12 25 40 54 70 82
|
|
||||||
9 27 39 56 72 83
|
|
||||||
16 29 36 62 71 91
|
|
||||||
11 24 33 60 65 81
|
|
||||||
3 24 47 54 66 85
|
|
||||||
11 19 41 56 78 89
|
|
||||||
16 20 39 59 80 86
|
|
||||||
4 23 36 64 79 82
|
|
||||||
5 31 34 60 70 91
|
|
||||||
13 32 46 57 73 83
|
|
||||||
1 27 40 55 69 92
|
|
||||||
7 22 33 61 71 95
|
|
||||||
14 28 42 62 72 81
|
|
||||||
8 30 48 50 67 84
|
|
||||||
2 29 37 63 65 88
|
|
||||||
9 25 45 52 68 87
|
|
||||||
12 17 38 53 74 94
|
|
||||||
15 21 44 49 77 93
|
|
||||||
6 26 43 51 76 90
|
|
||||||
10 18 35 58 75 96
|
|
||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,55 +0,0 @@
|
|||||||
31 20
|
|
||||||
6 6
|
|
||||||
1 1 2 3 4 4 4 4 4 5 5 6 6 6 6 6 6 6 6 6 5 5 4 3 2 2 2 2 2 1 1
|
|
||||||
6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
|
|
||||||
1 0 0 0 0 0
|
|
||||||
2 0 0 0 0 0
|
|
||||||
1 3 0 0 0 0
|
|
||||||
1 2 4 0 0 0
|
|
||||||
1 2 3 5 0 0
|
|
||||||
2 3 4 6 0 0
|
|
||||||
3 4 5 7 0 0
|
|
||||||
4 5 6 8 0 0
|
|
||||||
5 6 7 9 0 0
|
|
||||||
1 6 7 8 10 0
|
|
||||||
2 7 8 9 11 0
|
|
||||||
1 3 8 9 10 12
|
|
||||||
2 4 9 10 11 13
|
|
||||||
3 5 10 11 12 14
|
|
||||||
4 6 11 12 13 15
|
|
||||||
5 7 12 13 14 16
|
|
||||||
6 8 13 14 15 17
|
|
||||||
7 9 14 15 16 18
|
|
||||||
8 10 15 16 17 19
|
|
||||||
9 11 16 17 18 20
|
|
||||||
10 12 17 18 19 0
|
|
||||||
11 13 18 19 20 0
|
|
||||||
12 14 19 20 0 0
|
|
||||||
13 15 20 0 0 0
|
|
||||||
14 16 0 0 0 0
|
|
||||||
15 17 0 0 0 0
|
|
||||||
16 18 0 0 0 0
|
|
||||||
17 19 0 0 0 0
|
|
||||||
18 20 0 0 0 0
|
|
||||||
19 0 0 0 0 0
|
|
||||||
20 0 0 0 0 0
|
|
||||||
1 3 4 5 10 12
|
|
||||||
2 4 5 6 11 13
|
|
||||||
3 5 6 7 12 14
|
|
||||||
4 6 7 8 13 15
|
|
||||||
5 7 8 9 14 16
|
|
||||||
6 8 9 10 15 17
|
|
||||||
7 9 10 11 16 18
|
|
||||||
8 10 11 12 17 19
|
|
||||||
9 11 12 13 18 20
|
|
||||||
10 12 13 14 19 21
|
|
||||||
11 13 14 15 20 22
|
|
||||||
12 14 15 16 21 23
|
|
||||||
13 15 16 17 22 24
|
|
||||||
14 16 17 18 23 25
|
|
||||||
15 17 18 19 24 26
|
|
||||||
16 18 19 20 25 27
|
|
||||||
17 19 20 21 26 28
|
|
||||||
18 20 21 22 27 29
|
|
||||||
19 21 22 23 28 30
|
|
||||||
20 22 23 24 29 31
|
|
||||||
@@ -1,40 +0,0 @@
|
|||||||
31 5
|
|
||||||
5 16
|
|
||||||
1 1 1 2 2 2 3 3 2 3 3 3 4 5 4 3 2 2 2 2 3 4 4 3 4 3 3 2 2 1 1
|
|
||||||
16 16 16 16 16
|
|
||||||
1 0 0 0 0
|
|
||||||
2 0 0 0 0
|
|
||||||
3 0 0 0 0
|
|
||||||
1 4 0 0 0
|
|
||||||
2 5 0 0 0
|
|
||||||
1 3 0 0 0
|
|
||||||
1 2 4 0 0
|
|
||||||
2 3 5 0 0
|
|
||||||
3 4 0 0 0
|
|
||||||
1 4 5 0 0
|
|
||||||
1 2 5 0 0
|
|
||||||
1 2 3 0 0
|
|
||||||
1 2 3 4 0
|
|
||||||
1 2 3 4 5
|
|
||||||
2 3 4 5 0
|
|
||||||
3 4 5 0 0
|
|
||||||
4 5 0 0 0
|
|
||||||
1 5 0 0 0
|
|
||||||
1 2 0 0 0
|
|
||||||
2 3 0 0 0
|
|
||||||
1 3 4 0 0
|
|
||||||
1 2 4 5 0
|
|
||||||
1 2 3 5 0
|
|
||||||
2 3 4 0 0
|
|
||||||
1 3 4 5 0
|
|
||||||
2 4 5 0 0
|
|
||||||
1 3 5 0 0
|
|
||||||
2 4 0 0 0
|
|
||||||
3 5 0 0 0
|
|
||||||
4 0 0 0 0
|
|
||||||
5 0 0 0 0
|
|
||||||
1 4 6 7 10 11 12 13 14 18 19 21 22 23 25 27
|
|
||||||
2 5 7 8 11 12 13 14 15 19 20 22 23 24 26 28
|
|
||||||
3 6 8 9 12 13 14 15 16 20 21 23 24 25 27 29
|
|
||||||
4 7 9 10 13 14 15 16 17 21 22 24 25 26 28 30
|
|
||||||
5 8 10 11 14 15 16 17 18 22 23 25 26 27 29 31
|
|
||||||
@@ -1,14 +0,0 @@
|
|||||||
7 3
|
|
||||||
3 4
|
|
||||||
1 1 2 2 3 2 1
|
|
||||||
4 4 4
|
|
||||||
1 0 0
|
|
||||||
2 0 0
|
|
||||||
1 3 0
|
|
||||||
1 2 0
|
|
||||||
1 2 3
|
|
||||||
2 3 0
|
|
||||||
3 0 0
|
|
||||||
1 3 4 5
|
|
||||||
2 4 5 6
|
|
||||||
3 5 6 7
|
|
||||||
@@ -1,760 +0,0 @@
|
|||||||
504 252
|
|
||||||
3 7
|
|
||||||
3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3 3
|
|
||||||
6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 7 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 7 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 5 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 5 6 6 6 5 6 6 6 6 6 6 6 6 6 6 7 6 6 6 6 6 6
|
|
||||||
1 70 198
|
|
||||||
2 11 210
|
|
||||||
3 86 197
|
|
||||||
4 145 173
|
|
||||||
5 180 196
|
|
||||||
6 89 223
|
|
||||||
7 144 247
|
|
||||||
8 99 119
|
|
||||||
9 111 184
|
|
||||||
10 20 183
|
|
||||||
12 206 218
|
|
||||||
13 51 229
|
|
||||||
14 16 234
|
|
||||||
15 160 190
|
|
||||||
17 150 182
|
|
||||||
18 71 143
|
|
||||||
19 188 238
|
|
||||||
21 55 203
|
|
||||||
22 25 103
|
|
||||||
23 54 202
|
|
||||||
24 49 60
|
|
||||||
26 57 74
|
|
||||||
27 107 115
|
|
||||||
28 101 251
|
|
||||||
29 94 104
|
|
||||||
30 158 225
|
|
||||||
31 129 217
|
|
||||||
32 40 211
|
|
||||||
33 37 154
|
|
||||||
34 148 162
|
|
||||||
35 232 246
|
|
||||||
36 65 92
|
|
||||||
38 39 42
|
|
||||||
41 113 237
|
|
||||||
43 168 200
|
|
||||||
44 125 133
|
|
||||||
45 215 248
|
|
||||||
46 98 136
|
|
||||||
47 63 169
|
|
||||||
48 80 226
|
|
||||||
50 97 166
|
|
||||||
52 67 114
|
|
||||||
53 58 176
|
|
||||||
56 134 147
|
|
||||||
59 138 163
|
|
||||||
61 130 201
|
|
||||||
62 66 87
|
|
||||||
64 171 186
|
|
||||||
68 161 170
|
|
||||||
69 109 174
|
|
||||||
72 93 243
|
|
||||||
73 126 191
|
|
||||||
75 112 227
|
|
||||||
76 157 221
|
|
||||||
77 187 205
|
|
||||||
78 90 233
|
|
||||||
79 131 153
|
|
||||||
81 117 135
|
|
||||||
82 121 172
|
|
||||||
83 156 204
|
|
||||||
84 175 192
|
|
||||||
85 95 132
|
|
||||||
88 128 242
|
|
||||||
91 189 214
|
|
||||||
96 159 167
|
|
||||||
100 219 235
|
|
||||||
102 199 245
|
|
||||||
105 152 241
|
|
||||||
106 123 236
|
|
||||||
108 140 239
|
|
||||||
110 146 178
|
|
||||||
116 127 250
|
|
||||||
118 185 249
|
|
||||||
120 155 209
|
|
||||||
122 208 240
|
|
||||||
124 212 244
|
|
||||||
137 139 228
|
|
||||||
141 164 195
|
|
||||||
142 179 220
|
|
||||||
149 151 194
|
|
||||||
165 216 230
|
|
||||||
177 193 207
|
|
||||||
181 224 252
|
|
||||||
213 222 231
|
|
||||||
1 169 240
|
|
||||||
2 112 185
|
|
||||||
3 168 183
|
|
||||||
4 11 132
|
|
||||||
5 6 232
|
|
||||||
7 124 189
|
|
||||||
8 64 239
|
|
||||||
9 51 198
|
|
||||||
10 15 163
|
|
||||||
12 52 195
|
|
||||||
13 50 58
|
|
||||||
14 44 207
|
|
||||||
16 49 148
|
|
||||||
17 18 60
|
|
||||||
19 79 135
|
|
||||||
20 41 89
|
|
||||||
21 125 139
|
|
||||||
22 70 170
|
|
||||||
23 53 66
|
|
||||||
24 120 201
|
|
||||||
25 92 250
|
|
||||||
26 218 230
|
|
||||||
27 103 145
|
|
||||||
28 128 197
|
|
||||||
29 173 224
|
|
||||||
30 212 251
|
|
||||||
31 39 75
|
|
||||||
32 127 225
|
|
||||||
33 200 204
|
|
||||||
34 74 194
|
|
||||||
35 143 233
|
|
||||||
36 178 188
|
|
||||||
37 109 231
|
|
||||||
38 72 219
|
|
||||||
40 134 186
|
|
||||||
42 175 179
|
|
||||||
43 77 106
|
|
||||||
45 94 126
|
|
||||||
46 172 206
|
|
||||||
47 105 157
|
|
||||||
48 159 211
|
|
||||||
54 102 121
|
|
||||||
55 220 222
|
|
||||||
56 93 149
|
|
||||||
57 76 123
|
|
||||||
59 62 215
|
|
||||||
61 81 87
|
|
||||||
63 192 247
|
|
||||||
65 90 174
|
|
||||||
67 85 99
|
|
||||||
68 193 237
|
|
||||||
69 98 249
|
|
||||||
71 91 191
|
|
||||||
73 171 203
|
|
||||||
78 235 242
|
|
||||||
80 180 199
|
|
||||||
82 144 153
|
|
||||||
83 129 166
|
|
||||||
84 96 190
|
|
||||||
86 95 155
|
|
||||||
88 216 228
|
|
||||||
97 110 140
|
|
||||||
100 184 234
|
|
||||||
101 176 182
|
|
||||||
104 122 187
|
|
||||||
107 202 243
|
|
||||||
108 223 241
|
|
||||||
111 164 167
|
|
||||||
113 136 147
|
|
||||||
114 156 177
|
|
||||||
115 160 165
|
|
||||||
116 227 236
|
|
||||||
117 137 196
|
|
||||||
118 130 244
|
|
||||||
119 131 205
|
|
||||||
133 146 210
|
|
||||||
138 162 213
|
|
||||||
141 150 238
|
|
||||||
142 181 229
|
|
||||||
151 208 246
|
|
||||||
152 154 158
|
|
||||||
161 209 245
|
|
||||||
214 217 226
|
|
||||||
207 221 248
|
|
||||||
20 238 252
|
|
||||||
1 228 249
|
|
||||||
2 143 163
|
|
||||||
3 55 82
|
|
||||||
4 48 176
|
|
||||||
5 38 52
|
|
||||||
6 7 103
|
|
||||||
8 115 148
|
|
||||||
9 33 191
|
|
||||||
10 219 225
|
|
||||||
11 26 175
|
|
||||||
12 104 201
|
|
||||||
13 56 120
|
|
||||||
14 98 226
|
|
||||||
15 157 245
|
|
||||||
16 19 227
|
|
||||||
17 63 156
|
|
||||||
18 123 140
|
|
||||||
21 62 250
|
|
||||||
22 28 57
|
|
||||||
23 37 122
|
|
||||||
24 139 152
|
|
||||||
25 164 166
|
|
||||||
27 136 158
|
|
||||||
29 78 83
|
|
||||||
30 146 205
|
|
||||||
31 86 208
|
|
||||||
32 68 246
|
|
||||||
34 53 89
|
|
||||||
35 119 142
|
|
||||||
36 91 93
|
|
||||||
39 45 182
|
|
||||||
40 54 185
|
|
||||||
41 85 126
|
|
||||||
42 43 186
|
|
||||||
44 181 202
|
|
||||||
46 84 97
|
|
||||||
47 134 135
|
|
||||||
49 90 168
|
|
||||||
50 73 216
|
|
||||||
51 75 206
|
|
||||||
58 76 153
|
|
||||||
59 151 204
|
|
||||||
60 128 190
|
|
||||||
61 159 231
|
|
||||||
64 70 214
|
|
||||||
65 171 221
|
|
||||||
66 192 233
|
|
||||||
67 69 101
|
|
||||||
71 117 193
|
|
||||||
72 81 108
|
|
||||||
74 118 154
|
|
||||||
77 88 102
|
|
||||||
79 209 215
|
|
||||||
80 107 110
|
|
||||||
87 165 189
|
|
||||||
92 95 160
|
|
||||||
94 127 197
|
|
||||||
96 131 223
|
|
||||||
99 124 242
|
|
||||||
100 132 222
|
|
||||||
105 224 230
|
|
||||||
106 213 237
|
|
||||||
109 199 247
|
|
||||||
111 173 212
|
|
||||||
112 113 235
|
|
||||||
114 178 229
|
|
||||||
116 130 180
|
|
||||||
121 138 150
|
|
||||||
125 170 200
|
|
||||||
129 220 244
|
|
||||||
133 167 236
|
|
||||||
137 211 252
|
|
||||||
141 155 239
|
|
||||||
144 198 243
|
|
||||||
145 174 194
|
|
||||||
147 195 248
|
|
||||||
149 172 210
|
|
||||||
161 218 234
|
|
||||||
162 196 251
|
|
||||||
110 169 183
|
|
||||||
3 177 241
|
|
||||||
113 179 240
|
|
||||||
47 184 232
|
|
||||||
98 187 203
|
|
||||||
188 216 246
|
|
||||||
192 217 225
|
|
||||||
1 89 127
|
|
||||||
2 94 229
|
|
||||||
4 88 108
|
|
||||||
5 44 128
|
|
||||||
6 203 211
|
|
||||||
7 49 122
|
|
||||||
8 61 172
|
|
||||||
9 40 160
|
|
||||||
10 22 201
|
|
||||||
11 191 238
|
|
||||||
12 19 107
|
|
||||||
13 109 170
|
|
||||||
14 163 247
|
|
||||||
15 188 220
|
|
||||||
16 166 182
|
|
||||||
17 23 136
|
|
||||||
18 100 130
|
|
||||||
20 56 167
|
|
||||||
21 111 140
|
|
||||||
24 217 237
|
|
||||||
25 102 193
|
|
||||||
26 41 187
|
|
||||||
27 43 209
|
|
||||||
28 144 147
|
|
||||||
29 96 121
|
|
||||||
30 85 221
|
|
||||||
31 114 131
|
|
||||||
32 153 239
|
|
||||||
33 119 207
|
|
||||||
34 39 125
|
|
||||||
35 116 176
|
|
||||||
36 162 224
|
|
||||||
37 38 165
|
|
||||||
42 91 156
|
|
||||||
45 70 233
|
|
||||||
46 186 196
|
|
||||||
48 200 230
|
|
||||||
50 74 243
|
|
||||||
51 77 244
|
|
||||||
52 66 123
|
|
||||||
53 117 242
|
|
||||||
54 57 99
|
|
||||||
55 120 204
|
|
||||||
58 175 212
|
|
||||||
59 65 118
|
|
||||||
60 62 178
|
|
||||||
63 95 227
|
|
||||||
64 190 252
|
|
||||||
67 135 210
|
|
||||||
68 87 173
|
|
||||||
69 181 208
|
|
||||||
71 101 152
|
|
||||||
72 98 213
|
|
||||||
73 236 245
|
|
||||||
75 103 231
|
|
||||||
76 142 228
|
|
||||||
78 80 149
|
|
||||||
79 139 197
|
|
||||||
81 168 185
|
|
||||||
82 145 214
|
|
||||||
83 184 205
|
|
||||||
84 93 141
|
|
||||||
86 189 234
|
|
||||||
90 164 179
|
|
||||||
92 240 241
|
|
||||||
97 151 157
|
|
||||||
104 134 177
|
|
||||||
105 106 174
|
|
||||||
112 161 194
|
|
||||||
115 129 143
|
|
||||||
124 150 250
|
|
||||||
126 159 202
|
|
||||||
132 148 198
|
|
||||||
133 155 235
|
|
||||||
137 195 222
|
|
||||||
138 158 232
|
|
||||||
146 218 249
|
|
||||||
154 195 226
|
|
||||||
169 206 215
|
|
||||||
171 173 219
|
|
||||||
11 180 248
|
|
||||||
161 183 251
|
|
||||||
91 199 223
|
|
||||||
1 106 166
|
|
||||||
2 25 153
|
|
||||||
3 18 34
|
|
||||||
4 52 183
|
|
||||||
5 51 90
|
|
||||||
6 95 172
|
|
||||||
7 133 186
|
|
||||||
8 113 178
|
|
||||||
9 116 136
|
|
||||||
10 83 202
|
|
||||||
12 32 242
|
|
||||||
13 207 211
|
|
||||||
14 89 244
|
|
||||||
15 75 108
|
|
||||||
16 55 158
|
|
||||||
17 79 174
|
|
||||||
19 57 240
|
|
||||||
20 87 152
|
|
||||||
21 246 247
|
|
||||||
22 73 114
|
|
||||||
23 149 228
|
|
||||||
24 35 171
|
|
||||||
26 44 81
|
|
||||||
27 58 100
|
|
||||||
28 42 159
|
|
||||||
29 101 239
|
|
||||||
30 134 181
|
|
||||||
31 54 105
|
|
||||||
33 84 135
|
|
||||||
36 37 209
|
|
||||||
38 157 250
|
|
||||||
39 120 249
|
|
||||||
40 110 213
|
|
||||||
41 47 82
|
|
||||||
43 99 163
|
|
||||||
45 93 184
|
|
||||||
46 94 165
|
|
||||||
48 122 138
|
|
||||||
49 67 127
|
|
||||||
50 223 233
|
|
||||||
53 160 248
|
|
||||||
56 103 230
|
|
||||||
59 214 235
|
|
||||||
60 199 212
|
|
||||||
61 182 245
|
|
||||||
62 104 132
|
|
||||||
48 63 220
|
|
||||||
64 193 227
|
|
||||||
65 88 234
|
|
||||||
66 112 205
|
|
||||||
68 84 148
|
|
||||||
69 115 167
|
|
||||||
70 210 220
|
|
||||||
71 151 231
|
|
||||||
72 129 252
|
|
||||||
74 134 150
|
|
||||||
76 148 156
|
|
||||||
19 77 219
|
|
||||||
78 188 207
|
|
||||||
80 92 237
|
|
||||||
85 218 226
|
|
||||||
86 123 180
|
|
||||||
96 117 118
|
|
||||||
97 177 179
|
|
||||||
102 125 147
|
|
||||||
107 130 221
|
|
||||||
109 217 238
|
|
||||||
111 201 215
|
|
||||||
119 145 196
|
|
||||||
121 142 200
|
|
||||||
124 204 225
|
|
||||||
126 168 175
|
|
||||||
128 169 191
|
|
||||||
131 222 251
|
|
||||||
137 189 192
|
|
||||||
139 187 243
|
|
||||||
140 154 208
|
|
||||||
141 143 144
|
|
||||||
146 162 197
|
|
||||||
155 213 216
|
|
||||||
164 172 225
|
|
||||||
170 232 241
|
|
||||||
176 206 224
|
|
||||||
91 185 236
|
|
||||||
190 194 203
|
|
||||||
198 230 250
|
|
||||||
55 192 229
|
|
||||||
1 33 173
|
|
||||||
2 36 74
|
|
||||||
3 9 62
|
|
||||||
4 113 249
|
|
||||||
5 100 239
|
|
||||||
6 76 77
|
|
||||||
7 45 112
|
|
||||||
8 23 50
|
|
||||||
10 13 117
|
|
||||||
11 158 193
|
|
||||||
12 168 223
|
|
||||||
14 58 105
|
|
||||||
15 139 191
|
|
||||||
16 40 125
|
|
||||||
17 218 233
|
|
||||||
18 78 186
|
|
||||||
20 54 65
|
|
||||||
21 142 183
|
|
||||||
22 46 244
|
|
||||||
24 97 202
|
|
||||||
25 98 242
|
|
||||||
26 140 149
|
|
||||||
27 35 63
|
|
||||||
28 184 206
|
|
||||||
29 160 247
|
|
||||||
30 79 108
|
|
||||||
31 171 215
|
|
||||||
32 37 181
|
|
||||||
34 164 199
|
|
||||||
38 57 229
|
|
||||||
39 83 135
|
|
||||||
41 150 209
|
|
||||||
42 169 246
|
|
||||||
43 167 221
|
|
||||||
44 92 129
|
|
||||||
47 94 211
|
|
||||||
49 216 241
|
|
||||||
51 152 185
|
|
||||||
52 153 227
|
|
||||||
53 151 201
|
|
||||||
56 86 178
|
|
||||||
59 115 175
|
|
||||||
60 163 243
|
|
||||||
61 93 217
|
|
||||||
64 109 123
|
|
||||||
66 155 200
|
|
||||||
67 82 106
|
|
||||||
68 180 182
|
|
||||||
69 88 166
|
|
||||||
70 110 120
|
|
||||||
71 205 240
|
|
||||||
72 130 161
|
|
||||||
73 75 196
|
|
||||||
80 99 133
|
|
||||||
35 81 104
|
|
||||||
85 224 246
|
|
||||||
87 179 190
|
|
||||||
89 174 189
|
|
||||||
90 131 147
|
|
||||||
95 212 214
|
|
||||||
96 127 144
|
|
||||||
101 165 187
|
|
||||||
102 210 252
|
|
||||||
103 177 208
|
|
||||||
107 114 122
|
|
||||||
111 118 197
|
|
||||||
116 159 170
|
|
||||||
119 136 238
|
|
||||||
121 143 234
|
|
||||||
124 203 237
|
|
||||||
126 204 232
|
|
||||||
128 222 245
|
|
||||||
132 154 228
|
|
||||||
137 146 219
|
|
||||||
138 145 248
|
|
||||||
105 141 156
|
|
||||||
157 226 251
|
|
||||||
162 195 236
|
|
||||||
176 188 198
|
|
||||||
1 85 170 256 339 426 0
|
|
||||||
2 86 171 257 340 427 0
|
|
||||||
3 87 172 250 341 428 0
|
|
||||||
4 88 173 258 342 429 0
|
|
||||||
5 89 174 259 343 430 0
|
|
||||||
6 89 175 260 344 431 0
|
|
||||||
7 90 175 261 345 432 0
|
|
||||||
8 91 176 262 346 433 0
|
|
||||||
9 92 177 263 347 428 0
|
|
||||||
10 93 178 264 348 434 0
|
|
||||||
2 88 179 265 336 435 0
|
|
||||||
11 94 180 266 349 436 0
|
|
||||||
12 95 181 267 350 434 0
|
|
||||||
13 96 182 268 351 437 0
|
|
||||||
14 93 183 269 352 438 0
|
|
||||||
13 97 184 270 353 439 0
|
|
||||||
15 98 185 271 354 440 0
|
|
||||||
16 98 186 272 341 441 0
|
|
||||||
17 99 184 266 355 396 0
|
|
||||||
10 100 169 273 356 442 0
|
|
||||||
18 101 187 274 357 443 0
|
|
||||||
19 102 188 264 358 444 0
|
|
||||||
20 103 189 271 359 433 0
|
|
||||||
21 104 190 275 360 445 0
|
|
||||||
19 105 191 276 340 446 0
|
|
||||||
22 106 179 277 361 447 0
|
|
||||||
23 107 192 278 362 448 0
|
|
||||||
24 108 188 279 363 449 0
|
|
||||||
25 109 193 280 364 450 0
|
|
||||||
26 110 194 281 365 451 0
|
|
||||||
27 111 195 282 366 452 0
|
|
||||||
28 112 196 283 349 453 0
|
|
||||||
29 113 177 284 367 426 0
|
|
||||||
30 114 197 285 341 454 0
|
|
||||||
31 115 198 286 360 448 480
|
|
||||||
32 116 199 287 368 427 0
|
|
||||||
29 117 189 288 368 453 0
|
|
||||||
33 118 174 288 369 455 0
|
|
||||||
33 111 200 285 370 456 0
|
|
||||||
28 119 201 263 371 439 0
|
|
||||||
34 100 202 277 372 457 0
|
|
||||||
33 120 203 289 363 458 0
|
|
||||||
35 121 203 278 373 459 0
|
|
||||||
36 96 204 259 361 460 0
|
|
||||||
37 122 200 290 374 432 0
|
|
||||||
38 123 205 291 375 444 0
|
|
||||||
39 124 206 252 372 461 0
|
|
||||||
40 125 173 292 376 385 0
|
|
||||||
21 97 207 261 377 462 0
|
|
||||||
41 95 208 293 378 433 0
|
|
||||||
12 92 209 294 343 463 0
|
|
||||||
42 94 174 295 342 464 0
|
|
||||||
43 103 197 296 379 465 0
|
|
||||||
20 126 201 297 366 442 0
|
|
||||||
18 127 172 298 353 425 0
|
|
||||||
44 128 181 273 380 466 0
|
|
||||||
22 129 188 297 355 455 0
|
|
||||||
43 95 210 299 362 437 0
|
|
||||||
45 130 211 300 381 467 0
|
|
||||||
21 98 212 301 382 468 0
|
|
||||||
46 131 213 262 383 469 0
|
|
||||||
47 130 187 301 384 428 0
|
|
||||||
39 132 185 302 385 448 0
|
|
||||||
48 91 214 303 386 470 0
|
|
||||||
32 133 215 300 387 442 0
|
|
||||||
47 103 216 295 388 471 0
|
|
||||||
42 134 217 304 377 472 0
|
|
||||||
49 135 196 305 389 473 0
|
|
||||||
50 136 217 306 390 474 0
|
|
||||||
1 102 214 290 391 475 0
|
|
||||||
16 137 218 307 392 476 0
|
|
||||||
51 118 219 308 393 477 0
|
|
||||||
52 138 208 309 358 478 0
|
|
||||||
22 114 220 293 394 427 0
|
|
||||||
53 111 209 310 352 478 0
|
|
||||||
54 129 210 311 395 431 0
|
|
||||||
55 121 221 294 396 431 0
|
|
||||||
56 139 193 312 397 441 0
|
|
||||||
57 99 222 313 354 451 0
|
|
||||||
40 140 223 312 398 479 0
|
|
||||||
58 131 219 314 361 480 0
|
|
||||||
59 141 172 315 372 472 0
|
|
||||||
60 142 193 316 348 456 0
|
|
||||||
61 143 205 317 367 389 0
|
|
||||||
62 134 202 281 399 481 0
|
|
||||||
3 144 195 318 400 466 0
|
|
||||||
47 131 224 305 356 482 0
|
|
||||||
63 145 221 258 387 474 0
|
|
||||||
6 100 197 256 351 483 0
|
|
||||||
56 133 207 319 343 484 0
|
|
||||||
64 137 199 289 338 422 0
|
|
||||||
32 105 225 320 398 460 0
|
|
||||||
51 128 199 317 374 469 0
|
|
||||||
25 122 226 257 375 461 0
|
|
||||||
62 144 225 302 344 485 0
|
|
||||||
65 143 227 280 401 486 0
|
|
||||||
41 146 205 321 402 445 0
|
|
||||||
38 136 182 253 308 446 0
|
|
||||||
8 134 228 297 373 479 0
|
|
||||||
66 147 229 272 362 430 0
|
|
||||||
24 148 217 307 364 487 0
|
|
||||||
67 126 221 276 403 488 0
|
|
||||||
19 107 175 310 380 489 0
|
|
||||||
25 149 180 322 384 480 0
|
|
||||||
68 124 230 323 366 437 501
|
|
||||||
69 121 231 323 339 472 0
|
|
||||||
23 150 223 266 404 490 0
|
|
||||||
70 151 219 258 352 451 0
|
|
||||||
50 117 232 267 405 470 0
|
|
||||||
71 146 223 249 371 475 0
|
|
||||||
9 152 233 274 406 491 0
|
|
||||||
53 86 234 324 388 432 0
|
|
||||||
34 153 234 251 346 429 0
|
|
||||||
42 154 235 282 358 490 0
|
|
||||||
23 155 176 325 390 467 0
|
|
||||||
72 156 236 286 347 492 0
|
|
||||||
58 157 218 296 401 434 0
|
|
||||||
73 158 220 300 401 491 0
|
|
||||||
8 159 198 284 407 493 0
|
|
||||||
74 104 181 298 370 475 0
|
|
||||||
59 126 237 280 408 494 0
|
|
||||||
75 149 189 261 376 490 0
|
|
||||||
69 129 186 295 400 470 0
|
|
||||||
76 90 228 326 409 495 0
|
|
||||||
36 101 238 285 403 439 0
|
|
||||||
52 122 202 327 410 496 0
|
|
||||||
72 112 226 256 377 486 0
|
|
||||||
63 108 212 259 411 497 0
|
|
||||||
27 142 239 325 393 460 0
|
|
||||||
46 158 236 272 404 477 0
|
|
||||||
57 159 227 282 412 484 0
|
|
||||||
62 88 229 328 384 498 0
|
|
||||||
36 160 240 329 345 479 0
|
|
||||||
44 119 206 322 365 394 0
|
|
||||||
58 99 206 304 367 456 0
|
|
||||||
38 153 192 271 347 493 0
|
|
||||||
77 157 241 330 413 499 0
|
|
||||||
45 161 237 331 376 500 0
|
|
||||||
77 101 190 313 414 438 0
|
|
||||||
70 146 186 274 415 447 0
|
|
||||||
78 162 242 317 416 501 0
|
|
||||||
79 163 198 311 408 443 0
|
|
||||||
16 115 171 325 416 494 0
|
|
||||||
7 141 243 279 416 486 0
|
|
||||||
4 107 244 315 407 500 0
|
|
||||||
71 160 194 332 417 499 0
|
|
||||||
44 153 245 279 403 484 0
|
|
||||||
30 97 176 328 389 395 0
|
|
||||||
80 128 246 312 359 447 0
|
|
||||||
15 162 237 326 394 457 0
|
|
||||||
80 164 211 321 392 465 0
|
|
||||||
68 165 190 307 356 463 0
|
|
||||||
57 141 210 283 340 464 0
|
|
||||||
29 165 220 333 415 498 0
|
|
||||||
74 144 242 329 418 471 0
|
|
||||||
60 154 185 289 395 501 0
|
|
||||||
54 124 183 321 369 502 0
|
|
||||||
26 165 192 331 353 435 0
|
|
||||||
65 125 213 327 363 492 0
|
|
||||||
14 155 225 263 379 450 0
|
|
||||||
49 166 247 324 337 477 0
|
|
||||||
30 161 248 287 417 503 0
|
|
||||||
45 93 171 268 373 468 0
|
|
||||||
78 152 191 319 419 454 0
|
|
||||||
81 155 224 288 375 487 0
|
|
||||||
41 142 191 270 339 474 0
|
|
||||||
65 152 240 273 390 459 0
|
|
||||||
35 87 207 314 410 436 0
|
|
||||||
39 85 249 334 411 458 0
|
|
||||||
49 102 238 267 420 492 0
|
|
||||||
48 138 215 335 360 452 0
|
|
||||||
59 123 246 262 344 419 0
|
|
||||||
4 109 233 305 335 426 0
|
|
||||||
50 133 244 323 354 483 0
|
|
||||||
61 120 179 299 410 467 0
|
|
||||||
43 148 173 286 421 504 0
|
|
||||||
82 154 250 322 402 489 0
|
|
||||||
71 116 235 301 346 466 0
|
|
||||||
79 120 251 319 402 482 0
|
|
||||||
5 140 236 336 400 473 0
|
|
||||||
83 163 204 306 365 453 0
|
|
||||||
15 148 200 270 383 473 0
|
|
||||||
10 87 249 337 342 443 0
|
|
||||||
9 147 252 316 374 449 0
|
|
||||||
73 86 201 314 422 463 0
|
|
||||||
48 119 203 291 345 441 0
|
|
||||||
55 149 253 277 414 487 0
|
|
||||||
17 116 254 269 397 504 0
|
|
||||||
64 90 224 318 413 483 0
|
|
||||||
14 143 212 303 423 482 0
|
|
||||||
52 137 177 265 411 438 0
|
|
||||||
61 132 216 255 413 425 0
|
|
||||||
82 135 218 276 386 435 0
|
|
||||||
80 114 244 324 423 0 0
|
|
||||||
78 94 245 330 333 503 0
|
|
||||||
5 157 248 291 407 478 0
|
|
||||||
3 108 226 313 417 491 0
|
|
||||||
1 92 243 328 424 504 0
|
|
||||||
67 140 232 338 382 454 0
|
|
||||||
35 113 238 292 408 471 0
|
|
||||||
46 104 180 264 406 465 0
|
|
||||||
20 150 204 327 348 445 0
|
|
||||||
18 138 253 260 423 495 0
|
|
||||||
60 113 211 298 409 496 0
|
|
||||||
55 159 194 316 388 476 0
|
|
||||||
11 123 209 334 421 449 0
|
|
||||||
82 96 168 284 350 397 0
|
|
||||||
75 164 195 306 415 489 0
|
|
||||||
74 166 222 278 368 457 0
|
|
||||||
2 160 246 304 391 488 0
|
|
||||||
28 125 241 260 350 461 0
|
|
||||||
76 110 233 299 382 485 0
|
|
||||||
84 161 231 308 371 418 0
|
|
||||||
64 167 214 315 381 485 0
|
|
||||||
37 130 222 334 406 452 0
|
|
||||||
81 145 208 254 418 462 0
|
|
||||||
27 167 255 275 405 469 0
|
|
||||||
11 106 247 332 399 440 0
|
|
||||||
66 118 178 335 396 499 0
|
|
||||||
79 127 239 269 385 391 0
|
|
||||||
54 168 215 281 404 459 0
|
|
||||||
84 127 229 330 412 497 0
|
|
||||||
6 151 227 338 378 436 0
|
|
||||||
83 109 230 287 421 481 0
|
|
||||||
26 112 178 255 409 419 0
|
|
||||||
40 167 182 333 399 502 0
|
|
||||||
53 156 184 302 386 464 0
|
|
||||||
77 145 170 311 359 498 0
|
|
||||||
12 163 235 257 425 455 0
|
|
||||||
81 106 230 292 380 424 0
|
|
||||||
84 117 213 310 392 0 0
|
|
||||||
31 89 252 331 420 496 0
|
|
||||||
56 115 216 290 378 440 0
|
|
||||||
13 147 247 318 387 494 0
|
|
||||||
66 139 234 329 381 0 0
|
|
||||||
69 156 240 309 422 503 0
|
|
||||||
34 135 231 275 398 495 0
|
|
||||||
17 162 169 265 405 493 0
|
|
||||||
70 91 242 283 364 430 0
|
|
||||||
75 85 251 320 355 476 0
|
|
||||||
68 151 250 320 420 462 0
|
|
||||||
63 139 228 296 349 446 0
|
|
||||||
51 150 243 293 414 468 0
|
|
||||||
76 158 239 294 351 444 0
|
|
||||||
67 166 183 309 383 497 0
|
|
||||||
31 164 196 254 357 458 481
|
|
||||||
7 132 232 268 357 450 0
|
|
||||||
37 168 245 336 379 500 0
|
|
||||||
73 136 170 332 370 429 0
|
|
||||||
72 105 187 326 369 424 0
|
|
||||||
24 110 248 337 412 502 0
|
|
||||||
83 169 241 303 393 488 0
|
|
||||||
@@ -1,154 +0,0 @@
|
|||||||
import sys, os
|
|
||||||
import sys, os
|
|
||||||
sys.path.append(os.path.abspath('../..'))
|
|
||||||
print(sys.path)
|
|
||||||
|
|
||||||
|
|
||||||
import numpy as np
|
|
||||||
import seaborn as sns
|
|
||||||
import matplotlib.pyplot as plt
|
|
||||||
import signal
|
|
||||||
from timeit import default_timer
|
|
||||||
from functools import partial
|
|
||||||
|
|
||||||
from utility import codes, noise, misc
|
|
||||||
from utility.simulation.simulators import GenericMultithreadedSimulator
|
|
||||||
from utility.simulation import SimulationManager
|
|
||||||
|
|
||||||
from cpp_modules.cpp_decoders import ProximalDecoder_204_102 as ProximalDecoder
|
|
||||||
|
|
||||||
|
|
||||||
def task_func(params):
|
|
||||||
"""Function called by the GenericMultithreadedSimulator instance.
|
|
||||||
|
|
||||||
Calculate the BER, FER, and DFR for a given SNR and gamma.
|
|
||||||
"""
|
|
||||||
signal.signal(signal.SIGINT, signal.SIG_IGN)
|
|
||||||
|
|
||||||
decoder = params["decoder"]
|
|
||||||
max_iterations = params["max_iterations"]
|
|
||||||
SNR = params["SNR"]
|
|
||||||
n = params["n"]
|
|
||||||
k = params["k"]
|
|
||||||
|
|
||||||
c = np.zeros(n)
|
|
||||||
x_bpsk = c + 1
|
|
||||||
|
|
||||||
total_bit_errors = 0
|
|
||||||
total_frame_errors = 0
|
|
||||||
dec_fails = 0
|
|
||||||
|
|
||||||
num_iterations = 0
|
|
||||||
|
|
||||||
for i in range(max_iterations):
|
|
||||||
x = noise.add_awgn(x_bpsk, SNR, n, k)
|
|
||||||
x_hat, k_max = decoder.decode(x)
|
|
||||||
|
|
||||||
bit_errors = misc.count_bit_errors(x_hat, c)
|
|
||||||
if bit_errors > 0:
|
|
||||||
total_bit_errors += bit_errors
|
|
||||||
total_frame_errors += 1
|
|
||||||
|
|
||||||
num_iterations += 1
|
|
||||||
|
|
||||||
if k_max == -1:
|
|
||||||
dec_fails += 1
|
|
||||||
|
|
||||||
if total_frame_errors > 100:
|
|
||||||
break
|
|
||||||
|
|
||||||
BER = total_bit_errors / (num_iterations * n)
|
|
||||||
FER = total_frame_errors / num_iterations
|
|
||||||
DFR = dec_fails / (num_iterations + dec_fails)
|
|
||||||
|
|
||||||
return {"BER": BER, "FER": FER, "DFR": DFR,
|
|
||||||
"num_iterations": num_iterations}
|
|
||||||
|
|
||||||
|
|
||||||
def get_params(code_name: str):
|
|
||||||
"""In this function all parameters for the simulation are defined."""
|
|
||||||
# Define global simulation parameters
|
|
||||||
|
|
||||||
H_file = f"../../res/{code_name}.alist"
|
|
||||||
|
|
||||||
H = codes.read_alist_file(H_file)
|
|
||||||
n_min_k, n = H.shape
|
|
||||||
k = n - n_min_k
|
|
||||||
|
|
||||||
omega = 0.05
|
|
||||||
K = 100
|
|
||||||
gammas = np.arange(0.0, 0.17, 0.01)
|
|
||||||
|
|
||||||
SNRs = np.arange(1, 6, 0.5)
|
|
||||||
max_iterations = 20000
|
|
||||||
|
|
||||||
# Define parameters different for each task
|
|
||||||
|
|
||||||
task_params = []
|
|
||||||
for i, SNR in enumerate(SNRs):
|
|
||||||
for j, gamma in enumerate(gammas):
|
|
||||||
decoder = ProximalDecoder(H=H.astype('int32'), K=K, omega=omega,
|
|
||||||
gamma=gamma)
|
|
||||||
|
|
||||||
task_params.append(
|
|
||||||
{"decoder": decoder, "max_iterations": max_iterations,
|
|
||||||
"SNR": SNR, "gamma": gamma, "n": n, "k": k})
|
|
||||||
|
|
||||||
return omega, K, task_params
|
|
||||||
|
|
||||||
|
|
||||||
def configure_new_simulation(sim_mgr: SimulationManager, code_name: str,
|
|
||||||
sim_name: str) -> None:
|
|
||||||
sim = GenericMultithreadedSimulator()
|
|
||||||
|
|
||||||
omega, K, task_params = get_params(code_name)
|
|
||||||
|
|
||||||
sim.task_params = task_params
|
|
||||||
sim.task_func = task_func
|
|
||||||
sim.format_func = partial(misc.pgf_reformat_data_3d, x_param_name="SNR",
|
|
||||||
y_param_name="gamma",
|
|
||||||
z_param_names=["BER", "FER", "DFR",
|
|
||||||
"num_iterations"])
|
|
||||||
|
|
||||||
sim_mgr.configure_simulation(simulator=sim, name=sim_name,
|
|
||||||
additional_metadata={"omega": omega, "K": K})
|
|
||||||
|
|
||||||
|
|
||||||
def main():
|
|
||||||
# code_name = "BCH_7_4"
|
|
||||||
# code_name = "BCH_31_11"
|
|
||||||
# code_name = "BCH_31_26"
|
|
||||||
# code_name = "96.3.965"
|
|
||||||
# code_name = "204.33.486"
|
|
||||||
code_name = "204.33.484"
|
|
||||||
# code_name = "204.55.187"
|
|
||||||
# code_name = "408.33.844"
|
|
||||||
|
|
||||||
sim_name = f"2d_BER_FER_DFR_{misc.slugify(code_name)}"
|
|
||||||
|
|
||||||
# Run simulation
|
|
||||||
|
|
||||||
sim_mgr = SimulationManager(saves_dir="sim_saves",
|
|
||||||
results_dir="sim_results")
|
|
||||||
|
|
||||||
unfinished_sims = sim_mgr.get_unfinished()
|
|
||||||
if len(unfinished_sims) > 0:
|
|
||||||
sim_mgr.load_unfinished(unfinished_sims[0])
|
|
||||||
else:
|
|
||||||
configure_new_simulation(sim_mgr=sim_mgr, code_name=code_name,
|
|
||||||
sim_name=sim_name)
|
|
||||||
|
|
||||||
sim_mgr.simulate()
|
|
||||||
|
|
||||||
# Plot results
|
|
||||||
|
|
||||||
sns.set_theme()
|
|
||||||
ax = sns.lineplot(data=sim_mgr.get_current_results(), x="SNR", y="BER",
|
|
||||||
hue="gamma")
|
|
||||||
ax.set_yscale('log')
|
|
||||||
ax.set_ylim((5e-5, 2e-0))
|
|
||||||
plt.show()
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
main()
|
|
||||||
@@ -1,147 +0,0 @@
|
|||||||
import sys, os
|
|
||||||
sys.path.append(os.path.abspath('../..'))
|
|
||||||
|
|
||||||
import numpy as np
|
|
||||||
import seaborn as sns
|
|
||||||
import matplotlib.pyplot as plt
|
|
||||||
import signal
|
|
||||||
from timeit import default_timer
|
|
||||||
from functools import partial
|
|
||||||
import pandas as pd
|
|
||||||
|
|
||||||
from utility import codes, noise, misc
|
|
||||||
from utility.simulation.simulators import GenericMultithreadedSimulator
|
|
||||||
from utility.simulation import SimulationManager
|
|
||||||
|
|
||||||
from cpp_modules.cpp_decoders import ProximalDecoder_204_102 as ProximalDecoder
|
|
||||||
|
|
||||||
|
|
||||||
def task_func(params):
|
|
||||||
"""Function called by the GenericMultithreadedSimulator instance.
|
|
||||||
|
|
||||||
Calculate the average error over a number of iterations.
|
|
||||||
"""
|
|
||||||
signal.signal(signal.SIGINT, signal.SIG_IGN)
|
|
||||||
|
|
||||||
decoder = params["decoder"]
|
|
||||||
num_iterations = params["num_iterations"]
|
|
||||||
x_bpsk = params["x_bpsk"]
|
|
||||||
SNR = params["SNR"]
|
|
||||||
n = params["n"]
|
|
||||||
k = params["k"]
|
|
||||||
K = params["K"]
|
|
||||||
|
|
||||||
avg_error_values = np.zeros(K)
|
|
||||||
|
|
||||||
for i in range(num_iterations):
|
|
||||||
x = noise.add_awgn(x_bpsk, SNR, n, k)
|
|
||||||
|
|
||||||
error_values = decoder.get_error_values(x_bpsk.astype('int32'), x)
|
|
||||||
|
|
||||||
for j, val in enumerate(error_values):
|
|
||||||
avg_error_values[j] += val
|
|
||||||
|
|
||||||
avg_error_values = avg_error_values / num_iterations
|
|
||||||
|
|
||||||
return {"err": avg_error_values}
|
|
||||||
|
|
||||||
|
|
||||||
def get_params(code_name: str):
|
|
||||||
"""In this function all parameters for the simulation are defined."""
|
|
||||||
# Define global simulation parameters
|
|
||||||
|
|
||||||
H_file = f"../../res/{code_name}.alist"
|
|
||||||
H = codes.read_alist_file(H_file)
|
|
||||||
n_min_k, n = H.shape
|
|
||||||
k = n - n_min_k
|
|
||||||
|
|
||||||
SNR = 8
|
|
||||||
omegas = np.logspace(-0, -10, 40)
|
|
||||||
K = 200
|
|
||||||
|
|
||||||
num_iterations = 1000
|
|
||||||
x_bpsk = np.zeros(n) + 1
|
|
||||||
|
|
||||||
# Define parameters different for each task
|
|
||||||
|
|
||||||
task_params = []
|
|
||||||
for i, omega in enumerate(omegas):
|
|
||||||
decoder = ProximalDecoder(H=H.astype('int32'), K=K,
|
|
||||||
omega=omega)
|
|
||||||
task_params.append(
|
|
||||||
{"decoder": decoder, "num_iterations": num_iterations,
|
|
||||||
"x_bpsk": x_bpsk, "SNR": SNR, "n": n, "k": k, "K": K,
|
|
||||||
"omega": omega})
|
|
||||||
|
|
||||||
return SNR, K, task_params
|
|
||||||
|
|
||||||
|
|
||||||
def reformat_data(results):
|
|
||||||
"""Reformat the data obtained from the GenericMultithreadedSimulator to
|
|
||||||
be usable by pgfplots.
|
|
||||||
"""
|
|
||||||
K = 200
|
|
||||||
num_points = len(results) * K
|
|
||||||
|
|
||||||
x = np.zeros(num_points)
|
|
||||||
y = np.zeros(num_points)
|
|
||||||
z = np.zeros(num_points)
|
|
||||||
|
|
||||||
for i, (params, result) in enumerate(results.items()):
|
|
||||||
np.put(x, np.arange(i * K, (i + 1) * K), np.arange(1, K+1))
|
|
||||||
np.put(y, np.arange(i * K, (i + 1) * K), params["omega"])
|
|
||||||
np.put(z, np.arange(i * K, (i + 1) * K), result["err"])
|
|
||||||
|
|
||||||
x = x[::4]
|
|
||||||
y = y[::4]
|
|
||||||
z = z[::4]
|
|
||||||
|
|
||||||
df = pd.DataFrame({"k": x, "omega": y, "err": z}).sort_values(
|
|
||||||
by=['k', 'omega'], ascending=[True, False])
|
|
||||||
|
|
||||||
return df
|
|
||||||
|
|
||||||
|
|
||||||
def configure_new_simulation(sim_mgr: SimulationManager, code_name: str,
|
|
||||||
sim_name: str) -> None:
|
|
||||||
sim = GenericMultithreadedSimulator()
|
|
||||||
|
|
||||||
SNR, K, task_params = get_params(code_name)
|
|
||||||
|
|
||||||
sim.task_params = task_params
|
|
||||||
sim.task_func = task_func
|
|
||||||
sim.format_func = reformat_data
|
|
||||||
|
|
||||||
sim_mgr.configure_simulation(simulator=sim, name=sim_name,
|
|
||||||
additional_metadata={"SNR": SNR, "K": K})
|
|
||||||
|
|
||||||
|
|
||||||
def main():
|
|
||||||
# code_name = "BCH_7_4"
|
|
||||||
# code_name = "BCH_31_11"
|
|
||||||
# code_name = "BCH_31_26"
|
|
||||||
# code_name = "96.3.965"
|
|
||||||
# code_name = "204.33.486"
|
|
||||||
code_name = "204.33.484"
|
|
||||||
# code_name = "204.55.187"
|
|
||||||
# code_name = "408.33.844"
|
|
||||||
|
|
||||||
sim_name = f"2d_avg_error_{misc.slugify(code_name)}"
|
|
||||||
|
|
||||||
# Run simulation
|
|
||||||
|
|
||||||
sim_mgr = SimulationManager(saves_dir="sim_saves",
|
|
||||||
results_dir="sim_results")
|
|
||||||
|
|
||||||
unfinished_sims = sim_mgr.get_unfinished()
|
|
||||||
if len(unfinished_sims) > 0:
|
|
||||||
sim_mgr.load_unfinished(unfinished_sims[0])
|
|
||||||
else:
|
|
||||||
configure_new_simulation(sim_mgr=sim_mgr, code_name=code_name,
|
|
||||||
sim_name=sim_name)
|
|
||||||
|
|
||||||
sim_mgr.simulate()
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
main()
|
|
||||||
@@ -1,88 +0,0 @@
|
|||||||
import sys, os
|
|
||||||
sys.path.append(os.path.abspath('../..'))
|
|
||||||
|
|
||||||
import numpy as np
|
|
||||||
import pandas as pd
|
|
||||||
import seaborn as sns
|
|
||||||
import matplotlib.pyplot as plt
|
|
||||||
import signal
|
|
||||||
from timeit import default_timer
|
|
||||||
from tqdm import tqdm
|
|
||||||
|
|
||||||
from utility import codes, noise, misc
|
|
||||||
from utility.simulation.simulators import GenericMultithreadedSimulator
|
|
||||||
|
|
||||||
# from cpp_modules.cpp_decoders import ProximalDecoder
|
|
||||||
from cpp_modules.cpp_decoders import ProximalDecoder_204_102 as ProximalDecoder
|
|
||||||
|
|
||||||
|
|
||||||
def simulate(H_file, SNR, omega, K, gamma):
|
|
||||||
H = codes.read_alist_file(f"../../res/{H_file}")
|
|
||||||
n_min_k, n = H.shape
|
|
||||||
k = n - n_min_k
|
|
||||||
|
|
||||||
decoder = ProximalDecoder(H.astype('int32'), K=K, omega=omega, gamma=gamma)
|
|
||||||
|
|
||||||
c = np.zeros(n)
|
|
||||||
x_bpsk = (c + 1)
|
|
||||||
|
|
||||||
avg_grad_values = np.zeros(shape=(K, 2))
|
|
||||||
|
|
||||||
for i in range(1000):
|
|
||||||
x = noise.add_awgn(x_bpsk, SNR, n, k)
|
|
||||||
grad_values = decoder.get_gradient_values(x)
|
|
||||||
|
|
||||||
for j, (val_h, val_l) in enumerate(grad_values):
|
|
||||||
avg_grad_values[j, 0] += val_h
|
|
||||||
avg_grad_values[j, 1] += val_l
|
|
||||||
|
|
||||||
avg_grad_values = avg_grad_values / 1000
|
|
||||||
|
|
||||||
return avg_grad_values
|
|
||||||
|
|
||||||
|
|
||||||
def reformat_data(results):
|
|
||||||
return pd.DataFrame({"k": np.arange(0, results.size // 2, 1), "grad_h": results[:, 0], "grad_l": results[:, 1]})
|
|
||||||
|
|
||||||
|
|
||||||
def main():
|
|
||||||
# Set up simulation params
|
|
||||||
|
|
||||||
sim_name = "avg_grad_1dB"
|
|
||||||
|
|
||||||
# H_file = "96.3.965.alist"
|
|
||||||
H_file = "204.33.486.alist"
|
|
||||||
# H_file = "204.33.484.alist"
|
|
||||||
# H_file = "204.55.187.alist"
|
|
||||||
# H_file = "408.33.844.alist"
|
|
||||||
# H_file = "BCH_7_4.alist"
|
|
||||||
# H_file = "BCH_31_11.alist"
|
|
||||||
# H_file = "BCH_31_26.alist"
|
|
||||||
|
|
||||||
SNR = 1
|
|
||||||
omega = 0.05
|
|
||||||
K = 100
|
|
||||||
gamma = 0.05
|
|
||||||
|
|
||||||
# Run simulation
|
|
||||||
|
|
||||||
start_time = default_timer()
|
|
||||||
results = simulate(H_file, SNR, omega, K, gamma)
|
|
||||||
end_time = default_timer()
|
|
||||||
|
|
||||||
print(f"duration: {end_time - start_time}")
|
|
||||||
|
|
||||||
df = reformat_data(results)
|
|
||||||
|
|
||||||
df.to_csv(
|
|
||||||
f"sim_results/{sim_name}_{misc.slugify(H_file)}.csv", index=False)
|
|
||||||
|
|
||||||
sns.set_theme()
|
|
||||||
sns.lineplot(data=df, x="k", y="grad_h")
|
|
||||||
sns.lineplot(data=df, x="k", y="grad_l")
|
|
||||||
|
|
||||||
plt.show()
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
main()
|
|
||||||
@@ -1,2 +0,0 @@
|
|||||||
"""This package contains various utilities that can be used in combination
|
|
||||||
with the decoders."""
|
|
||||||
@@ -1,249 +0,0 @@
|
|||||||
"""This file Helper functions for generating an H matrix from alist data.
|
|
||||||
Code from https://github.com/gnuradio/gnuradio/blob/master/gr-fec/python/fec
|
|
||||||
/LDPC/Generate_LDPC_matrix_functions.py
|
|
||||||
"""
|
|
||||||
|
|
||||||
import numpy as np
|
|
||||||
|
|
||||||
|
|
||||||
#
|
|
||||||
# Related to alist files
|
|
||||||
#
|
|
||||||
|
|
||||||
|
|
||||||
def _parse_alist_header(header):
|
|
||||||
size = header.split()
|
|
||||||
return int(size[0]), int(size[1])
|
|
||||||
|
|
||||||
|
|
||||||
def read_alist_file(filename):
|
|
||||||
"""
|
|
||||||
This function reads in an alist file and creates the
|
|
||||||
corresponding parity check matrix H. The format of alist
|
|
||||||
files is described at:
|
|
||||||
http://www.inference.phy.cam.ac.uk/mackay/codes/alist.html
|
|
||||||
"""
|
|
||||||
|
|
||||||
with open(filename, 'r') as myfile:
|
|
||||||
data = myfile.readlines()
|
|
||||||
numCols, numRows = _parse_alist_header(data[0])
|
|
||||||
|
|
||||||
H = np.zeros((numRows, numCols))
|
|
||||||
|
|
||||||
# The locations of 1s starts in the 5th line of the file
|
|
||||||
for lineNumber in np.arange(4, 4 + numCols):
|
|
||||||
indices = data[lineNumber].split()
|
|
||||||
for index in indices:
|
|
||||||
H[int(index) - 1, lineNumber - 4] = 1
|
|
||||||
|
|
||||||
return H
|
|
||||||
|
|
||||||
|
|
||||||
#
|
|
||||||
# G matrices of specific codes
|
|
||||||
#
|
|
||||||
|
|
||||||
|
|
||||||
# @formatter:off
|
|
||||||
|
|
||||||
Gs = {'Hamming_7_4': np.array([[1, 0, 0, 0, 0, 1, 1],
|
|
||||||
[0, 1, 0, 0, 1, 0, 1],
|
|
||||||
[0, 0, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 1, 1, 1, 1]]),
|
|
||||||
|
|
||||||
'Golay_24_12': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 1],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1]]),
|
|
||||||
|
|
||||||
'BCH_15_7': np.array([[1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1]]),
|
|
||||||
|
|
||||||
'BCH_31_6': np.array([[1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1],
|
|
||||||
[0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1]]),
|
|
||||||
|
|
||||||
'BCH_31_11': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1]]),
|
|
||||||
|
|
||||||
'BCH_31_16': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1]]),
|
|
||||||
|
|
||||||
'BCH_31_21': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 1]]),
|
|
||||||
|
|
||||||
'BCH_63_16': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 0, 1, 1]]),
|
|
||||||
|
|
||||||
'BCH_63_30': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 0, 1, 1, 0, 0, 1, 1],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 0, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 0, 1, 1, 0, 0, 1, 1, 1]]),
|
|
||||||
|
|
||||||
# TODO: Fix this. This code should be systematic
|
|
||||||
'BCH_63_45': np.array([[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1],
|
|
||||||
[0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0],
|
|
||||||
[0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1],
|
|
||||||
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 1]])
|
|
||||||
}
|
|
||||||
|
|
||||||
# @formatter:on
|
|
||||||
|
|
||||||
|
|
||||||
#
|
|
||||||
# Utilities for systematic codes
|
|
||||||
#
|
|
||||||
|
|
||||||
|
|
||||||
def get_systematic_H(G: np.array) -> np.array:
|
|
||||||
"""Compute the H matrix for a systematic code.
|
|
||||||
|
|
||||||
:param G: Generator matrix of the systematic code
|
|
||||||
:return: Parity check matrix H
|
|
||||||
"""
|
|
||||||
k, n = G.shape
|
|
||||||
|
|
||||||
I = G[:, :k]
|
|
||||||
assert np.array_equal(I, np.identity(k))
|
|
||||||
|
|
||||||
P = G[:, k:]
|
|
||||||
|
|
||||||
H = np.zeros(shape=(n - k, n))
|
|
||||||
H[:, :k] = P.T
|
|
||||||
H[:, k:] = np.identity(n - k)
|
|
||||||
|
|
||||||
return H
|
|
||||||
@@ -1,72 +0,0 @@
|
|||||||
import unicodedata
|
|
||||||
import re
|
|
||||||
import typing
|
|
||||||
import pandas as pd
|
|
||||||
import numpy as np
|
|
||||||
|
|
||||||
|
|
||||||
def slugify(value, allow_unicode=False):
|
|
||||||
"""
|
|
||||||
Taken from https://github.com/django/django/blob/master/django/utils
|
|
||||||
/text.py
|
|
||||||
Convert to ASCII if 'allow_unicode' is False. Convert spaces or repeated
|
|
||||||
dashes to single dashes. Remove characters that aren't alphanumerics,
|
|
||||||
underscores, or hyphens. Convert to lowercase. Also strip leading and
|
|
||||||
trailing whitespace, dashes, and underscores.
|
|
||||||
"""
|
|
||||||
value = str(value)
|
|
||||||
if allow_unicode:
|
|
||||||
value = unicodedata.normalize('NFKC', value)
|
|
||||||
else:
|
|
||||||
value = unicodedata.normalize('NFKD', value).encode('ascii',
|
|
||||||
'ignore').decode(
|
|
||||||
'ascii')
|
|
||||||
value = re.sub(r'[^\w\s-]', '', value.lower())
|
|
||||||
return re.sub(r'[-\s]+', '-', value).strip('-_')
|
|
||||||
|
|
||||||
|
|
||||||
def pgf_reformat_data_3d(results: typing.Sequence, x_param_name: str,
|
|
||||||
y_param_name: str,
|
|
||||||
z_param_names: typing.Sequence[str]):
|
|
||||||
"""Reformat the results obtained from the GenericMultithreadedSimulator
|
|
||||||
into a form usable by pgfplots.
|
|
||||||
|
|
||||||
:param results: Results from GenericMultiThreadedSimulator
|
|
||||||
(dict of the form {params1: results1, params2: results2, ...}),
|
|
||||||
where resultsN and paramsN are themselves dicts:
|
|
||||||
paramsN = {param_name_1: val, param_name_2: val, ...}
|
|
||||||
resultsN = {result_name_1: val, result_name_2: val, ...}
|
|
||||||
:param x_param_name:
|
|
||||||
:param y_param_name:
|
|
||||||
:param z_param_names:
|
|
||||||
:return: pandas DataFrame of the following form:
|
|
||||||
{x_param_name: [x1, x1, x1, ..., x2, x2, x2, ...],
|
|
||||||
y_param_name: [y1, y2, y3, ..., y1, y2, y3, ...],
|
|
||||||
z_param_name: [z11, z21, z31, ..., z12, z22, z32, ...]}
|
|
||||||
"""
|
|
||||||
# Create result variables
|
|
||||||
x = np.zeros(len(results))
|
|
||||||
y = np.zeros(len(results))
|
|
||||||
zs = {name: np.zeros(len(results)) for name in z_param_names}
|
|
||||||
|
|
||||||
# Populate result variables
|
|
||||||
for i, (params, result) in enumerate(results.items()):
|
|
||||||
x_val = params[x_param_name]
|
|
||||||
y_val = params[y_param_name]
|
|
||||||
for z_param_name in z_param_names:
|
|
||||||
zs[z_param_name][i] = result[z_param_name]
|
|
||||||
|
|
||||||
x[i] = x_val
|
|
||||||
y[i] = y_val
|
|
||||||
|
|
||||||
# Create and return pandas DataFrame
|
|
||||||
df = pd.DataFrame({x_param_name: x, y_param_name: y})
|
|
||||||
for z_param_name in z_param_names:
|
|
||||||
df[z_param_name] = zs[z_param_name]
|
|
||||||
|
|
||||||
return df.sort_values(by=[x_param_name, y_param_name])
|
|
||||||
|
|
||||||
|
|
||||||
def count_bit_errors(x: np.array, x_hat: np.array) -> int:
|
|
||||||
"""Count the number of different bits between two words."""
|
|
||||||
return np.sum(x != x_hat)
|
|
||||||
@@ -1,34 +0,0 @@
|
|||||||
"""Utility functions relating to noise and SNR calculations."""
|
|
||||||
|
|
||||||
import numpy as np
|
|
||||||
|
|
||||||
|
|
||||||
def get_noise_variance_from_SNR(SNR: float, n: int, k: int) -> float:
|
|
||||||
"""Calculate the variance of the noise from an SNR and the signal
|
|
||||||
amplitude.
|
|
||||||
|
|
||||||
:param SNR: Signal-to-Noise-Ratio in dB (E_b/N_0)
|
|
||||||
:param n: Length of a codeword of the used code
|
|
||||||
:param k: Length of a dataword of the used code
|
|
||||||
:return: Variance of the noise
|
|
||||||
"""
|
|
||||||
SNR_linear = 10 ** (SNR / 10)
|
|
||||||
variance = 1 / (2 * (k / n) * SNR_linear)
|
|
||||||
|
|
||||||
return variance
|
|
||||||
|
|
||||||
|
|
||||||
def add_awgn(c: np.array, SNR: float, n: int, k: int) -> np.array:
|
|
||||||
"""Add Additive White Gaussian Noise to a data vector. As this function
|
|
||||||
adds random noise to the input, the output changes, even if it is called
|
|
||||||
multiple times with the same input.
|
|
||||||
|
|
||||||
:param c: Binary vector representing the data to be transmitted
|
|
||||||
:param SNR: Signal-to-Noise-Ratio in dB
|
|
||||||
:param n: Length of a codeword of the used code
|
|
||||||
:param k: Length of a dataword of the used code
|
|
||||||
:return: Data vector with added noise
|
|
||||||
"""
|
|
||||||
noise_var = get_noise_variance_from_SNR(SNR, n, k)
|
|
||||||
y = c + np.sqrt(noise_var) * np.random.normal(size=c.size)
|
|
||||||
return y
|
|
||||||
@@ -1,77 +0,0 @@
|
|||||||
"""Simulation package.
|
|
||||||
|
|
||||||
This package provides a way to easily define simulations in such a way that
|
|
||||||
they can be paused and resumed.
|
|
||||||
|
|
||||||
General Structure
|
|
||||||
=================
|
|
||||||
The package consists of 3 main components:
|
|
||||||
- The 'SimulationDeSerializer': Responsible for file IO
|
|
||||||
- The 'Simulator': Responsible for the actual simulating
|
|
||||||
- The 'SimulationManager': Delegates work to the DeSerializer and the
|
|
||||||
Simulator
|
|
||||||
|
|
||||||
The Simulator Class
|
|
||||||
===================
|
|
||||||
For each new simulating task, a new 'Simulator' must be defined. The
|
|
||||||
requirements for this class are the following:
|
|
||||||
- Must define the 'start_or_continue()', 'stop()' and
|
|
||||||
'get_current_results()' functions
|
|
||||||
- Must be picklable in order to store the simulation state
|
|
||||||
|
|
||||||
An example simulator could look as follows:
|
|
||||||
----------------------------------------------------------------
|
|
||||||
class SomeSimulator:
|
|
||||||
def __init__(self, num_iterations):
|
|
||||||
self._num_iterations = num_iterations
|
|
||||||
self._current_iter = 0
|
|
||||||
|
|
||||||
self._simulation_running = False
|
|
||||||
|
|
||||||
self._results = pd.DataFrame()
|
|
||||||
|
|
||||||
def _perform_iteration(self):
|
|
||||||
# Perform iteration and append results
|
|
||||||
...
|
|
||||||
|
|
||||||
def start_or_continue(self) -> None:
|
|
||||||
self._simulation_running = True
|
|
||||||
|
|
||||||
while self._simulation_running and (
|
|
||||||
self._current_iter < self._num_iterations):
|
|
||||||
self._perform_iteration()
|
|
||||||
|
|
||||||
def stop(self) -> None:
|
|
||||||
self._simulation_running = False
|
|
||||||
|
|
||||||
def get_current_results(self) -> pd.DataFrame:
|
|
||||||
return self._results
|
|
||||||
----------------------------------------------------------------
|
|
||||||
|
|
||||||
Usage
|
|
||||||
=====
|
|
||||||
To start a new simulation:
|
|
||||||
----------------------------------------------------------------
|
|
||||||
sim_mgr = SimulationManager(results_dir="results", saves_dir="saves")
|
|
||||||
|
|
||||||
sim = SomeSimulator(num_iterations=100)
|
|
||||||
sim_mgr.configure_simulation(simulator=sim, name='Some Simulation', \
|
|
||||||
column_labels=['label1', 'label2'])
|
|
||||||
sim_mgr.start()
|
|
||||||
----------------------------------------------------------------
|
|
||||||
|
|
||||||
To check for a previously interrupted simulation and continue:
|
|
||||||
----------------------------------------------------------------
|
|
||||||
sim_mgr = SimulationManager(results_dir="results", saves_dir="saves")
|
|
||||||
|
|
||||||
unfinished_sims = sim_mgr.get_unfinished()
|
|
||||||
|
|
||||||
if len(unfinished_sims) > 0:
|
|
||||||
sim_mgr.load_unfinished(unfinished_sims[0])
|
|
||||||
sim_mgr.simulate()
|
|
||||||
----------------------------------------------------------------
|
|
||||||
"""
|
|
||||||
|
|
||||||
|
|
||||||
from utility.simulation.management import SimulationManager, \
|
|
||||||
SimulationDeSerializer
|
|
||||||
@@ -1,239 +0,0 @@
|
|||||||
import json
|
|
||||||
import pandas as pd
|
|
||||||
import typing
|
|
||||||
import signal
|
|
||||||
import pickle
|
|
||||||
import os
|
|
||||||
from pathlib import Path
|
|
||||||
import platform
|
|
||||||
from datetime import datetime
|
|
||||||
import timeit
|
|
||||||
import collections.abc
|
|
||||||
|
|
||||||
from utility import misc
|
|
||||||
|
|
||||||
|
|
||||||
class SimulationDeSerializer:
|
|
||||||
"""Class responsible for file management, de- and serialization of
|
|
||||||
Simulator objects."""
|
|
||||||
|
|
||||||
def __init__(self, save_dir: str, results_dir: str):
|
|
||||||
self._saves_dir = save_dir
|
|
||||||
self._results_dir = results_dir
|
|
||||||
|
|
||||||
Path(self._saves_dir).mkdir(parents=True, exist_ok=True)
|
|
||||||
Path(self._results_dir).mkdir(parents=True, exist_ok=True)
|
|
||||||
|
|
||||||
def _get_savefile_path(self, sim_name):
|
|
||||||
return f"{self._saves_dir}/{misc.slugify(sim_name)}_state.pickle"
|
|
||||||
|
|
||||||
def _get_metadata_path(self, sim_name):
|
|
||||||
return f"{self._results_dir}/{misc.slugify(sim_name)}_metadata.json"
|
|
||||||
|
|
||||||
def _get_results_path(self, sim_name):
|
|
||||||
return f"{self._results_dir}/{misc.slugify(sim_name)}.csv"
|
|
||||||
|
|
||||||
def _read_metadata(self, sim_name) -> typing.Dict:
|
|
||||||
with open(self._get_metadata_path(sim_name), 'r',
|
|
||||||
encoding='utf-8') as f:
|
|
||||||
return json.load(f)
|
|
||||||
|
|
||||||
def _save_metadata(self, sim_name, metadata) -> None:
|
|
||||||
with open(self._get_metadata_path(sim_name), 'w+',
|
|
||||||
encoding='utf-8') as f:
|
|
||||||
json.dump(metadata, f, ensure_ascii=False, indent=4)
|
|
||||||
|
|
||||||
def unfinished_sim_present(self, sim_name: str):
|
|
||||||
"""Check if the savefile of a previously paused simulation is
|
|
||||||
present.
|
|
||||||
|
|
||||||
:param sim_name: Name
|
|
||||||
:return: True if a paused simulation with the given name is found
|
|
||||||
"""
|
|
||||||
return os.path.isfile(
|
|
||||||
self._get_savefile_path(sim_name)) and os.path.isfile(
|
|
||||||
self._get_metadata_path(sim_name))
|
|
||||||
|
|
||||||
# TODO: Make the directories configurable in the init function
|
|
||||||
def get_unfinished_sims(self) -> typing.List[str]:
|
|
||||||
"""Get a list unfinished simulations."""
|
|
||||||
save_files = [f for f in os.listdir(self._saves_dir) if
|
|
||||||
os.path.isfile(os.path.join(self._saves_dir, f))]
|
|
||||||
|
|
||||||
state_files = [f for f in save_files if f.endswith("_state.pickle")]
|
|
||||||
sim_slugs = [f.removesuffix("_state.pickle") for f in state_files]
|
|
||||||
|
|
||||||
sim_names = [self._read_metadata(slug)["name"] for slug in sim_slugs]
|
|
||||||
|
|
||||||
return sim_names
|
|
||||||
|
|
||||||
def remove_unfinished_sim(self, sim_name: str):
|
|
||||||
"""Remove the savefile of a previously paused simulation.
|
|
||||||
|
|
||||||
:param sim_name: Name of the simulation
|
|
||||||
"""
|
|
||||||
os.remove(self._get_savefile_path(sim_name))
|
|
||||||
# os.remove(self._get_metadata_path(sim_name))
|
|
||||||
|
|
||||||
def save_state(self, simulator: typing.Any, sim_name: str,
|
|
||||||
metadata: typing.Dict) -> None:
|
|
||||||
"""Save the state of a currently running simulation.
|
|
||||||
|
|
||||||
:param simulator: Simulator object
|
|
||||||
:param sim_name: Name of the simulation
|
|
||||||
:param metadata: Metadata to be saved besides the actual state
|
|
||||||
"""
|
|
||||||
# Save metadata
|
|
||||||
self._save_metadata(sim_name, metadata)
|
|
||||||
|
|
||||||
# Save simulation state
|
|
||||||
with open(self._get_savefile_path(sim_name), "wb") as file:
|
|
||||||
pickle.dump(simulator, file)
|
|
||||||
|
|
||||||
def read_state(self, sim_name: str) -> typing.Tuple[
|
|
||||||
typing.Any, typing.Dict]:
|
|
||||||
"""Read the saved state of a paused simulation.
|
|
||||||
|
|
||||||
:param sim_name: Name of the simulation
|
|
||||||
:return: Tuple of the form (simulator, metadata)
|
|
||||||
"""
|
|
||||||
# Read metadata
|
|
||||||
metadata = self._read_metadata(sim_name)
|
|
||||||
|
|
||||||
# Read simulation state
|
|
||||||
simulator = None
|
|
||||||
with open(self._get_savefile_path(sim_name), "rb") as file:
|
|
||||||
simulator = pickle.load(file)
|
|
||||||
|
|
||||||
return simulator, metadata
|
|
||||||
|
|
||||||
# TODO: Is the simulator object actually necessary here?
|
|
||||||
def save_results(self, simulator: typing.Any, sim_name: str,
|
|
||||||
metadata: typing.Dict) -> None:
|
|
||||||
"""Save simulation results to file.
|
|
||||||
|
|
||||||
:param simulator: Simulator object. Used to obtain the data
|
|
||||||
:param sim_name: Name of the simulation. Determines the filename
|
|
||||||
:param metadata: Metadata to be saved besides the actual simulation
|
|
||||||
results
|
|
||||||
"""
|
|
||||||
# Save metadata
|
|
||||||
self._save_metadata(sim_name, metadata)
|
|
||||||
|
|
||||||
# Save current results
|
|
||||||
simulator.current_results.to_csv(self._get_results_path(sim_name),
|
|
||||||
index=False)
|
|
||||||
|
|
||||||
def read_results(self, sim_name: str) -> typing.Tuple[
|
|
||||||
pd.DataFrame, typing.Dict]:
|
|
||||||
"""Read simulation results from file.
|
|
||||||
|
|
||||||
:param sim_name: Name of the simulation.
|
|
||||||
:return: Tuple of the form (data, metadata), where data is a pandas
|
|
||||||
dataframe and metadata is a dict
|
|
||||||
"""
|
|
||||||
# Read metadata
|
|
||||||
metadata = self._read_metadata(sim_name)
|
|
||||||
|
|
||||||
# Read results
|
|
||||||
results = pd.read_csv(self._get_results_path(sim_name))
|
|
||||||
|
|
||||||
return results, metadata
|
|
||||||
|
|
||||||
|
|
||||||
# TODO: Autosave simulation every so often
|
|
||||||
# TODO: Comment explaining what a Simulator class is
|
|
||||||
class SimulationManager:
|
|
||||||
"""This class only contains functions relating to stopping and
|
|
||||||
restarting of simulations (and storing of the simulation state in a
|
|
||||||
file, to be resumed at a later date).
|
|
||||||
|
|
||||||
All actual work is outsourced to a provided simulator class.
|
|
||||||
"""
|
|
||||||
|
|
||||||
def __init__(self, saves_dir: str, results_dir: str):
|
|
||||||
"""Construct a SimulationManager object.
|
|
||||||
|
|
||||||
:param saves_dir: Directory in which the simulation state of a paused
|
|
||||||
simulation should be stored
|
|
||||||
:param results_dir: Directory in which the results of the simulation
|
|
||||||
should be stored
|
|
||||||
"""
|
|
||||||
self._de_serializer = SimulationDeSerializer(saves_dir, results_dir)
|
|
||||||
|
|
||||||
self._simulator = None
|
|
||||||
self._sim_name = None
|
|
||||||
self._metadata = {"duration": 0}
|
|
||||||
self._sim_start_time = None
|
|
||||||
|
|
||||||
def _sim_configured(self) -> bool:
|
|
||||||
"""Check whether 'configure_simulation()' has been called."""
|
|
||||||
return (self._simulator is not None) and (
|
|
||||||
self._sim_name is not None) and (
|
|
||||||
self._metadata is not None)
|
|
||||||
|
|
||||||
def configure_simulation(self, simulator: typing.Any, name: str,
|
|
||||||
additional_metadata: dict = {}) -> None:
|
|
||||||
"""Configure a new simulation."""
|
|
||||||
self._simulator = simulator
|
|
||||||
self._sim_name = name
|
|
||||||
self._metadata["name"] = name
|
|
||||||
self._metadata["platform"] = platform.platform()
|
|
||||||
self._metadata.update(additional_metadata)
|
|
||||||
|
|
||||||
def get_unfinished(self) -> typing.List[str]:
|
|
||||||
"""Get a list of names of all present unfinished simulations."""
|
|
||||||
return self._de_serializer.get_unfinished_sims()
|
|
||||||
|
|
||||||
def load_unfinished(self, sim_name: str) -> None:
|
|
||||||
"""Load the state of an unfinished simulation form its savefile.
|
|
||||||
|
|
||||||
Warning: This function deletes the savefile after loading.
|
|
||||||
"""
|
|
||||||
assert self._de_serializer.unfinished_sim_present(sim_name)
|
|
||||||
|
|
||||||
self._sim_name = sim_name
|
|
||||||
self._simulator, self._metadata = self._de_serializer.read_state(
|
|
||||||
sim_name)
|
|
||||||
|
|
||||||
self._de_serializer.remove_unfinished_sim(sim_name)
|
|
||||||
|
|
||||||
# TODO: Metadata is being written twice here. Should save_results() also
|
|
||||||
# save the metadata?
|
|
||||||
def _exit_gracefully(self, *args) -> None:
|
|
||||||
"""Handler called when the program is interrupted. Pauses and saves
|
|
||||||
the currently running simulation."""
|
|
||||||
if self._sim_configured():
|
|
||||||
self._simulator.stop()
|
|
||||||
|
|
||||||
self._metadata["end_time"] = f"{datetime.now(tz=None)}"
|
|
||||||
self._metadata["duration"] \
|
|
||||||
+= timeit.default_timer() - self._sim_start_time
|
|
||||||
|
|
||||||
self._de_serializer.save_state(self._simulator, self._sim_name,
|
|
||||||
self._metadata)
|
|
||||||
self._de_serializer.save_results(self._simulator, self._sim_name,
|
|
||||||
self._metadata)
|
|
||||||
|
|
||||||
exit()
|
|
||||||
|
|
||||||
def simulate(self) -> None:
|
|
||||||
"""Start the simulation. This is a blocking call."""
|
|
||||||
assert self._sim_configured()
|
|
||||||
|
|
||||||
try:
|
|
||||||
self._sim_start_time = timeit.default_timer()
|
|
||||||
|
|
||||||
self._simulator.start_or_continue()
|
|
||||||
|
|
||||||
self._metadata["end_time"] = f"{datetime.now(tz=None)}"
|
|
||||||
self._metadata["duration"] \
|
|
||||||
+= timeit.default_timer() - self._sim_start_time
|
|
||||||
|
|
||||||
self._de_serializer.save_results(self._simulator, self._sim_name,
|
|
||||||
self._metadata)
|
|
||||||
except KeyboardInterrupt:
|
|
||||||
self._exit_gracefully()
|
|
||||||
|
|
||||||
def get_current_results(self) -> pd.DataFrame:
|
|
||||||
return self._simulator.current_results
|
|
||||||
@@ -1,121 +0,0 @@
|
|||||||
import pandas as pd
|
|
||||||
import numpy as np
|
|
||||||
import typing
|
|
||||||
from tqdm import tqdm
|
|
||||||
from concurrent.futures import ProcessPoolExecutor, process, wait
|
|
||||||
from functools import partial
|
|
||||||
from multiprocessing import Lock
|
|
||||||
|
|
||||||
from utility import noise
|
|
||||||
|
|
||||||
|
|
||||||
# TODO: Fix ProximalDecoder_Dynamic
|
|
||||||
# from cpp_modules.cpp_decoders import ProximalDecoder_Dynamic as
|
|
||||||
# ProximalDecoder
|
|
||||||
|
|
||||||
|
|
||||||
def count_bit_errors(d: np.array, d_hat: np.array) -> int:
|
|
||||||
"""Count the number of wrong bits in a decoded codeword.
|
|
||||||
|
|
||||||
:param d: Originally sent data
|
|
||||||
:param d_hat: Received data
|
|
||||||
:return: Number of bit errors
|
|
||||||
"""
|
|
||||||
return np.sum(d != d_hat)
|
|
||||||
|
|
||||||
|
|
||||||
class HashableDict:
|
|
||||||
"""Class behaving like an immutable dict. More importantly it is
|
|
||||||
hashable and thus usable as a key type for another dict."""
|
|
||||||
|
|
||||||
def __init__(self, data_dict):
|
|
||||||
assert (isinstance(data_dict, dict))
|
|
||||||
for key, val in data_dict.items():
|
|
||||||
self.__dict__[key] = val
|
|
||||||
|
|
||||||
def __getitem__(self, item):
|
|
||||||
return self.__dict__[item]
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
return str(self.__dict__)
|
|
||||||
|
|
||||||
|
|
||||||
class GenericMultithreadedSimulator:
|
|
||||||
def __init__(self, max_workers=8):
|
|
||||||
self._format_func = None
|
|
||||||
self._task_func = None
|
|
||||||
self._task_params = None
|
|
||||||
self._max_workers = max_workers
|
|
||||||
|
|
||||||
self._results = {}
|
|
||||||
self._executor = None
|
|
||||||
|
|
||||||
@property
|
|
||||||
def task_params(self):
|
|
||||||
return self._task_params
|
|
||||||
|
|
||||||
@task_params.setter
|
|
||||||
def task_params(self, sim_params):
|
|
||||||
self._task_params = {HashableDict(iteration_params): iteration_params
|
|
||||||
for iteration_params in sim_params}
|
|
||||||
|
|
||||||
@property
|
|
||||||
def task_func(self):
|
|
||||||
return self._task_func
|
|
||||||
|
|
||||||
@task_func.setter
|
|
||||||
def task_func(self, func):
|
|
||||||
self._task_func = func
|
|
||||||
|
|
||||||
@property
|
|
||||||
def format_func(self):
|
|
||||||
return self._format_func
|
|
||||||
|
|
||||||
@format_func.setter
|
|
||||||
def format_func(self, func):
|
|
||||||
self._format_func = func
|
|
||||||
|
|
||||||
def start_or_continue(self):
|
|
||||||
assert self._task_func is not None
|
|
||||||
assert self._task_params is not None
|
|
||||||
assert self._format_func is not None
|
|
||||||
|
|
||||||
self._executor = ProcessPoolExecutor(max_workers=self._max_workers)
|
|
||||||
|
|
||||||
with tqdm(total=(len(self._task_params)), leave=False) as pbar:
|
|
||||||
def done_callback(key, f):
|
|
||||||
try:
|
|
||||||
pbar.update(1)
|
|
||||||
self._results[key] = f.result()
|
|
||||||
del self._task_params[key]
|
|
||||||
except process.BrokenProcessPool:
|
|
||||||
# This exception is thrown when the program is
|
|
||||||
# prematurely stopped with a KeyboardInterrupt
|
|
||||||
pass
|
|
||||||
|
|
||||||
futures = []
|
|
||||||
|
|
||||||
for key, params in list(self._task_params.items()):
|
|
||||||
future = self._executor.submit(self._task_func, params)
|
|
||||||
future.add_done_callback(partial(done_callback, key))
|
|
||||||
futures.append(future)
|
|
||||||
|
|
||||||
self._executor.shutdown(wait=True, cancel_futures=False)
|
|
||||||
|
|
||||||
def stop(self):
|
|
||||||
assert self._executor is not None, "The simulation has to be started" \
|
|
||||||
" before it can be stopped"
|
|
||||||
self._executor.shutdown(wait=True, cancel_futures=True)
|
|
||||||
|
|
||||||
@property
|
|
||||||
def current_results(self):
|
|
||||||
return self._format_func(self._results)
|
|
||||||
|
|
||||||
def __getstate__(self):
|
|
||||||
state = self.__dict__.copy()
|
|
||||||
state["_executor"] = None
|
|
||||||
return state
|
|
||||||
|
|
||||||
def __setstate__(self, state):
|
|
||||||
self.__dict__.update(state)
|
|
||||||
self._executor = ProcessPoolExecutor()
|
|
||||||
@@ -1 +0,0 @@
|
|||||||
"""This package contains unit tests."""
|
|
||||||
@@ -1,72 +0,0 @@
|
|||||||
import unittest
|
|
||||||
import numpy as np
|
|
||||||
from decoders import proximal
|
|
||||||
|
|
||||||
|
|
||||||
class CheckParityTestCase(unittest.TestCase):
|
|
||||||
"""Test case for the check_parity function."""
|
|
||||||
|
|
||||||
def test_check_parity(self):
|
|
||||||
# Hamming(7,4) code
|
|
||||||
G = np.array([[1, 1, 1, 0, 0, 0, 0],
|
|
||||||
[1, 0, 0, 1, 1, 0, 0],
|
|
||||||
[0, 1, 0, 1, 0, 1, 0],
|
|
||||||
[1, 1, 0, 1, 0, 0, 1]])
|
|
||||||
H = np.array([[1, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 1, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 1, 1, 1, 1]])
|
|
||||||
R = np.array([[0, 0, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1]])
|
|
||||||
|
|
||||||
decoder = proximal.ProximalDecoder(H)
|
|
||||||
|
|
||||||
d1 = np.array([0, 1, 0, 1])
|
|
||||||
c1 = np.dot(np.transpose(G), d1) % 2
|
|
||||||
|
|
||||||
d2 = np.array([0, 0, 0, 0])
|
|
||||||
c2 = np.dot(np.transpose(G), d2) % 2
|
|
||||||
|
|
||||||
d3 = np.array([1, 1, 1, 1])
|
|
||||||
c3 = np.dot(np.transpose(G), d3) % 2
|
|
||||||
|
|
||||||
invalid_codeword = np.array([0, 1, 1, 0, 1, 1, 1])
|
|
||||||
|
|
||||||
self.assertEqual(decoder._check_parity(c1), True)
|
|
||||||
self.assertEqual(decoder._check_parity(c2), True)
|
|
||||||
self.assertEqual(decoder._check_parity(c3), True)
|
|
||||||
self.assertEqual(decoder._check_parity(invalid_codeword), False)
|
|
||||||
|
|
||||||
|
|
||||||
class GradientTestCase(unittest.TestCase):
|
|
||||||
"""Test case for the calculation of the gradient of the
|
|
||||||
code-constraint-polynomial."""
|
|
||||||
|
|
||||||
def test_grad_h(self):
|
|
||||||
"""Test the gradient of the code-constraint polynomial."""
|
|
||||||
# Hamming(7,4) code
|
|
||||||
G = np.array([[1, 1, 1, 0, 0, 0, 0],
|
|
||||||
[1, 0, 0, 1, 1, 0, 0],
|
|
||||||
[0, 1, 0, 1, 0, 1, 0],
|
|
||||||
[1, 1, 0, 1, 0, 0, 1]])
|
|
||||||
H = np.array([[1, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 1, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 1, 1, 1, 1]])
|
|
||||||
R = np.array([[0, 0, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 0, 1, 0, 0],
|
|
||||||
[0, 0, 0, 0, 0, 1, 0],
|
|
||||||
[0, 0, 0, 0, 0, 0, 1]])
|
|
||||||
|
|
||||||
x = np.array([1, 2, -1, -2, 2, 1, -1]) # Some randomly chosen vector
|
|
||||||
expected_grad_h = np.array(
|
|
||||||
[4, 26, -8, -36, 38, 28, -32]) # Manually calculated result
|
|
||||||
|
|
||||||
decoder = proximal.ProximalDecoder(H)
|
|
||||||
grad_h = decoder._grad_h(x)
|
|
||||||
|
|
||||||
self.assertEqual(np.array_equal(grad_h, expected_grad_h), True)
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
unittest.main()
|
|
||||||
@@ -1,55 +0,0 @@
|
|||||||
import unittest
|
|
||||||
import numpy as np
|
|
||||||
from decoders import maximum_likelihood
|
|
||||||
|
|
||||||
|
|
||||||
class CodewordGenerationTestCase(unittest.TestCase):
|
|
||||||
def test_codeword_generation(self):
|
|
||||||
"""Test case for data word and code word generation."""
|
|
||||||
# Hamming(7,4) code
|
|
||||||
G = np.array([[1, 1, 1, 0, 0, 0, 0],
|
|
||||||
[1, 0, 0, 1, 1, 0, 0],
|
|
||||||
[0, 1, 0, 1, 0, 1, 0],
|
|
||||||
[1, 1, 0, 1, 0, 0, 1]])
|
|
||||||
H = np.array([[1, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 1, 1, 0, 0, 1, 1],
|
|
||||||
[0, 0, 0, 1, 1, 1, 1]])
|
|
||||||
|
|
||||||
decoder = maximum_likelihood.MLDecoder(G, H)
|
|
||||||
|
|
||||||
expected_datawords = np.array([[0, 0, 0, 0],
|
|
||||||
[0, 0, 0, 1],
|
|
||||||
[0, 0, 1, 0],
|
|
||||||
[0, 0, 1, 1],
|
|
||||||
[0, 1, 0, 0],
|
|
||||||
[0, 1, 0, 1],
|
|
||||||
[0, 1, 1, 0],
|
|
||||||
[0, 1, 1, 1],
|
|
||||||
[1, 0, 0, 0],
|
|
||||||
[1, 0, 0, 1],
|
|
||||||
[1, 0, 1, 0],
|
|
||||||
[1, 0, 1, 1],
|
|
||||||
[1, 1, 0, 0],
|
|
||||||
[1, 1, 0, 1],
|
|
||||||
[1, 1, 1, 0],
|
|
||||||
[1, 1, 1, 1]])
|
|
||||||
|
|
||||||
expected_codewords = np.array([[0, 0, 0, 0, 0, 0, 0],
|
|
||||||
[1, 1, 0, 1, 0, 0, 1],
|
|
||||||
[0, 1, 0, 1, 0, 1, 0],
|
|
||||||
[1, 0, 0, 0, 0, 1, 1],
|
|
||||||
[1, 0, 0, 1, 1, 0, 0],
|
|
||||||
[0, 1, 0, 0, 1, 0, 1],
|
|
||||||
[1, 1, 0, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 1, 1, 1, 1],
|
|
||||||
[1, 1, 1, 0, 0, 0, 0],
|
|
||||||
[0, 0, 1, 1, 0, 0, 1],
|
|
||||||
[1, 0, 1, 1, 0, 1, 0],
|
|
||||||
[0, 1, 1, 0, 0, 1, 1],
|
|
||||||
[0, 1, 1, 1, 1, 0, 0],
|
|
||||||
[1, 0, 1, 0, 1, 0, 1],
|
|
||||||
[0, 0, 1, 0, 1, 1, 0],
|
|
||||||
[1, 1, 1, 1, 1, 1, 1]])
|
|
||||||
|
|
||||||
self.assertEqual(np.array_equal(decoder._datawords, expected_datawords), True)
|
|
||||||
self.assertEqual(np.array_equal(decoder._codewords, expected_codewords), True)
|
|
||||||
@@ -1,48 +0,0 @@
|
|||||||
import unittest
|
|
||||||
import numpy as np
|
|
||||||
|
|
||||||
from utility import noise, codes
|
|
||||||
|
|
||||||
|
|
||||||
# TODO: Rewrite tests for new SNR calculation
|
|
||||||
class NoiseAmpFromSNRTestCase(unittest.TestCase):
|
|
||||||
"""Test case for noise amplitude calculation."""
|
|
||||||
|
|
||||||
def test_get_noise_amp_from_SNR(self):
|
|
||||||
SNR1 = 0
|
|
||||||
SNR2 = 3
|
|
||||||
SNR3 = 20
|
|
||||||
SNR4 = -20
|
|
||||||
|
|
||||||
var1 = noise.get_noise_variance_from_SNR(SNR1, n=8, k=8)
|
|
||||||
var2 = noise.get_noise_variance_from_SNR(SNR2, n=8, k=8)
|
|
||||||
var3 = noise.get_noise_variance_from_SNR(SNR3, n=8, k=8)
|
|
||||||
var4 = noise.get_noise_variance_from_SNR(SNR4, n=8, k=8)
|
|
||||||
|
|
||||||
self.assertEqual(var1, 1 * 0.5)
|
|
||||||
self.assertAlmostEqual(var2, 0.5 * 0.5, places=2)
|
|
||||||
self.assertEqual(var3, 0.01 * 0.5)
|
|
||||||
self.assertEqual(var4, 100 * 0.5)
|
|
||||||
|
|
||||||
|
|
||||||
class CodesTestCase(unittest.TestCase):
|
|
||||||
"""Tests relating to the 'codes' utilities."""
|
|
||||||
|
|
||||||
def test_get_systematic_H(self):
|
|
||||||
# Hamming(7,4) code
|
|
||||||
G = np.array([[1, 0, 0, 0, 0, 1, 1],
|
|
||||||
[0, 1, 0, 0, 1, 0, 1],
|
|
||||||
[0, 0, 1, 0, 1, 1, 0],
|
|
||||||
[0, 0, 0, 1, 1, 1, 1]])
|
|
||||||
|
|
||||||
expected_H = np.array([[0, 1, 1, 1, 1, 0, 0],
|
|
||||||
[1, 0, 1, 1, 0, 1, 0],
|
|
||||||
[1, 1, 0, 1, 0, 0, 1]])
|
|
||||||
|
|
||||||
H = codes.get_systematic_H(G)
|
|
||||||
|
|
||||||
self.assertEqual(np.array_equal(expected_H, H), True)
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
|
||||||
unittest.main()
|
|
||||||
@@ -1,24 +0,0 @@
|
|||||||
import unittest
|
|
||||||
from utility import visualization
|
|
||||||
|
|
||||||
|
|
||||||
class NumRowsTestCase(unittest.TestCase):
|
|
||||||
def test_get_num_rows(self):
|
|
||||||
"""Test case for number of row calculation."""
|
|
||||||
|
|
||||||
num_rows1 = visualization._get_num_rows(num_graphs=4, num_cols=3)
|
|
||||||
expected_rows1 = 2
|
|
||||||
|
|
||||||
num_rows2 = visualization._get_num_rows(num_graphs=5, num_cols=2)
|
|
||||||
expected_rows2 = 3
|
|
||||||
|
|
||||||
num_rows3 = visualization._get_num_rows(num_graphs=4, num_cols=4)
|
|
||||||
expected_rows3 = 1
|
|
||||||
|
|
||||||
num_rows4 = visualization._get_num_rows(num_graphs=4, num_cols=5)
|
|
||||||
expected_rows4 = 1
|
|
||||||
|
|
||||||
self.assertEqual(num_rows1, expected_rows1)
|
|
||||||
self.assertEqual(num_rows2, expected_rows2)
|
|
||||||
self.assertEqual(num_rows3, expected_rows3)
|
|
||||||
self.assertEqual(num_rows4, expected_rows4)
|
|
||||||
@@ -1,75 +0,0 @@
|
|||||||
import seaborn as sns
|
|
||||||
import matplotlib.pyplot as plt
|
|
||||||
import pandas as pd
|
|
||||||
import typing
|
|
||||||
from itertools import chain
|
|
||||||
import math
|
|
||||||
|
|
||||||
|
|
||||||
def _get_num_rows(num_graphs: int, num_cols: int) -> int:
|
|
||||||
"""Get the minimum number of rows needed to show a certain number of
|
|
||||||
graphs, given a certain number of columns.
|
|
||||||
|
|
||||||
:param num_graphs: Number of graphs
|
|
||||||
:param num_cols: Number of columns
|
|
||||||
:return: Number of rows
|
|
||||||
"""
|
|
||||||
return math.ceil(num_graphs / num_cols)
|
|
||||||
|
|
||||||
|
|
||||||
# TODO: Handle number of graphs not nicely fitting into rows and columns
|
|
||||||
def plot_BERs(title: str,
|
|
||||||
data: typing.Sequence[
|
|
||||||
typing.Tuple[str, pd.DataFrame, typing.Sequence[str]]],
|
|
||||||
num_cols: int = 3) -> plt.figure:
|
|
||||||
"""This function creates a matplotlib figure containing a number of plots.
|
|
||||||
|
|
||||||
The plots created are logarithmic and the scaling is adjusted to be
|
|
||||||
sensible for BER plots.
|
|
||||||
|
|
||||||
:param title: Title of the figure
|
|
||||||
:param data: Sequence of tuples. Each tuple corresponds to a new plot and
|
|
||||||
is of the following form: [graph_title, pd.Dataframe, [line_label_1,
|
|
||||||
line_label2, ...]]. Each dataframe is assumed to have an "SNR" column
|
|
||||||
that is used as the x axis.
|
|
||||||
:param num_cols: Number of columns in which the graphs should be
|
|
||||||
arranged in the resulting figure
|
|
||||||
:return: Matplotlib figure
|
|
||||||
"""
|
|
||||||
# Determine layout and create figure
|
|
||||||
|
|
||||||
num_graphs = len(data)
|
|
||||||
num_rows = _get_num_rows(num_graphs, num_cols)
|
|
||||||
|
|
||||||
fig, axes = plt.subplots(num_rows, num_cols,
|
|
||||||
figsize=(num_cols * 4, num_rows * 4),
|
|
||||||
squeeze=False)
|
|
||||||
fig.suptitle(title)
|
|
||||||
|
|
||||||
fig.subplots_adjust(left=0.1,
|
|
||||||
bottom=0.1,
|
|
||||||
right=0.9,
|
|
||||||
top=0.9,
|
|
||||||
wspace=0.3,
|
|
||||||
hspace=0.4)
|
|
||||||
|
|
||||||
axes = list(chain.from_iterable(axes))[
|
|
||||||
:num_graphs] # Flatten the 2d axes array
|
|
||||||
|
|
||||||
# Populate axes
|
|
||||||
|
|
||||||
for axis, (graph_title, df, labels) in zip(axes, data):
|
|
||||||
column_names = [column for column in df.columns.values.tolist() if
|
|
||||||
not column == "SNR"]
|
|
||||||
|
|
||||||
for column, label in zip(column_names, labels):
|
|
||||||
sns.lineplot(ax=axis, data=df, x="SNR", y=column, label=label)
|
|
||||||
|
|
||||||
axis.set_title(graph_title)
|
|
||||||
axis.set(yscale="log")
|
|
||||||
axis.set_xlabel("SNR")
|
|
||||||
axis.set_ylabel("BER")
|
|
||||||
axis.set_yticks([10e-5, 10e-4, 10e-3, 10e-2, 10e-1, 10e0])
|
|
||||||
axis.legend()
|
|
||||||
|
|
||||||
return fig
|
|
||||||
Reference in New Issue
Block a user