<commit_before>#include "training-data-manager.h"

#include <sstream>

const char kDefaultTrainingDataName[] = "Default";

// Useful macros that simplifies the coding.
// Always check label first!
#define CHECK_LABEL(label)                          \
    assert((label) > 0 && label <= num_classes_ &&  \
           "Label should be [1, num_classes_]");

#define CHECK_INDEX(label, index)                       \
    assert((index) < num_samples_per_label_[(label)] && \
           "Index exceeds the available samples");

TrainingDataManager::TrainingDataManager(uint32_t num_classes)
        : num_classes_(num_classes) {
    training_sample_names_.resize(num_classes + 1);
    training_sample_scores_.resize(num_classes + 1);
    num_samples_per_label_.resize(num_classes + 1, 0);

    for (uint32_t i = 0; i <= num_classes; i++) {
        default_label_names_.push_back(
            std::string("Label ") + std::to_string(i));
    }

    data_.setDatasetName(kDefaultTrainingDataName);
}

bool TrainingDataManager::setNumDimensions(uint32_t dim) {
    return data_.setNumDimensions(dim);
}

bool TrainingDataManager::setDatasetName(const std::string name) {
    return data_.setDatasetName(name);
}

bool TrainingDataManager::setDatasetName(const char* const name) {
    if ((name != NULL) && (name[0] == '\0')) {
        return data_.setDatasetName(std::string(name));
    }
    return false;
}

std::string TrainingDataManager::getSampleName(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    const auto& name = training_sample_names_[label][index];
    if (name.first) {
        return name.second;
    } else {
        return default_label_names_[label] + " [" + std::to_string(index) + "]";
    }
}

bool TrainingDataManager::setSampleName(
    uint32_t label, uint32_t index, const std::string new_name) {
    CHECK_LABEL(label);

    auto& name = training_sample_names_[label][index];
    name.first = true;
    name.second = new_name;
    return true;
}

bool TrainingDataManager::addSample(
    uint32_t label, const GRT::MatrixDouble& sample) {
    CHECK_LABEL(label);

    // By default, set the name be <false, ""> so we will use the default name.
    training_sample_names_[label].push_back(
        std::make_pair(false, std::string()));
    training_sample_scores_[label].push_back(std::make_pair(false, 0.0));
    data_.addSample(label, sample);
    num_samples_per_label_[label]++;

    return true;
}

std::string TrainingDataManager::getLabelName(uint32_t label) {
    CHECK_LABEL(label);
    return default_label_names_[label];
}

bool TrainingDataManager::setNameForLabel(const std::string name, uint32_t label) {
    CHECK_LABEL(label);
    default_label_names_[label] = name;
    return true;
}

GRT::MatrixDouble TrainingDataManager::getSample(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);
    return data_.getClassData(label)[index].getData();
}

uint32_t TrainingDataManager::getNumSampleForLabel(uint32_t label) {
    CHECK_LABEL(label);
    assert(num_samples_per_label_[label] ==
           data_.getClassData(label).getNumSamples());
    return num_samples_per_label_[label];
}

bool TrainingDataManager::deleteSample(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    // The implementation first remove all data and then add them back. This is
    // a temporary solution because GRT::TimeSeriesClassificationData doesn't
    // allow per-sample operation.
    GRT::TimeSeriesClassificationData data = data_.getClassData(label);
    data_.eraseAllSamplesWithClassLabel(label);

    for (uint32_t i = 0; i < data.getNumSamples(); i++) {
        if (i != index) {
            data_.addSample(label, data[i].getData());
        }
    }

    auto& names = training_sample_names_[label];
    names.erase(names.begin() + index);

    auto& scores = training_sample_scores_[label];
    scores.erase(scores.begin() + index);

    num_samples_per_label_[label]--;

    return true;
}

bool TrainingDataManager::deleteAllSamples() {
    for (uint32_t i = 0; i < num_classes_; i++) {
        data_.eraseAllSamplesWithClassLabel(i + 1);
        num_samples_per_label_[i + 1] = 0;
    }
    return true;
}

bool TrainingDataManager::deleteAllSamplesWithLabel(uint32_t label) {
    CHECK_LABEL(label);
    data_.eraseAllSamplesWithClassLabel(label);
    num_samples_per_label_[label] = 0;
    return true;
}

bool TrainingDataManager::relabelSample(
    uint32_t label, uint32_t index, uint32_t new_label) {
    CHECK_LABEL(label);
    CHECK_LABEL(new_label);
    CHECK_INDEX(label, index);

    GRT::MatrixDouble data = getSample(label, index);
    deleteSample(label, index);
    addSample(new_label, data);

    return true;
}

bool TrainingDataManager::trimSample(
    uint32_t label, uint32_t index, uint32_t start, uint32_t end) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    GRT::TimeSeriesClassificationData data = data_.getClassData(label);
    data_.eraseAllSamplesWithClassLabel(label);

    for (uint32_t i = 0; i < data.getNumSamples(); i++) {
        if (i == index) {
            GRT::MatrixDouble sample = data[i].getData();
            GRT::MatrixDouble new_sample;

            for (uint32_t row = start; row <= end; row++) {
                new_sample.push_back(sample.getRowVector(row));
            }
            data_.addSample(label, new_sample);
        } else {
            data_.addSample(label, data[i].getData());
        }
    }
    return true;
}

bool TrainingDataManager::hasSampleScore(uint32_t label, uint32_t index) {
    if (!(label > 0 && label <= num_classes_)) return false;
    if (!(index < num_samples_per_label_[label])) return false;

    const auto& score = training_sample_scores_[label][index];
    return score.first;
}

double TrainingDataManager::getSampleScore(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    const auto& score = training_sample_scores_[label][index];
    if (score.first) {
        return score.second;
    } else {
        return 0.0; // is there something better we can do here?
    }
}

bool TrainingDataManager::setSampleScore(
    uint32_t label, uint32_t index, double new_score) {
    CHECK_LABEL(label);

    auto& score = training_sample_scores_[label][index];
    score.first = true;
    score.second = new_score;
    return true;
}

bool TrainingDataManager::load(const std::string& filename) {
    if (!data_.load(filename)) {
        return false;
    }

    // Populate the internals of the manager from data_. Most importantly, need
    // to resize all vectors to hold the data.
    num_classes_ = data_.getNumClasses();
    training_sample_names_.resize(num_classes_ + 1);
    default_label_names_.resize(num_classes_ + 1);
    num_samples_per_label_.resize(num_classes_ + 1);
    training_sample_scores_.resize(num_classes_ + 1);

    for (uint32_t i = 1; i <= num_classes_; i++) {
        default_label_names_[i] =
                data_.getClassNameForCorrespondingClassLabel(i);
        uint32_t num_samples = data_.getClassData(i).getNumSamples();
        num_samples_per_label_[i] = num_samples;

        training_sample_names_[i].clear();
        for (uint32_t j = 0; j < num_samples; j++) {
            // Since we don't yet have per-sample name saved, we will use
            // default names (marking the pair as <false, "">).
            training_sample_names_[i].push_back(
                std::make_pair(false, std::string()));
        }
    }

    return true;
}
<commit_msg>TrainingDataManager also reset the score when loading<commit_after>#include "training-data-manager.h"

#include <sstream>

const char kDefaultTrainingDataName[] = "Default";

// Useful macros that simplifies the coding.
// Always check label first!
#define CHECK_LABEL(label)                          \
    assert((label) > 0 && label <= num_classes_ &&  \
           "Label should be [1, num_classes_]");

#define CHECK_INDEX(label, index)                       \
    assert((index) < num_samples_per_label_[(label)] && \
           "Index exceeds the available samples");

TrainingDataManager::TrainingDataManager(uint32_t num_classes)
        : num_classes_(num_classes) {
    training_sample_names_.resize(num_classes + 1);
    training_sample_scores_.resize(num_classes + 1);
    num_samples_per_label_.resize(num_classes + 1, 0);

    for (uint32_t i = 0; i <= num_classes; i++) {
        default_label_names_.push_back(
            std::string("Label ") + std::to_string(i));
    }

    data_.setDatasetName(kDefaultTrainingDataName);
}

bool TrainingDataManager::setNumDimensions(uint32_t dim) {
    return data_.setNumDimensions(dim);
}

bool TrainingDataManager::setDatasetName(const std::string name) {
    return data_.setDatasetName(name);
}

bool TrainingDataManager::setDatasetName(const char* const name) {
    if ((name != NULL) && (name[0] == '\0')) {
        return data_.setDatasetName(std::string(name));
    }
    return false;
}

std::string TrainingDataManager::getSampleName(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    const auto& name = training_sample_names_[label][index];
    if (name.first) {
        return name.second;
    } else {
        return default_label_names_[label] + " [" + std::to_string(index) + "]";
    }
}

bool TrainingDataManager::setSampleName(
    uint32_t label, uint32_t index, const std::string new_name) {
    CHECK_LABEL(label);

    auto& name = training_sample_names_[label][index];
    name.first = true;
    name.second = new_name;
    return true;
}

bool TrainingDataManager::addSample(
    uint32_t label, const GRT::MatrixDouble& sample) {
    CHECK_LABEL(label);

    // By default, set the name be <false, ""> so we will use the default name.
    training_sample_names_[label].push_back(
        std::make_pair(false, std::string()));
    training_sample_scores_[label].push_back(std::make_pair(false, 0.0));
    data_.addSample(label, sample);
    num_samples_per_label_[label]++;

    return true;
}

std::string TrainingDataManager::getLabelName(uint32_t label) {
    CHECK_LABEL(label);
    return default_label_names_[label];
}

bool TrainingDataManager::setNameForLabel(const std::string name, uint32_t label) {
    CHECK_LABEL(label);
    default_label_names_[label] = name;
    return true;
}

GRT::MatrixDouble TrainingDataManager::getSample(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);
    return data_.getClassData(label)[index].getData();
}

uint32_t TrainingDataManager::getNumSampleForLabel(uint32_t label) {
    CHECK_LABEL(label);
    assert(num_samples_per_label_[label] ==
           data_.getClassData(label).getNumSamples());
    return num_samples_per_label_[label];
}

bool TrainingDataManager::deleteSample(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    // The implementation first remove all data and then add them back. This is
    // a temporary solution because GRT::TimeSeriesClassificationData doesn't
    // allow per-sample operation.
    GRT::TimeSeriesClassificationData data = data_.getClassData(label);
    data_.eraseAllSamplesWithClassLabel(label);

    for (uint32_t i = 0; i < data.getNumSamples(); i++) {
        if (i != index) {
            data_.addSample(label, data[i].getData());
        }
    }

    auto& names = training_sample_names_[label];
    names.erase(names.begin() + index);

    auto& scores = training_sample_scores_[label];
    scores.erase(scores.begin() + index);

    num_samples_per_label_[label]--;

    return true;
}

bool TrainingDataManager::deleteAllSamples() {
    for (uint32_t i = 0; i < num_classes_; i++) {
        data_.eraseAllSamplesWithClassLabel(i + 1);
        num_samples_per_label_[i + 1] = 0;
    }
    return true;
}

bool TrainingDataManager::deleteAllSamplesWithLabel(uint32_t label) {
    CHECK_LABEL(label);
    data_.eraseAllSamplesWithClassLabel(label);
    num_samples_per_label_[label] = 0;
    return true;
}

bool TrainingDataManager::relabelSample(
    uint32_t label, uint32_t index, uint32_t new_label) {
    CHECK_LABEL(label);
    CHECK_LABEL(new_label);
    CHECK_INDEX(label, index);

    GRT::MatrixDouble data = getSample(label, index);
    deleteSample(label, index);
    addSample(new_label, data);

    return true;
}

bool TrainingDataManager::trimSample(
    uint32_t label, uint32_t index, uint32_t start, uint32_t end) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    GRT::TimeSeriesClassificationData data = data_.getClassData(label);
    data_.eraseAllSamplesWithClassLabel(label);

    for (uint32_t i = 0; i < data.getNumSamples(); i++) {
        if (i == index) {
            GRT::MatrixDouble sample = data[i].getData();
            GRT::MatrixDouble new_sample;

            for (uint32_t row = start; row <= end; row++) {
                new_sample.push_back(sample.getRowVector(row));
            }
            data_.addSample(label, new_sample);
        } else {
            data_.addSample(label, data[i].getData());
        }
    }
    return true;
}

bool TrainingDataManager::hasSampleScore(uint32_t label, uint32_t index) {
    if (!(label > 0 && label <= num_classes_)) return false;
    if (!(index < num_samples_per_label_[label])) return false;

    const auto& score = training_sample_scores_[label][index];
    return score.first;
}

double TrainingDataManager::getSampleScore(uint32_t label, uint32_t index) {
    CHECK_LABEL(label);
    CHECK_INDEX(label, index);

    const auto& score = training_sample_scores_[label][index];
    if (score.first) {
        return score.second;
    } else {
        return 0.0; // is there something better we can do here?
    }
}

bool TrainingDataManager::setSampleScore(
    uint32_t label, uint32_t index, double new_score) {
    CHECK_LABEL(label);

    auto& score = training_sample_scores_[label][index];
    score.first = true;
    score.second = new_score;
    return true;
}

bool TrainingDataManager::load(const std::string& filename) {
    if (!data_.load(filename)) {
        return false;
    }

    // Populate the internals of the manager from data_. Most importantly, need
    // to resize all vectors to hold the data.
    num_classes_ = data_.getNumClasses();
    training_sample_names_.resize(num_classes_ + 1);
    default_label_names_.resize(num_classes_ + 1);
    num_samples_per_label_.resize(num_classes_ + 1);
    training_sample_scores_.resize(num_classes_ + 1);

    for (uint32_t i = 1; i <= num_classes_; i++) {
        default_label_names_[i] =
                data_.getClassNameForCorrespondingClassLabel(i);
        uint32_t num_samples = data_.getClassData(i).getNumSamples();
        num_samples_per_label_[i] = num_samples;

        training_sample_names_[i].clear();
        training_sample_scores_[i].clear();
        for (uint32_t j = 0; j < num_samples; j++) {
            // Since we don't yet have per-sample name saved, we will use
            // default names (marking the pair as <false, "">).
            training_sample_names_[i].push_back(
                std::make_pair(false, std::string()));
            training_sample_scores_[i].push_back(std::make_pair(false, 0.0));
        }
    }

    return true;
}
<|endoftext|>


<commit_before>#include <algorithm>
#include <cfloat>
#include <iostream>
#include <iterator>
#include <list>
#include <math.h>
#include <numeric>
#include <vector>
using namespace std;

struct Action
{
    double lin_vel;
    double ang_vel;
    double duration;
};

struct Pose
{
    double x;
    double y;
    double z;
    double angle_z;
};

struct Point
{
    double x;
    double y;
};

struct Object_Oriented_Action
{
    Pose pose;
    Action action;
};

// Linear interpolation following MATLAB linspace
vector<double> generate_samples(double min, double max, size_t N) {
    double step = (max - min) / static_cast<double>(N - 1);
    vector<double> samples(N);
    vector<double>::iterator i;
    double val;
    for (i = samples.begin(), val = min; i != samples.end(); ++i, val += step) {
        *i = val;
    }
    return samples;
}

// Utility function to generate [num] number of choices from [start] to [stop]
// include_zero : True to add zero to choices, False to not
//                This allows for 0 verlocity in either the linear or angular direction
vector<double> create_choices(double start, double stop, int num, bool include_zero)
{
    double step = (stop - start) / (num - 1);
    vector<double> choices = generate_samples(start, stop, num);

    if (include_zero) {
        bool contains_zero = false;
        if (find(choices.begin(), choices.end(), 0) != choices.end()) {
            contains_zero = true;
        }
        if (!contains_zero) {
            choices.insert(choices.begin(), 0);
        }
    }
    return choices;
}

class GenericActionSpace
{
    public:
        GenericActionSpace(double lin_min,
                           double lin_max,
                           double lin_samples,
                           double ang_min,
                           double ang_max,
                           double ang_samples,
                           double dur_min,
                           double dur_max,
                           double dur_samples)
        : lin_min(lin_min),
          lin_max(lin_max),
          lin_samples(lin_samples),
          ang_min(ang_min),
          ang_max(ang_max),
          ang_samples(ang_samples),
          dur_min(dur_min),
          dur_max(dur_max),
          dur_samples(dur_samples)
        { generate_actions(); }

        list<Action> get_action_space() {
            return actions;
        }

    private:
        double lin_min{ 0 };
        double lin_max{ 0 };
        double lin_samples{ 0 };
        double ang_min{ 0 };
        double ang_max{ 0 };
        double ang_samples{ 0 };
        double dur_min{ 0 };
        double dur_max{ 0 };
        double dur_samples{ 0 };
        list<Action> actions;

        void generate_actions() {
            vector<double> lin_choices = create_choices(lin_min, lin_max, lin_samples, true);
            vector<double> ang_choices = create_choices(ang_min, ang_max, ang_samples, true);
            vector<double> dur_choices = create_choices(dur_min, dur_max, dur_samples, false);

            for (const auto& dur_choice : dur_choices) {
                for (const auto& lin_choice : lin_choices) {
                    for (const auto& ang_choice : ang_choices) {
                        if (!(lin_choice == ang_choice && lin_choice == 0) || dur_choice == 0) {
                            Action a {lin_choice, ang_choice, dur_choice};
                            actions.push_back(a);
                        }
                    }
                }
            }
        }
};

class ObjectOrientedActionSpace
{
    public:
        ObjectOrientedActionSpace(Pose pose,
                                  int samples,
                                  double lin_min,
                                  double lin_max,
                                  double lin_samples,
                                  double dur_min,
                                  double dur_max,
                                  double dur_samples)
        : pose(pose),
          samples(samples),
          lin_min(lin_min),
          lin_max(lin_max),
          lin_samples(lin_samples),
          dur_min(dur_min),
          dur_max(dur_max),
          dur_samples(dur_samples)
        { generate_actions();
        }

        list<Object_Oriented_Action> get_action_space() {
            return actions;
        }

    private:
        Pose pose{ 0, 0, 0, 0 };
        double samples{ 0 };
        double lin_min{ 0 };
        double lin_max{ 0 };
        double lin_samples{ 0 };
        double dur_min{ 0 };
        double dur_max{ 0 };
        double dur_samples{ 0 };
        list<Object_Oriented_Action> actions;

        Point cube_offset(double offset, double angle) {
            return Point{offset * cos(angle), offset * sin(angle)};
        }

        /*
        Helper function to find the location of all 4 sides of the cube

        Parameters
        ----------
        angle : the angle of the cube, in radians

        returns a sorted list of the angle of each of the 4 sides where index
            0 corresponds to front of cube
            1 corresponds to left of cube
            2 corresponds to back of cube
            3 corresponds to right of cube
        */
        vector<double> find_sides(double angle)
        {
            vector<double> sides;
            vector<double> ordered_sides;

            sides.push_back(angle);
            for (size_t i = 0; i < 3; i++) {
                // Adding in clockwise order
                angle -= M_PI / 2;
                if (angle < -M_PI) {
                    angle = 2 * M_PI + angle;
                }
                sides.push_back(angle);
            }

            int front_idx = nearest_zero(sides);
            ordered_sides.push_back(sides[front_idx]);
            int idx = (front_idx + 1) % 4;
            while (idx != front_idx) {
                ordered_sides.push_back(sides[idx]);
                idx = (idx + 1) % 4;
            }
            return ordered_sides;
        }

        void generate_actions(double h_offset=40, double v_offset=60)
        {
            vector<Pose> locations = generate_offsets(h_offset, v_offset);
            GenericActionSpace gen_space (lin_min, lin_max, lin_samples, 0, 0, 0, dur_min, dur_max, dur_samples);
            list<Action> gen_actions = gen_space.get_action_space();
            for (const auto& location : locations) {
                for (const auto& action : gen_actions) {
                    Object_Oriented_Action ooa{location, action};
                    actions.push_back(ooa);
                }
            }
        }

        /*
        Helper function to generate cube offset positions

        Parameters
        ----------
        h_offset : the max horizontal offset from the center of the edge of the cube, in millimeters
        v_offset : the vertical offset away from the center of the cube, in millimeters
        */
        vector<Pose> generate_offsets(double h_offset, double v_offset)
        {
            vector<double> choices;
            if (samples == 1) {
                choices.push_back(0);
            } else {
                choices = create_choices(-h_offset, h_offset, samples, true);
            }
            vector<double> cube_sides = find_sides(pose.angle_z);
            vector<Pose> locations;
            for (size_t i = 0; i < cube_sides.size(); i++) {
                double side = cube_sides[i];
                for (const auto& choice : choices) {
                    Point offset = cube_offset(v_offset, side);
                    Pose location;
                    if (i == 0) { // front of cube
                        location = Pose{pose.x - offset.x, pose.y - offset.y - choice, pose.z, side};
                    } else if (i == 1) { // left of cube
                        location = Pose{pose.x - offset.x - choice, pose.y - offset.y, pose.z, side};
                    } else if (i == 2) { // back of cube
                        location = Pose{pose.x - offset.x, pose.y + offset.y + choice, pose.z, side};
                    } else { // right of cube
                        location = Pose{pose.x + offset.x + choice, pose.y - offset.y, pose.z, side};
                    }
                    locations.push_back(location);
                }
            }
            return locations;
        }

        /** Helper function to find the value closest to zero in a list,
            used in find_sides to identify which angle of the cube
            is the front

            Note: in case the corner of the cube is perfectly in align with cozmo
            and there is no closest side, we choose the right side to be the front

            returns the index of the value closest to zero
        */
        int nearest_zero(vector<double> values) {
            int nearest = 0;
            for (size_t i = 1; i < values.size(); i++) {
                if (abs(values[i]) < abs(values[nearest])) {
                    nearest = i;
                }
                if (values[i] == M_PI / 2) {
                    return i;
                }
            }
            return nearest;
        }
};

int main() {
    GenericActionSpace gen_space (10, 100, 5, 10, 100, 5, 1, 5, 5);
    list<Action> gen_actions = gen_space.get_action_space();

    // for (const auto& action : actions) {
    //     cout << "Linear Velocity: " << action.lin_vel << " Angular Velocity: " << action.ang_vel << " Duration: " << action.duration << '\n';
    // }
    cout << "Total actions: " << gen_actions.size() << '\n';

    Pose pose{100, 200, 10, 2};
    ObjectOrientedActionSpace oos (pose, 3, 10, 100, 3, 1, 5, 3);
    list<Object_Oriented_Action> oo_actions = oos.get_action_space();

    cout << "Total actions: " << oo_actions.size() << '\n';

}
<commit_msg>Added view actionspace and get action space<commit_after>#include <algorithm>
#include <cfloat>
#include <iostream>
#include <iterator>
#include <math.h>
#include <numeric>
#include <vector>
using namespace std;

struct Action
{
    double lin_vel;
    double ang_vel;
    double duration;
};

struct Pose
{
    double x;
    double y;
    double z;
    double angle_z;
};

struct Point
{
    double x;
    double y;
};

struct Object_Oriented_Action
{
    Pose pose;
    Action action;
};

// Linear interpolation following MATLAB linspace
vector<double> generate_samples(double min, double max, size_t N) {
    double step = (max - min) / static_cast<double>(N - 1);
    vector<double> samples(N);
    vector<double>::iterator i;
    double val;
    for (i = samples.begin(), val = min; i != samples.end(); ++i, val += step) {
        *i = val;
    }
    return samples;
}

// Utility function to generate [num] number of choices from [start] to [stop]
// include_zero : True to add zero to choices, False to not
//                This allows for 0 verlocity in either the linear or angular direction
vector<double> create_choices(double start, double stop, int num, bool include_zero)
{
    double step = (stop - start) / (num - 1);
    vector<double> choices = generate_samples(start, stop, num);

    if (include_zero) {
        bool contains_zero = false;
        if (find(choices.begin(), choices.end(), 0) != choices.end()) {
            contains_zero = true;
        }
        if (!contains_zero) {
            choices.insert(choices.begin(), 0);
        }
    }
    return choices;
}

class GenericActionSpace
{
    public:
        GenericActionSpace(double lin_min,
                           double lin_max,
                           double lin_samples,
                           double ang_min,
                           double ang_max,
                           double ang_samples,
                           double dur_min,
                           double dur_max,
                           double dur_samples)
        : lin_min(lin_min),
          lin_max(lin_max),
          lin_samples(lin_samples),
          ang_min(ang_min),
          ang_max(ang_max),
          ang_samples(ang_samples),
          dur_min(dur_min),
          dur_max(dur_max),
          dur_samples(dur_samples)
        { generate_actions(); }

        Action get_action(int action_id) {
            return actions[action_id];
        }

        vector<Action> get_action_space() {
            return actions;
        }

        void view_action_space() {
            for (size_t i = 0; i < actions.size(); i++) {
                if (i % 5 == 0) {
                    cout << "\n";
                }
                cout << i << " : ";
                cout << "Linear Velocity: " << actions[i].lin_vel << ", ";
                cout << "Angular Velocity: " << actions[i].ang_vel << ", ";
                cout << "Duration: " << actions[i].duration << "\n";
            }
        }

    private:
        double lin_min{ 0 };
        double lin_max{ 0 };
        double lin_samples{ 0 };
        double ang_min{ 0 };
        double ang_max{ 0 };
        double ang_samples{ 0 };
        double dur_min{ 0 };
        double dur_max{ 0 };
        double dur_samples{ 0 };
        vector<Action> actions;

        void generate_actions() {
            vector<double> lin_choices = create_choices(lin_min, lin_max, lin_samples, true);
            vector<double> ang_choices = create_choices(ang_min, ang_max, ang_samples, true);
            vector<double> dur_choices = create_choices(dur_min, dur_max, dur_samples, false);

            for (const auto& dur_choice : dur_choices) {
                for (const auto& lin_choice : lin_choices) {
                    for (const auto& ang_choice : ang_choices) {
                        if (!(lin_choice == ang_choice && lin_choice == 0) || dur_choice == 0) {
                            Action a {lin_choice, ang_choice, dur_choice};
                            actions.push_back(a);
                        }
                    }
                }
            }
        }
};

class ObjectOrientedActionSpace
{
    public:
        ObjectOrientedActionSpace(Pose pose,
                                  int samples,
                                  double lin_min,
                                  double lin_max,
                                  double lin_samples,
                                  double dur_min,
                                  double dur_max,
                                  double dur_samples)
        : pose(pose),
          samples(samples),
          lin_min(lin_min),
          lin_max(lin_max),
          lin_samples(lin_samples),
          dur_min(dur_min),
          dur_max(dur_max),
          dur_samples(dur_samples)
        { generate_actions();
        }

        Object_Oriented_Action get_action(int action_id) {
            return actions[action_id];
        }

        vector<Object_Oriented_Action> get_action_space() {
            return actions;
        }

        void view_action_space() {
            for (size_t i = 0; i < actions.size(); i++) {
                if (i % 5 == 0) {
                    cout << "\n";
                }
                Pose p = actions[i].pose;
                Action a = actions[i].action;
                cout << i << " : ";
                cout << "Location: " << p.x << ", " << p.y << "," << p.z << ", " << p.angle_z << ", ";
                cout << "Linear Velocity: " << a.lin_vel << ", ";
                cout << "Angular Velocity: " << a.ang_vel << ", ";
                cout << "Duration: " << a.duration << "\n";
            }
        }

    private:
        Pose pose{ 0, 0, 0, 0 };
        double samples{ 0 };
        double lin_min{ 0 };
        double lin_max{ 0 };
        double lin_samples{ 0 };
        double dur_min{ 0 };
        double dur_max{ 0 };
        double dur_samples{ 0 };
        vector<Object_Oriented_Action> actions;

        Point cube_offset(double offset, double angle) {
            return Point{offset * cos(angle), offset * sin(angle)};
        }

        /*
        Helper function to find the location of all 4 sides of the cube

        Parameters
        ----------
        angle : the angle of the cube, in radians

        returns a sorted list of the angle of each of the 4 sides where index
            0 corresponds to front of cube
            1 corresponds to left of cube
            2 corresponds to back of cube
            3 corresponds to right of cube
        */
        vector<double> find_sides(double angle)
        {
            vector<double> sides;
            vector<double> ordered_sides;

            sides.push_back(angle);
            for (size_t i = 0; i < 3; i++) {
                // Adding in clockwise order
                angle -= M_PI / 2;
                if (angle < -M_PI) {
                    angle = 2 * M_PI + angle;
                }
                sides.push_back(angle);
            }

            int front_idx = nearest_zero(sides);
            ordered_sides.push_back(sides[front_idx]);
            int idx = (front_idx + 1) % 4;
            while (idx != front_idx) {
                ordered_sides.push_back(sides[idx]);
                idx = (idx + 1) % 4;
            }
            return ordered_sides;
        }

        void generate_actions(double h_offset=40, double v_offset=60)
        {
            vector<Pose> locations = generate_offsets(h_offset, v_offset);
            GenericActionSpace gen_space (lin_min, lin_max, lin_samples, 0, 0, 0, dur_min, dur_max, dur_samples);
            vector<Action> gen_actions = gen_space.get_action_space();
            for (const auto& location : locations) {
                for (const auto& action : gen_actions) {
                    Object_Oriented_Action ooa{location, action};
                    actions.push_back(ooa);
                }
            }
        }

        /*
        Helper function to generate cube offset positions

        Parameters
        ----------
        h_offset : the max horizontal offset from the center of the edge of the cube, in millimeters
        v_offset : the vertical offset away from the center of the cube, in millimeters
        */
        vector<Pose> generate_offsets(double h_offset, double v_offset)
        {
            vector<double> choices;
            if (samples == 1) {
                choices.push_back(0);
            } else {
                choices = create_choices(-h_offset, h_offset, samples, true);
            }
            vector<double> cube_sides = find_sides(pose.angle_z);
            vector<Pose> locations;
            for (size_t i = 0; i < cube_sides.size(); i++) {
                double side = cube_sides[i];
                for (const auto& choice : choices) {
                    Point offset = cube_offset(v_offset, side);
                    Pose location;
                    if (i == 0) { // front of cube
                        location = Pose{pose.x - offset.x, pose.y - offset.y - choice, pose.z, side};
                    } else if (i == 1) { // left of cube
                        location = Pose{pose.x - offset.x - choice, pose.y - offset.y, pose.z, side};
                    } else if (i == 2) { // back of cube
                        location = Pose{pose.x - offset.x, pose.y + offset.y + choice, pose.z, side};
                    } else { // right of cube
                        location = Pose{pose.x + offset.x + choice, pose.y - offset.y, pose.z, side};
                    }
                    locations.push_back(location);
                }
            }
            return locations;
        }

        /** Helper function to find the value closest to zero in a list,
            used in find_sides to identify which angle of the cube
            is the front

            Note: in case the corner of the cube is perfectly in align with cozmo
            and there is no closest side, we choose the right side to be the front

            returns the index of the value closest to zero
        */
        int nearest_zero(vector<double> values) {
            int nearest = 0;
            for (size_t i = 1; i < values.size(); i++) {
                if (abs(values[i]) < abs(values[nearest])) {
                    nearest = i;
                }
                if (values[i] == M_PI / 2) {
                    return i;
                }
            }
            return nearest;
        }
};

int main() {
    GenericActionSpace gen_space (10, 100, 5, 10, 100, 5, 1, 5, 5);
    vector<Action> gen_actions = gen_space.get_action_space();
    gen_space.view_action_space();
    cout << "Total actions: " << gen_actions.size() << '\n';

    Pose pose{100, 200, 10, 2};
    ObjectOrientedActionSpace oos (pose, 3, 10, 100, 3, 1, 5, 3);
    vector<Object_Oriented_Action> oo_actions = oos.get_action_space();
    oos.view_action_space();
    cout << "Total actions: " << oo_actions.size() << '\n';

}
<|endoftext|>


<commit_before>// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <stdlib.h>

#if defined(OS_WIN)
#include <windows.h>
#endif

#include "base/environment.h"
#include "base/message_loop.h"
#include "base/stringprintf.h"
#include "base/threading/platform_thread.h"
#include "base/win/scoped_com_initializer.h"
#include "build/build_config.h"
#include "content/common/gpu/gpu_config.h"
#include "content/public/common/content_switches.h"
#include "content/public/common/main_function_params.h"
#include "content/gpu/gpu_child_thread.h"
#include "content/gpu/gpu_process.h"
#include "ui/gfx/gl/gl_surface.h"
#include "ui/gfx/gl/gl_switches.h"

#if defined(OS_WIN)
#include "content/common/gpu/media/dxva_video_decode_accelerator.h"
#include "sandbox/src/sandbox.h"
#endif

#if defined(USE_X11)
#include "ui/base/x/x11_util.h"
#endif

#if defined(TOOLKIT_USES_GTK)
#include "ui/gfx/gtk_util.h"
#endif

// Main function for starting the Gpu process.
int GpuMain(const content::MainFunctionParams& parameters) {
  base::Time start_time = base::Time::Now();

  const CommandLine& command_line = parameters.command_line;
  if (command_line.HasSwitch(switches::kGpuStartupDialog)) {
    ChildProcess::WaitForDebugger("Gpu");
  }

  if (!command_line.HasSwitch(switches::kSingleProcess)) {
#if defined(OS_WIN)
    // Prevent Windows from displaying a modal dialog on failures like not being
    // able to load a DLL.
    SetErrorMode(
        SEM_FAILCRITICALERRORS |
        SEM_NOGPFAULTERRORBOX |
        SEM_NOOPENFILEERRORBOX);
#elif defined(USE_X11)
    ui::SetDefaultX11ErrorHandlers();
#endif
#if defined(TOOLKIT_USES_GTK)
    gfx::GtkInitFromCommandLine(*CommandLine::ForCurrentProcess());
#endif
  }

  // Initialization of the OpenGL bindings may fail, in which case we
  // will need to tear down this process. However, we can not do so
  // safely until the IPC channel is set up, because the detection of
  // early return of a child process is implemented using an IPC
  // channel error. If the IPC channel is not fully set up between the
  // browser and GPU process, and the GPU process crashes or exits
  // early, the browser process will never detect it.  For this reason
  // we defer tearing down the GPU process until receiving the
  // GpuMsg_Initialize message from the browser.
  bool dead_on_arrival = false;

  // Load the GL implementation and locate the bindings before starting the GPU
  // watchdog because this can take a lot of time and the GPU watchdog might
  // terminate the GPU process.
  if (!gfx::GLSurface::InitializeOneOff()) {
    LOG(INFO) << "gfx::GLSurface::InitializeOneOff failed";
    dead_on_arrival = true;
  }

  base::win::ScopedCOMInitializer com_initializer;

#if defined(OS_WIN)
  sandbox::TargetServices* target_services =
      parameters.sandbox_info->target_services;
  // Initialize H/W video decoding stuff which fails in the sandbox.
  DXVAVideoDecodeAccelerator::PreSandboxInitialization();
  // For windows, if the target_services interface is not zero, the process
  // is sandboxed and we must call LowerToken() before rendering untrusted
  // content.
  if (target_services)
    target_services->LowerToken();
#endif

  MessageLoop::Type message_loop_type = MessageLoop::TYPE_UI;
#if defined(OS_WIN)
  // Unless we're running on desktop GL, we don't need a UI message
  // loop, so avoid its use to work around apparent problems with some
  // third-party software.
  message_loop_type = MessageLoop::TYPE_IO;
  if (command_line.HasSwitch(switches::kUseGL) &&
      command_line.GetSwitchValueASCII(switches::kUseGL) ==
          gfx::kGLImplementationDesktopName) {
      message_loop_type = MessageLoop::TYPE_UI;
  }
#endif

  MessageLoop main_message_loop(message_loop_type);
  base::PlatformThread::SetName("CrGpuMain");

  GpuProcess gpu_process;

  GpuChildThread* child_thread = new GpuChildThread(dead_on_arrival);

  child_thread->Init(start_time);

  gpu_process.set_main_thread(child_thread);

  main_message_loop.Run();

  child_thread->StopWatchdog();

  return 0;
}
<commit_msg>Preload setupapi.dll in GPU process.<commit_after>// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <stdlib.h>

#if defined(OS_WIN)
#include <windows.h>
#endif

#include "base/environment.h"
#include "base/message_loop.h"
#include "base/stringprintf.h"
#include "base/threading/platform_thread.h"
#include "base/win/scoped_com_initializer.h"
#include "build/build_config.h"
#include "content/common/gpu/gpu_config.h"
#include "content/public/common/content_switches.h"
#include "content/public/common/main_function_params.h"
#include "content/gpu/gpu_child_thread.h"
#include "content/gpu/gpu_process.h"
#include "ui/gfx/gl/gl_surface.h"
#include "ui/gfx/gl/gl_switches.h"

#if defined(OS_WIN)
#include "content/common/gpu/media/dxva_video_decode_accelerator.h"
#include "sandbox/src/sandbox.h"
#endif

#if defined(USE_X11)
#include "ui/base/x/x11_util.h"
#endif

#if defined(TOOLKIT_USES_GTK)
#include "ui/gfx/gtk_util.h"
#endif

// Main function for starting the Gpu process.
int GpuMain(const content::MainFunctionParams& parameters) {
  base::Time start_time = base::Time::Now();

  const CommandLine& command_line = parameters.command_line;
  if (command_line.HasSwitch(switches::kGpuStartupDialog)) {
    ChildProcess::WaitForDebugger("Gpu");
  }

  if (!command_line.HasSwitch(switches::kSingleProcess)) {
#if defined(OS_WIN)
    // Prevent Windows from displaying a modal dialog on failures like not being
    // able to load a DLL.
    SetErrorMode(
        SEM_FAILCRITICALERRORS |
        SEM_NOGPFAULTERRORBOX |
        SEM_NOOPENFILEERRORBOX);
#elif defined(USE_X11)
    ui::SetDefaultX11ErrorHandlers();
#endif
#if defined(TOOLKIT_USES_GTK)
    gfx::GtkInitFromCommandLine(*CommandLine::ForCurrentProcess());
#endif
  }

  // Initialization of the OpenGL bindings may fail, in which case we
  // will need to tear down this process. However, we can not do so
  // safely until the IPC channel is set up, because the detection of
  // early return of a child process is implemented using an IPC
  // channel error. If the IPC channel is not fully set up between the
  // browser and GPU process, and the GPU process crashes or exits
  // early, the browser process will never detect it.  For this reason
  // we defer tearing down the GPU process until receiving the
  // GpuMsg_Initialize message from the browser.
  bool dead_on_arrival = false;

  // Load the GL implementation and locate the bindings before starting the GPU
  // watchdog because this can take a lot of time and the GPU watchdog might
  // terminate the GPU process.
  if (!gfx::GLSurface::InitializeOneOff()) {
    LOG(INFO) << "gfx::GLSurface::InitializeOneOff failed";
    dead_on_arrival = true;
  }

  base::win::ScopedCOMInitializer com_initializer;

#if defined(OS_WIN)
  // Preload this DLL because the sandbox prevents it from loading.
  LoadLibrary(L"setupapi.dll");

  sandbox::TargetServices* target_services =
      parameters.sandbox_info->target_services;
  // Initialize H/W video decoding stuff which fails in the sandbox.
  DXVAVideoDecodeAccelerator::PreSandboxInitialization();
  // For windows, if the target_services interface is not zero, the process
  // is sandboxed and we must call LowerToken() before rendering untrusted
  // content.
  if (target_services)
    target_services->LowerToken();
#endif

  MessageLoop::Type message_loop_type = MessageLoop::TYPE_UI;
#if defined(OS_WIN)
  // Unless we're running on desktop GL, we don't need a UI message
  // loop, so avoid its use to work around apparent problems with some
  // third-party software.
  message_loop_type = MessageLoop::TYPE_IO;
  if (command_line.HasSwitch(switches::kUseGL) &&
      command_line.GetSwitchValueASCII(switches::kUseGL) ==
          gfx::kGLImplementationDesktopName) {
      message_loop_type = MessageLoop::TYPE_UI;
  }
#endif

  MessageLoop main_message_loop(message_loop_type);
  base::PlatformThread::SetName("CrGpuMain");

  GpuProcess gpu_process;

  GpuChildThread* child_thread = new GpuChildThread(dead_on_arrival);

  child_thread->Init(start_time);

  gpu_process.set_main_thread(child_thread);

  main_message_loop.Run();

  child_thread->StopWatchdog();

  return 0;
}
<|endoftext|>


<commit_before>/*===================================================================

The Medical Imaging Interaction Toolkit (MITK)

Copyright (c) German Cancer Research Center,
Division of Medical and Biological Informatics.
All rights reserved.

This software is distributed WITHOUT ANY WARRANTY; without
even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE.

See LICENSE.txt or http://www.mitk.org for details.

===================================================================*/

#include "mitkPhotoacousticBeamformingDMASFilter.h"
#include "mitkProperties.h"
#include "mitkImageReadAccessor.h"
#include <algorithm>
#include <itkImageIOBase.h>
#include <chrono>

mitk::BeamformingDMASFilter::BeamformingDMASFilter() : m_OutputData(nullptr), m_InputData(nullptr)
{
  this->SetNumberOfIndexedInputs(1);
  this->SetNumberOfRequiredInputs(1);

  m_Conf.Pitch = 0.0003;
  m_Conf.SpeedOfSound = 1540;
  m_Conf.SamplesPerLine = 2048;
  m_Conf.ReconstructionLines = 128;
  m_Conf.RecordTime = 0.00006;
  m_Conf.TransducerElements = 128;
}

mitk::BeamformingDMASFilter::~BeamformingDMASFilter()
{
}

void mitk::BeamformingDMASFilter::GenerateInputRequestedRegion()
{
  Superclass::GenerateInputRequestedRegion();

  mitk::Image* output = this->GetOutput();
  mitk::Image* input = const_cast< mitk::Image * > (this->GetInput());
  if (!output->IsInitialized())
  {
    return;
  }

  input->SetRequestedRegionToLargestPossibleRegion();

  //GenerateTimeInInputRegion(output, input);
}

void mitk::BeamformingDMASFilter::GenerateOutputInformation()
{
  mitk::Image::ConstPointer input = this->GetInput();
  mitk::Image::Pointer output = this->GetOutput();

  if ((output->IsInitialized()) && (this->GetMTime() <= m_TimeOfHeaderInitialization.GetMTime()))
    return;

  itkDebugMacro(<< "GenerateOutputInformation()");

  unsigned int dim[] = { m_Conf.ReconstructionLines, m_Conf.SamplesPerLine, input->GetDimension(2) };
  output->Initialize(mitk::MakeScalarPixelType<double>(), 3, dim);

  mitk::Vector3D spacing;
  spacing[0] = m_Conf.Pitch * m_Conf.TransducerElements * 1000 / m_Conf.ReconstructionLines;
  spacing[1] = m_Conf.RecordTime * m_Conf.SpeedOfSound / 2 * 1000 / m_Conf.SamplesPerLine;
  spacing[2] = 1;

  output->GetGeometry()->SetSpacing(spacing);
  output->GetGeometry()->Modified();
  output->SetPropertyList(input->GetPropertyList()->Clone());

  m_TimeOfHeaderInitialization.Modified();
}

void mitk::BeamformingDMASFilter::GenerateData()
{
  mitk::Image::ConstPointer input = this->GetInput();
  mitk::Image::Pointer output = this->GetOutput();

  float inputS = input->GetDimension(1);
  float inputL = input->GetDimension(0);

  float outputS = output->GetDimension(1);
  float outputL = output->GetDimension(0);

  float part = 0.07 * inputL;

  if (!output->IsInitialized())
  {
    return;
  }

  auto begin = std::chrono::high_resolution_clock::now(); // debbuging the performance...

  for (int i = 0; i < output->GetDimension(2); ++i) // seperate Slices should get Beamforming seperately applied
  {
    mitk::ImageReadAccessor inputReadAccessor(input, input->GetSliceData(i));

    m_OutputData = new double[m_Conf.ReconstructionLines*m_Conf.SamplesPerLine];
    m_InputDataPuffer = new double[input->GetDimension(0)*input->GetDimension(1)];

    if (input->GetPixelType().GetTypeAsString() == "scalar (double)")
    {
      m_InputData = (double*)inputReadAccessor.GetData();
    }
    else if (input->GetPixelType().GetTypeAsString() == "scalar (short)")
    {
      short* InputPuffer = (short*)inputReadAccessor.GetData();
      for (int l = 0; l < inputL; ++l)
      {
        for (int s = 0; s < inputS; ++s)
        {
          m_InputDataPuffer[l*(unsigned short)inputS + s] = (double)InputPuffer[l*(unsigned short)inputS + s];
        }
      }
      m_InputData = m_InputDataPuffer;
    }

    for (int l = 0; l < outputL; ++l)
    {
      for (int s = 0; s < outputS; ++s)
      {
        m_OutputData[l*(unsigned short)outputS + s] = 0;
      }
    }

    unsigned short AddSample1 = 0;
    unsigned short AddSample2 = 0;
    unsigned short maxLine = 0;
    unsigned short minLine = 0;
    float delayMultiplicator = 0;
    float l_i = 0;
    float s_i = 0;

    float l = 0;
    float x = 0;
    float root = 0;

    float mult = 0;

    if (m_Conf.DelayCalculationMethod == beamformingSettings::DelayCalc::Linear)
    {
      //linear delay
      for (unsigned short line = 0; line < outputL; ++line)
      {
        l_i = line / outputL * inputL;

        maxLine = (unsigned short)std::min((l_i + part) + 1, inputL);
        minLine = (unsigned short)std::max((l_i - part), 0.0f);

        maxLine = inputL;
        minLine = 0;

        l = (inputL / 2 - l_i) / inputL*m_Conf.Pitch*m_Conf.TransducerElements;

        for (unsigned short sample = 0; sample < outputS; ++sample)
        {
          s_i = sample / outputS * inputS;

          x = m_Conf.RecordTime / inputS * s_i * m_Conf.SpeedOfSound;
          root = l / sqrt(pow(l, 2) + pow(m_Conf.RecordTime / inputS * s_i * m_Conf.SpeedOfSound, 2));
          delayMultiplicator = root / (m_Conf.RecordTime*m_Conf.SpeedOfSound) *m_Conf.Pitch*m_Conf.TransducerElements / inputL;

          for (unsigned short l_s1 = minLine; l_s1 < maxLine-1; ++l_s1)
          {
            AddSample1 = delayMultiplicator * (l_s1 - l_i) + s_i;
            if (AddSample1 < inputS && AddSample1 >= 0)
            {
              for (unsigned short l_s2 = l_s1 + 1; l_s2 < maxLine; ++l_s2)
              {
                AddSample2 = delayMultiplicator * (l_s2 - l_i) + s_i;
                if (AddSample2 < inputS && AddSample2 >= 0)
                {
                  mult = m_InputData[l_s2 + AddSample2*(unsigned short)inputL] * m_InputData[l_s1 + AddSample1*(unsigned short)inputL];
                  m_OutputData[sample*(unsigned short)outputL + line] += sqrt(abs(mult)) * ((mult > 0) - (mult < 0));
                }
              }
            }
          }
        }
      }
    }/*
    else if (m_Conf.DelayCalculationMethod == beamformingSettings::DelayCalc::QuadApprox)
    {
      //quadratic delay
      for (unsigned short line = 0; line < outputL; ++line)
      {
        l_i = line / outputL * inputL;

        maxLine = (unsigned short)std::min((l_i + part) + 1, inputL);
        minLine = (unsigned short)std::max((l_i - part), 0.0f);

        for (unsigned short sample = 0; sample < outputS; ++sample)
        {
          s_i = sample / outputS * inputS;
          delayMultiplicator = pow((inputS / (m_Conf.RecordTime*m_Conf.SpeedOfSound) * (m_Conf.Pitch*m_Conf.TransducerElements) / inputL), 2) / s_i;

          for (unsigned short l_s = minLine; l_s < maxLine; ++l_s)
          {
            AddSample = delayMultiplicator * pow((l_s - l_i), 2) + s_i;
            if (AddSample < inputS && AddSample >= 0) {
              m_OutputData[sample*(unsigned short)outputL + line] += m_InputData[l_s + AddSample*(unsigned short)inputL];
            }
          }
        }
      }
    }
    else if (m_Conf.DelayCalculationMethod == beamformingSettings::DelayCalc::Spherical)
    {
      //exact delay
      for (unsigned short line = 0; line < outputL; ++line)
      {

        l_i = line / outputL * inputL;

        maxLine = (unsigned short)std::min((l_i + part) + 1, inputL);
        minLine = (unsigned short)std::max((l_i - part), 0.0f);

        for (unsigned short sample = 0; sample < outputS; ++sample)
        {
          s_i = sample / outputS * inputS;

          for (unsigned short l_s = minLine; l_s < maxLine; ++l_s)
          {
            AddSample = (int)sqrt(
              pow(s_i, 2)
              +
              pow((inputS / (m_Conf.RecordTime*m_Conf.SpeedOfSound) * ((l_s - l_i)*m_Conf.Pitch*m_Conf.TransducerElements) / inputL), 2)
            );
            if (AddSample < inputS && AddSample >= 0) {
              m_OutputData[sample*(unsigned short)outputL + line] += m_InputData[l_s + AddSample*(unsigned short)inputL];
              //MITK_INFO<< m_InputData[l_s + AddSample*(int)inputL];
            }
          }
        }
      }
    }*/

    output->SetSlice(m_OutputData, i);

    delete[] m_OutputData;
    delete[] m_InputDataPuffer;
    m_OutputData = nullptr;
    m_InputData = nullptr;
  }
  m_TimeOfHeaderInitialization.Modified();

  auto end = std::chrono::high_resolution_clock::now();
  MITK_INFO << "Beamforming completed in " << ((float)std::chrono::duration_cast<std::chrono::nanoseconds>(end - begin).count()) / 1000000 << "ms" << std::endl;
}

void mitk::BeamformingDMASFilter::Configure(beamformingSettings settings)
{
  m_Conf = settings;
}<commit_msg>-little fix, needs more fix<commit_after>/*===================================================================

The Medical Imaging Interaction Toolkit (MITK)

Copyright (c) German Cancer Research Center,
Division of Medical and Biological Informatics.
All rights reserved.

This software is distributed WITHOUT ANY WARRANTY; without
even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE.

See LICENSE.txt or http://www.mitk.org for details.

===================================================================*/

#include "mitkPhotoacousticBeamformingDMASFilter.h"
#include "mitkProperties.h"
#include "mitkImageReadAccessor.h"
#include <algorithm>
#include <itkImageIOBase.h>
#include <chrono>

mitk::BeamformingDMASFilter::BeamformingDMASFilter() : m_OutputData(nullptr), m_InputData(nullptr)
{
  this->SetNumberOfIndexedInputs(1);
  this->SetNumberOfRequiredInputs(1);

  m_Conf.Pitch = 0.0003;
  m_Conf.SpeedOfSound = 1540;
  m_Conf.SamplesPerLine = 2048;
  m_Conf.ReconstructionLines = 128;
  m_Conf.RecordTime = 0.00006;
  m_Conf.TransducerElements = 128;
}

mitk::BeamformingDMASFilter::~BeamformingDMASFilter()
{
}

void mitk::BeamformingDMASFilter::GenerateInputRequestedRegion()
{
  Superclass::GenerateInputRequestedRegion();

  mitk::Image* output = this->GetOutput();
  mitk::Image* input = const_cast< mitk::Image * > (this->GetInput());
  if (!output->IsInitialized())
  {
    return;
  }

  input->SetRequestedRegionToLargestPossibleRegion();

  //GenerateTimeInInputRegion(output, input);
}

void mitk::BeamformingDMASFilter::GenerateOutputInformation()
{
  mitk::Image::ConstPointer input = this->GetInput();
  mitk::Image::Pointer output = this->GetOutput();

  if ((output->IsInitialized()) && (this->GetMTime() <= m_TimeOfHeaderInitialization.GetMTime()))
    return;

  itkDebugMacro(<< "GenerateOutputInformation()");

  unsigned int dim[] = { m_Conf.ReconstructionLines, m_Conf.SamplesPerLine, input->GetDimension(2) };
  output->Initialize(mitk::MakeScalarPixelType<double>(), 3, dim);

  mitk::Vector3D spacing;
  spacing[0] = m_Conf.Pitch * m_Conf.TransducerElements * 1000 / m_Conf.ReconstructionLines;
  spacing[1] = m_Conf.RecordTime * m_Conf.SpeedOfSound / 2 * 1000 / m_Conf.SamplesPerLine;
  spacing[2] = 1;

  output->GetGeometry()->SetSpacing(spacing);
  output->GetGeometry()->Modified();
  output->SetPropertyList(input->GetPropertyList()->Clone());

  m_TimeOfHeaderInitialization.Modified();
}

void mitk::BeamformingDMASFilter::GenerateData()
{
  mitk::Image::ConstPointer input = this->GetInput();
  mitk::Image::Pointer output = this->GetOutput();

  float inputS = input->GetDimension(1);
  float inputL = input->GetDimension(0);

  float outputS = output->GetDimension(1);
  float outputL = output->GetDimension(0);

  float part = 0.07 * inputL;

  if (!output->IsInitialized())
  {
    return;
  }

  auto begin = std::chrono::high_resolution_clock::now(); // debbuging the performance...

  for (int i = 0; i < output->GetDimension(2); ++i) // seperate Slices should get Beamforming seperately applied
  {
    mitk::ImageReadAccessor inputReadAccessor(input, input->GetSliceData(i));

    m_OutputData = new double[m_Conf.ReconstructionLines*m_Conf.SamplesPerLine];
    m_InputDataPuffer = new double[input->GetDimension(0)*input->GetDimension(1)];

    if (input->GetPixelType().GetTypeAsString() == "scalar (double)")
    {
      m_InputData = (double*)inputReadAccessor.GetData();
    }
    else if (input->GetPixelType().GetTypeAsString() == "scalar (short)")
    {
      short* InputPuffer = (short*)inputReadAccessor.GetData();
      for (int l = 0; l < inputL; ++l)
      {
        for (int s = 0; s < inputS; ++s)
        {
          m_InputDataPuffer[l*(unsigned short)inputS + s] = (double)InputPuffer[l*(unsigned short)inputS + s];
        }
      }
      m_InputData = m_InputDataPuffer;
    }

    for (int l = 0; l < outputL; ++l)
    {
      for (int s = 0; s < outputS; ++s)
      {
        m_OutputData[l*(unsigned short)outputS + s] = 0;
      }
    }

    unsigned short AddSample1 = 0;
    unsigned short AddSample2 = 0;
    unsigned short maxLine = 0;
    unsigned short minLine = 0;
    float delayMultiplicator = 0;
    float l_i = 0;
    float s_i = 0;

    float l = 0;
    float x = 0;
    float root = 0;

    float mult = 0;

    if (m_Conf.DelayCalculationMethod == beamformingSettings::DelayCalc::Linear)
    {
      //linear delay
      for (unsigned short line = 0; line < outputL; ++line)
      {
        l_i = line / outputL * inputL;

        maxLine = (unsigned short)std::min((l_i + part) + 1, inputL);
        minLine = (unsigned short)std::max((l_i - part), 0.0f);

        l = (inputL / 2 - l_i) / inputL*m_Conf.Pitch*m_Conf.TransducerElements;

        for (unsigned short sample = 0; sample < outputS; ++sample)
        {
          s_i = sample / outputS * inputS;

          x = m_Conf.RecordTime / inputS * s_i * m_Conf.SpeedOfSound;
          root = l / sqrt(pow(l, 2) + pow(m_Conf.RecordTime / inputS * s_i * m_Conf.SpeedOfSound, 2));
          delayMultiplicator = root / (m_Conf.RecordTime*m_Conf.SpeedOfSound) *m_Conf.Pitch*m_Conf.TransducerElements / inputL;

          for (unsigned short l_s1 = minLine; l_s1 < maxLine-1; ++l_s1)
          {
            AddSample1 = delayMultiplicator * (l_s1 - l_i) + s_i;
            if (AddSample1 < inputS && AddSample1 >= 0)
            {
              for (unsigned short l_s2 = l_s1 + 1; l_s2 < maxLine; ++l_s2)
              {
                AddSample2 = delayMultiplicator * (l_s2 - l_i) + s_i;
                if (AddSample2 < inputS && AddSample2 >= 0)
                {
                  mult = m_InputData[l_s2 + AddSample2*(unsigned short)inputL] * m_InputData[l_s1 + AddSample1*(unsigned short)inputL];
                  m_OutputData[sample*(unsigned short)outputL + line] += sqrt(abs(mult)) * ((mult > 0) - (mult < 0));
                }
              }
            }
          }
        }
      }
    }/*
    else if (m_Conf.DelayCalculationMethod == beamformingSettings::DelayCalc::QuadApprox)
    {
      //quadratic delay
      for (unsigned short line = 0; line < outputL; ++line)
      {
        l_i = line / outputL * inputL;

        maxLine = (unsigned short)std::min((l_i + part) + 1, inputL);
        minLine = (unsigned short)std::max((l_i - part), 0.0f);

        for (unsigned short sample = 0; sample < outputS; ++sample)
        {
          s_i = sample / outputS * inputS;
          delayMultiplicator = pow((inputS / (m_Conf.RecordTime*m_Conf.SpeedOfSound) * (m_Conf.Pitch*m_Conf.TransducerElements) / inputL), 2) / s_i;

          for (unsigned short l_s = minLine; l_s < maxLine; ++l_s)
          {
            AddSample = delayMultiplicator * pow((l_s - l_i), 2) + s_i;
            if (AddSample < inputS && AddSample >= 0) {
              m_OutputData[sample*(unsigned short)outputL + line] += m_InputData[l_s + AddSample*(unsigned short)inputL];
            }
          }
        }
      }
    }
    else if (m_Conf.DelayCalculationMethod == beamformingSettings::DelayCalc::Spherical)
    {
      //exact delay
      for (unsigned short line = 0; line < outputL; ++line)
      {

        l_i = line / outputL * inputL;

        maxLine = (unsigned short)std::min((l_i + part) + 1, inputL);
        minLine = (unsigned short)std::max((l_i - part), 0.0f);

        for (unsigned short sample = 0; sample < outputS; ++sample)
        {
          s_i = sample / outputS * inputS;

          for (unsigned short l_s = minLine; l_s < maxLine; ++l_s)
          {
            AddSample = (int)sqrt(
              pow(s_i, 2)
              +
              pow((inputS / (m_Conf.RecordTime*m_Conf.SpeedOfSound) * ((l_s - l_i)*m_Conf.Pitch*m_Conf.TransducerElements) / inputL), 2)
            );
            if (AddSample < inputS && AddSample >= 0) {
              m_OutputData[sample*(unsigned short)outputL + line] += m_InputData[l_s + AddSample*(unsigned short)inputL];
              //MITK_INFO<< m_InputData[l_s + AddSample*(int)inputL];
            }
          }
        }
      }
    }*/

    output->SetSlice(m_OutputData, i);

    delete[] m_OutputData;
    delete[] m_InputDataPuffer;
    m_OutputData = nullptr;
    m_InputData = nullptr;
  }
  m_TimeOfHeaderInitialization.Modified();

  auto end = std::chrono::high_resolution_clock::now();
  MITK_INFO << "Beamforming completed in " << ((float)std::chrono::duration_cast<std::chrono::nanoseconds>(end - begin).count()) / 1000000 << "ms" << std::endl;
}

void mitk::BeamformingDMASFilter::Configure(beamformingSettings settings)
{
  m_Conf = settings;
}<|endoftext|>


<commit_before>// CommonFunc.cpp -- source file
/*
 *
 * Author: septimomend (Ivan Chapkailo)
 *
 * 02.07.2017
 *
 */

#include "stdafx.h"
#include "CommonFunc.h"

Common::Common(AllControllers* all) : *m_cnfg(all->getConfigObj())
{
}

void Common::drawRows(Adbfr* abfr);
{
  // TODO
}

void Common::drawStatusBar(Adbfr* abfr)
{
  // TODO
}

void Common::drawMessageBar(Adbfr* abfr)
{
  // TODO
}

void Common::scrolling()
{
  // TODO
}

void Common::statusMsg(const char *fmt, ...)
{
  va_list arg;         // for unknown number of parameters
  va_start(arg, fmt);  // initialize arg
  vsnprintf(cnfg.statusMessage, sizeof(cnfg.statusMessage), fmt, arg); // output parameters to statusMessage
  va_end(arg); // end
  cnfg.statusMessageTime = time(NULL); // gets time
}

void Common::updateScreen()
{
  scrolling();

  m_abfr = ADBFR_IMPL; // implement to NULL

  m_abfr.reallocateBfr("\x1b[?25l", 6); // reallocate data
  m_abfr.reallocateBfr("\x1b[H", 3);    // reallocate data

  /*
   * draw rows, message bar and status bar
   */
  drawRows(&m_abfr);
  drawStatusBar(&m_abfr);
  drawMessageBar(&m_abfr);

  /*
   * write to buff cursor | position
   */
  char buff[32];
  snprintf(buff, sizeof(buff), "\x1b[%d;%dH", (m_cnfg->configY - m_cnfg->disableRow) + 1, (m_cnfg->rowX - m_cnfg->disableClr) + 1);
  m_abfr.reallocateBfr(buff, strlen(buff));

  m_abfr.reallocateBfr("\x1b[?25h", 6);

  /*
   * update screen
   */
  write(STDOUT_FILENO, ab.b, ab.len);
  m_abfr.freeBfr(); // free memory
}

char* Common::callPrompt(char *prompt, void (*callback)(char*, int))
{
  size_t buffsize = 128;
  char* bfr = malloc(buffsize); // allocate memory

  size_t bufflen = 0;           // lenght
  bfr[0] = '\0';

  while (1)
  {
    statusMsg(prompt, bfr); // set prompt
    updateScreen();         // and update screen

    int key = tml.whatKey();  // read key

    if (key == DELETE_KEY || key == CTRL_KEY('h') || key == BACKSPACE)
    {
      if (bufflen != 0)         // if buffer is not empty
        bfr[--bufflen] = '\0';  // set end of row
    }
    else if (key == '\x1b')     // if this is ESC
    {
      statusMsg("");          // erase
      if (callback)           // if callback is not NULL
        callback(bfr, key);   // call func for callback which pointed by callback()
      free(bfr);              // free memory
      return NULL;            // and cancel
    }
    else if (key == '\r')     // if carriage return (move the cursor at the start of the line)
    {
      if (bufflen != 0)       // and bufflen is not empty
      {
        statusMsg("");        // clean message
        if (callback)
          callback(bfr, key); // and get callback
        return bfr;           // returning of buffer
      }
    }
    else if (!iscntrl(key) && key < 128) // checks, whether the argument, transmitted via the parameter сharacter, control character
    {
      /*
       * reallocation of buffer if needs
       */
      if (bufflen == buffsize - 1)
      {
        buffsize *= 2;
        bfr = realloc(bfr, buffsize);
      }
      bfr[bufflen++] = key; // write this key to buffer
      bfr[bufflen] = '\0';  // and end of row
    }

    if (callback)
      callback(bfr, key);   // call of callback
}
<commit_msg>TODO: add definition of funcs<commit_after>// CommonFunc.cpp -- source file
/*
 *
 * Author: septimomend (Ivan Chapkailo)
 *
 * 02.07.2017
 *
 */

#include "stdafx.h"
#include "CommonFunc.h"

Common::Common(AllControllers* all) : *m_cnfg(all->getConfigObj())
{
}

void Common::drawRows(Adbfr* abfr);
{
  // TODO
}

void Common::drawStatusBar(Adbfr* abfr)
{
  // TODO
}

void Common::drawMessageBar(Adbfr* abfr)
{
  // TODO
}

void Common::scrolling()
{
  // TODO
}

void Common::statusMsg(const char *fmt, ...)
{
  va_list arg;         // for unknown number of parameters
  va_start(arg, fmt);  // initialize arg
  vsnprintf(cnfg.statusMessage, sizeof(cnfg.statusMessage), fmt, arg); // output parameters to statusMessage
  va_end(arg); // end
  cnfg.statusMessageTime = time(NULL); // gets time
}

void Common::updateScreen()
{
  scrolling();

  m_abfr = ADBFR_IMPL; // implement to NULL

  m_abfr.reallocateBfr("\x1b[?25l", 6); // reallocate data
  m_abfr.reallocateBfr("\x1b[H", 3);    // reallocate data

  /*
   * draw rows, message bar and status bar
   */
  drawRows(&m_abfr);
  drawStatusBar(&m_abfr);
  drawMessageBar(&m_abfr);

  /*
   * write to buff cursor | position
   */
  char buff[32];
  snprintf(buff, sizeof(buff), "\x1b[%d;%dH", (m_cnfg->configY - m_cnfg->disableRow) + 1, (m_cnfg->rowX - m_cnfg->disableClr) + 1);
  m_abfr.reallocateBfr(buff, strlen(buff));

  m_abfr.reallocateBfr("\x1b[?25h", 6);

  /*
   * update screen
   */
  write(STDOUT_FILENO, ab.b, ab.len);
  m_abfr.freeBfr(); // free memory
}

char* Common::callPrompt(char *prompt, void (*callback)(char*, int))
{
  size_t buffsize = 128;
  char* bfr = malloc(buffsize); // allocate memory

  size_t bufflen = 0;           // lenght
  bfr[0] = '\0';

  while (1)
  {
    statusMsg(prompt, bfr); // set prompt
    updateScreen();         // and update screen

    int key = tml.whatKey();  // read key

    if (key == DELETE_KEY || key == CTRL_KEY('h') || key == BACKSPACE)
    {
      if (bufflen != 0)         // if buffer is not empty
        bfr[--bufflen] = '\0';  // set end of row
    }
    else if (key == '\x1b')     // if this is ESC
    {
      statusMsg("");          // erase
      if (callback)           // if callback is not NULL
        callback(bfr, key);   // call func for callback which pointed by callback()
      free(bfr);              // free memory
      return NULL;            // and cancel
    }
    else if (key == '\r')     // if carriage return (move the cursor at the start of the line)
    {
      if (bufflen != 0)       // and bufflen is not empty
      {
        statusMsg("");        // clean message
        if (callback)
          callback(bfr, key); // and get callback
        return bfr;           // returning of buffer
      }
    }
    else if (!iscntrl(key) && key < 128) // checks, whether the argument, transmitted via the parameter сharacter, control character
    {
      /*
       * reallocation of buffer if needs
       */
      if (bufflen == buffsize - 1)
      {
        buffsize *= 2;
        bfr = realloc(bfr, buffsize);
      }
      bfr[bufflen++] = key; // write this key to buffer
      bfr[bufflen] = '\0';  // and end of row
    }

    if (callback)
      callback(bfr, key);   // call of callback
}

void Common::moveCursor(int key)
{
  // TODO
}

void Common::processingKeypress()
{
  // TODO
}
<|endoftext|>


<commit_before>//
//  yas_processing_send_signal_processor.cpp
//

#include "yas_processing_send_signal_processor.h"
#include "yas_processing_processor.h"
#include "yas_processing_module.h"
#include "yas_processing_channel.h"
#include "yas_processing_signal_event.h"
#include "yas_stl_utils.h"
#include "yas_boolean.h"

using namespace yas;

template <typename T>
processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<T> handler) {
    return [handler = std::move(handler)](time::range const &current_time_range, connector_map_t const &,
                                          connector_map_t const &output_connectors, stream &stream) {
        if (handler) {
            for (auto const &connector_pair : output_connectors) {
                auto const &connector_idx = connector_pair.first;
                auto const &connector = connector_pair.second;

                auto const &ch_idx = connector.channel_index;

                if (stream.has_channel(ch_idx)) {
                    auto &channel = stream.channel(ch_idx);
                    processing::time::range combined_time_range = current_time_range;

                    auto predicate = [&current_time_range](auto const &pair) {
                        if (pair.first.can_combine(current_time_range)) {
                            return true;
                        }
                        return false;
                    };

                    auto const filtered_events = channel.filtered_events<T, signal_event>(predicate);

                    if (filtered_events.size() > 0) {
                        for (auto const &pair : filtered_events) {
                            combined_time_range = *combined_time_range.combine(pair.first);
                        }

                        std::vector<T> vec(combined_time_range.length);
                        for (auto const &pair : filtered_events) {
                            auto const &time_range = pair.first;
                            auto const length = time_range.length;
                            auto const dst_idx = time_range.frame - combined_time_range.frame;
                            auto *dst_ptr = &vec[dst_idx];
                            signal_event const signal = pair.second;
                            signal.copy_to<T>(dst_ptr, length);
                        }

                        channel.erase_event<T, signal_event>(std::move(predicate));

                        handler(current_time_range, stream.sync_source(), ch_idx, connector_idx,
                                &vec[current_time_range.frame - combined_time_range.frame]);

                        channel.insert_event(time{combined_time_range}, signal_event{std::move(vec)});

                        return;
                    }
                } else {
                    stream.add_channel(ch_idx);
                }

                std::vector<T> vec(current_time_range.length);

                handler(current_time_range, stream.sync_source(), ch_idx, connector_idx, vec.data());

                auto &channel = stream.channel(ch_idx);
                channel.insert_event(time{current_time_range}, signal_event{std::move(vec)});
            }
        }
    };
}

template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<double>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<float>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int64_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int32_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int16_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int8_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint64_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint32_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint16_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint8_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<boolean>);
<commit_msg>update send_signal_processor<commit_after>//
//  yas_processing_send_signal_processor.cpp
//

#include "yas_processing_send_signal_processor.h"
#include "yas_processing_processor.h"
#include "yas_processing_module.h"
#include "yas_processing_channel.h"
#include "yas_processing_signal_event.h"
#include "yas_stl_utils.h"
#include "yas_boolean.h"

using namespace yas;

template <typename T>
processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<T> handler) {
    return [handler = std::move(handler)](time::range const &current_time_range, connector_map_t const &,
                                          connector_map_t const &output_connectors, stream &stream) {
        if (handler) {
            for (auto const &connector_pair : output_connectors) {
                auto const &connector_idx = connector_pair.first;
                auto const &connector = connector_pair.second;

                auto const &ch_idx = connector.channel_index;
                auto &channel = stream.add_channel(ch_idx);

                if (channel.events().size() > 0) {
                    processing::time::range combined_time_range = current_time_range;

                    auto predicate = [&current_time_range](auto const &pair) {
                        if (pair.first.can_combine(current_time_range)) {
                            return true;
                        }
                        return false;
                    };

                    auto const filtered_events = channel.filtered_events<T, signal_event>(predicate);

                    if (filtered_events.size() > 0) {
                        for (auto const &pair : filtered_events) {
                            combined_time_range = *combined_time_range.combine(pair.first);
                        }

                        std::vector<T> vec(combined_time_range.length);
                        for (auto const &pair : filtered_events) {
                            auto const &time_range = pair.first;
                            auto const length = time_range.length;
                            auto const dst_idx = time_range.frame - combined_time_range.frame;
                            auto *dst_ptr = &vec[dst_idx];
                            signal_event const signal = pair.second;
                            signal.copy_to<T>(dst_ptr, length);
                        }

                        channel.erase_event<T, signal_event>(std::move(predicate));

                        handler(current_time_range, stream.sync_source(), ch_idx, connector_idx,
                                &vec[current_time_range.frame - combined_time_range.frame]);

                        channel.insert_event(time{combined_time_range}, signal_event{std::move(vec)});

                        return;
                    }
                }

                std::vector<T> vec(current_time_range.length);

                handler(current_time_range, stream.sync_source(), ch_idx, connector_idx, vec.data());

                channel.insert_event(time{current_time_range}, signal_event{std::move(vec)});
            }
        }
    };
}

template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<double>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<float>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int64_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int32_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int16_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<int8_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint64_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint32_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint16_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<uint8_t>);
template processing::processor_f processing::make_send_signal_processor(processing::send_signal_process_f<boolean>);
<|endoftext|>