Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 11 additions & 4 deletions src/deepcpp/controller.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -137,18 +137,22 @@ void Controller::clear()
y_ini.clear();
}

std::vector<VectorXd> Controller::apply(const std::vector<VectorXd> &target)
std::vector<VectorXd> Controller::apply(const std::vector<VectorXd> &target, const std::vector<VectorXd> &offset)
{
if (!is_initialized())
return {};

check_dimensions(target, "target", target_size, output_dims);

if (!offset.empty())
check_dimensions(offset, "offset", target_size, input_dims);

// Flatten
VectorXd target_ = concat(target);
VectorXd offset_ = offset.empty() ? VectorXd::Zero(target_size * output_dims) : concat(offset);

auto x = concat(u_ini.get(), y_ini.get());
auto w = M_u.transpose() * Q * (target_ - M_x * x);
auto w = M_u.transpose() * Q * (target_ - M_x * x) + R * offset_;
auto u_star = G.ldlt().solve(w).eval();

if (input_constrain_fkt != nullptr)
Expand All @@ -163,7 +167,10 @@ std::vector<VectorXd> Controller::apply(const std::vector<VectorXd> &target)
return split(u_star, target_size);
}

std::vector<VectorXd> Controller::apply(const VectorXd &target)
std::vector<VectorXd> Controller::apply(const VectorXd &target, const VectorXd &offset)
{
return apply(std::vector<VectorXd>{target});
return apply(
std::vector<VectorXd>{target},
offset.size() == 0 ? std::vector<VectorXd>{} : std::vector<VectorXd>{offset}
);
}
4 changes: 2 additions & 2 deletions src/deepcpp/controller.h
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,6 @@ class Controller
bool is_initialized() const;
void update(VectorXd u, VectorXd y);
void clear();
std::vector<VectorXd> apply(const std::vector<VectorXd> &);
std::vector<VectorXd> apply(const VectorXd &);
std::vector<VectorXd> apply(const std::vector<VectorXd> &target, const std::vector<VectorXd> &offset = {});
std::vector<VectorXd> apply(const VectorXd &target, const VectorXd &offset = {});
};
25 changes: 23 additions & 2 deletions tests/deepcpp/test_controller.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -76,12 +76,17 @@ void warm_up_controller(Controller& controller, DiscreteLTI& system, const Vecto

// Control the system for a given number of time steps.
// Returns the output of the system after the last time step.
VectorXd control_system(Controller& controller, DiscreteLTI& system, const std::vector<VectorXd>& target, int time_steps)
VectorXd control_system(
Controller& controller,
DiscreteLTI& system,
const std::vector<VectorXd>& target,
int time_steps,
const std::vector<VectorXd>& offset = {})
{
VectorXd u, y;
for (int i = 0; i < time_steps; ++i)
{
u = controller.apply(target).front();
u = controller.apply(target, offset).front();
y = system.apply(u);
controller.update(u, y);
}
Expand Down Expand Up @@ -119,6 +124,14 @@ TEST_F(Test_1D_in_1D_out_LTI, Constrained)
expect_near(y, target[0], 1e-5);
}

TEST_F(Test_1D_in_1D_out_LTI, Offset)
{
Controller controller{u_d, y_d, T_ini, target.size(), /*Q*/1.0, /*R*/0.001};
warm_up_controller(controller, system, Vector(1));
VectorXd y = control_system(controller, system, target, T_ini, {Vector(10), Vector(10)});
expect_near(y, target[0], 0.02);
}


class Test_2D_in_3D_out_LTI : public ::testing::Test
{
Expand Down Expand Up @@ -150,3 +163,11 @@ TEST_F(Test_2D_in_3D_out_LTI, Constrained)
VectorXd y = control_system(controller, system, target, 2 * T_ini);
expect_near(y, target[0], 0.05);
}

TEST_F(Test_2D_in_3D_out_LTI, Offset)
{
Controller controller{u_d, y_d, T_ini, target.size(), /*Q*/1.0, /*R*/0.001};
warm_up_controller(controller, system, Vector(1, 1));
VectorXd y = control_system(controller, system, target, T_ini, {Vector(1, 1)});
expect_near(y, target[0], 0.05);
}