Esempio n. 1
0
def custom_dynamic(states: MX, controls: MX, parameters: MX,
                   nlp: NonLinearProgram) -> tuple:
    """
    The dynamics of the system using an external force (see custom_dynamics for more explanation)

    Parameters
    ----------
    states: MX
        The current states of the system
    controls: MX
        The current controls of the system
    parameters: MX
        The current parameters of the system
    nlp: NonLinearProgram
        A reference to the phase of the ocp

    Returns
    -------
    The state derivative
    """

    q = DynamicsFunctions.get(nlp.states["q"], states)
    qdot = DynamicsFunctions.get(nlp.states["qdot"], states)
    tau = DynamicsFunctions.get(nlp.controls["tau"], controls)

    force_vector = MX.zeros(6)
    force_vector[5] = 100 * q[0]**2

    f_ext = biorbd.VecBiorbdSpatialVector()
    f_ext.append(biorbd.SpatialVector(force_vector))
    qddot = nlp.model.ForwardDynamics(q, qdot, tau, f_ext).to_mx()

    return qdot, qddot
Esempio n. 2
0
    def test_blockdiag(self):
        # Test blockdiag with DM
        correct_res = DM([[1, 1, 0, 0, 0], [1, 1, 0, 0, 0], [0, 0, 1, 1, 1],
                          [0, 0, 1, 1, 1], [0, 0, 1, 1, 1]])

        a = DM.ones(2, 2)
        b = DM.ones(3, 3)
        res = blockdiag(a, b)
        self.assertTrue(is_equal(res, correct_res))

        # MX and DM mix
        a = MX.sym('a', 2, 2)
        b = DM.ones(1, 1)
        correct_res = MX.zeros(3, 3)
        correct_res[:2, :2] = a
        correct_res[2:, 2:] = b

        res = blockdiag(a, b)
        self.assertTrue(is_equal(res, correct_res, 30))

        # SX and DM mix
        a = SX.sym('a', 2, 2)
        b = DM.ones(1, 1)
        correct_res = SX.zeros(3, 3)
        correct_res[:2, :2] = a
        correct_res[2:, 2:] = b

        res = blockdiag(a, b)
        self.assertTrue(is_equal(res, correct_res, 30))

        # SX and MX
        a = SX.sym('a', 2, 2)
        b = MX.sym('b', 2, 2)
        self.assertRaises(ValueError, blockdiag, a, b)
Esempio n. 3
0
def blockdiag(*matrices_list):
    """Receives a list of matrices and return a block diagonal.

    :param DM|MX|SX matrices_list: list of matrices
    """

    size_1 = sum([m.size1() for m in matrices_list])
    size_2 = sum([m.size2() for m in matrices_list])
    matrix_types = [type(m) for m in matrices_list]

    if SX in matrix_types and MX in matrix_types:
        raise ValueError(
            "Can not mix MX and SX types. Types give: {}".format(matrix_types))

    if SX in matrix_types:
        matrix = SX.zeros(size_1, size_2)
    elif MX in matrix_types:
        matrix = MX.zeros(size_1, size_2)
    else:
        matrix = DM.zeros(size_1, size_2)

    index_1 = 0
    index_2 = 0

    for m in matrices_list:
        matrix[index_1:index_1 + m.size1(), index_2:index_2 + m.size2()] = m
        index_1 += m.size1()
        index_2 += m.size2()

    return matrix
Esempio n. 4
0
def contact_force_continuity(pen_node: PenaltyNode, idx_pre, idx_post):
    final_contact_z = sum1(pen_node[0].nlp.contact_forces_func(pen_node[0].x[0], pen_node[0].u[0], pen_node[0].p)[idx_pre, :])
    if idx_post:
        starting_contact_z = sum1(pen_node[1].nlp.contact_forces_func(pen_node[1].x[0], pen_node[1].u[0], pen_node[1].p)[idx_post, :])
    else:
        starting_contact_z = MX.zeros(final_contact_z.shape)

    return final_contact_z - starting_contact_z
Esempio n. 5
0
 def my_parameter_function(biorbd_model, value, extra_value):
     new_gravity = MX.zeros(3, 1)
     new_gravity[2] = value + extra_value
     biorbd_model.setGravity(new_gravity)
def onestep_reachability(p_center,
                         ssm,
                         k_ff,
                         l_mu,
                         l_sigma,
                         q_shape=None,
                         k_fb=None,
                         c_safety=1.,
                         a=None,
                         b=None,
                         t_z_gp=None):
    """ Overapproximate the reachable set of states under affine control law

    given a system of the form:
        x_{t+1} = \mathcal{N}(\mu(x_t,u_t), \Sigma(x_t,u_t)),
    where x,\mu \in R^{n_s}, u \in R^{n_u} and \Sigma^{n_s \times n_s} are given bei the
    gp predictive mean and variance respectively
    we approximate the reachset of a set of inputs x_t \in \epsilon(p,Q)
    describing an ellipsoid with center p and shape matrix Q
    under the control low u_t = Kx_t + k

    Parameters
    ----------
        p_center: n_s x 1 array[float]
            Center of state ellipsoid
        gp: SimpleGPModel
            The gp representing the dynamics
        k_ff: n_u x 1 array[float]
            The additive term of the controls
        l_mu: 1d_array of size n_s
            Set of Lipschitz constants on the Gradients of the mean function (per state
            dimension)
        l_sigma: 1d_array of size n_s
            Set of Lipschitz constants of the predictive variance (per state dimension)
        q_shape: np.ndarray[float], array of shape n_s x n_s, optional
            Shape matrix of state ellipsoid
        k_fb: n_u x n_s array[float], optional
            The state feedback-matrix for the controls
        c_safety: float, optional
            The scaling of the semi-axes of the uncertainty matrix
            corresponding to a level-set of the gaussian pdf.

    Returns:
    -------
        p_new: n_s x 1 array[float]
            Center of the overapproximated next state ellipsoid
        Q_new: np.ndarray[float], array of shape n_s x n_s
            Shape matrix of the overapproximated next state ellipsoid.
    """
    n_s = np.shape(p_center)[0]
    n_u = np.shape(k_ff)[0]

    if t_z_gp is None:
        t_z_gp = MX.eye(n_s)

    if a is None:
        a = MX.eye(n_s)
        b = MX.zeros(n_s, n_u)

    if q_shape is None:  # the state is a point

        u_p = k_ff

        x_bar = mtimes(t_z_gp, p_center)

        mu_new, pred_var, _ = ssm(x_bar.T, u_p.T)

        p_lin = mtimes(a, p_center) + mtimes(b, u_p)
        p_1 = p_lin + mu_new

        rkhs_bound = c_safety * sqrt(pred_var)
        q_1 = ellipsoid_from_rectangle(rkhs_bound)

        return p_1, q_1, pred_var
    else:  # the state is a (ellipsoid) set

        # compute the linearization centers
        x_bar = mtimes(t_z_gp, p_center)  # center of the state ellipsoid
        u_bar = k_ff  # u_bar = K*(u_bar-u_bar) + k = k

        z_bar = vertcat(x_bar, u_bar)

        # compute the zero and first order matrices

        mu_0, sigm_0, jac_mu = ssm(x_bar.T, u_bar.T)

        n_x_in = np.shape(t_z_gp)[0]

        a_mu = jac_mu[:, :n_x_in]
        a_mu = mtimes(a_mu, t_z_gp)
        b_mu = jac_mu[:, n_x_in:]

        # reach set of the affine terms
        H = a + a_mu + mtimes(b_mu + b, k_fb)

        p_0 = mu_0 + mtimes(a, p_center) + mtimes(b, u_bar)

        Q_0 = mtimes(H, mtimes(q_shape, H.T))

        ub_mean, ub_sigma = compute_remainder_overapproximations(
            q_shape, k_fb, l_mu, l_sigma)
        # computing the box approximate to the lagrange remainder
        Q_lagrange_mu = ellipsoid_from_rectangle(ub_mean)
        p_lagrange_mu = MX.zeros((n_s, 1))

        b_sigma_eps = c_safety * (sqrt(sigm_0) + ub_sigma)
        Q_lagrange_sigm = ellipsoid_from_rectangle(b_sigma_eps)
        p_lagrange_sigm = MX.zeros((n_s, 1))

        p_sum_lagrange, Q_sum_lagrange = sum_two_ellipsoids(
            p_lagrange_sigm, Q_lagrange_sigm, p_lagrange_mu, Q_lagrange_mu)
        p_1, q_1 = sum_two_ellipsoids(p_sum_lagrange, Q_sum_lagrange, p_0, Q_0)

        return p_1, q_1, sigm_0
Esempio n. 7
0
 def _construct_upd_z_nlp(self):
     # construct variables
     self._var_struct_updz = struct([entry('z_i', struct=self.q_i_struct),
                                     entry('z_ij', struct=self.q_ij_struct)])
     var = struct_symMX(self._var_struct_updz)
     z_i = self.q_i_struct(var['z_i'])
     z_ij = self.q_ij_struct(var['z_ij'])
     # construct parameters
     self._par_struct_updz = struct([entry('x_i', struct=self.q_i_struct),
                                     entry('x_j', struct=self.q_ij_struct),
                                     entry('l_i', struct=self.q_i_struct),
                                     entry('l_ij', struct=self.q_ij_struct),
                                     entry('t'), entry('T'), entry('rho'),
                                     entry('par', struct=self.par_struct)])
     par = struct_symMX(self._par_struct_updz)
     x_i, x_j = self.q_i_struct(par['x_i']), self.q_ij_struct(par['x_j'])
     l_i, l_ij = self.q_i_struct(par['l_i']), self.q_ij_struct(par['l_ij'])
     t, T, rho = par['t'], par['T'], par['rho']
     t0 = t/T
     # transform spline variables: only consider future piece of spline
     tf = lambda cfs, basis: shift_knot1_fwd(cfs, basis, t0)
     self._transform_spline([x_i, z_i, l_i], tf, self.q_i)
     self._transform_spline([x_j, z_ij, l_ij], tf, self.q_ij)
     # construct constraints
     constraints, lb, ub = [], [], []
     for con in self.constraints:
         c = con[0]
         for sym in symvar(c):
             for label, child in self.group.items():
                 if sym.getName() in child.symbol_dict:
                     name = child.symbol_dict[sym.getName()][1]
                     v = z_i[label, name]
                     ind = self.q_i[child][name]
                     sym2 = MX.zeros(sym.size())
                     sym2[ind] = v
                     sym2 = reshape(sym2, sym.shape)
                     c = substitute(c, sym, sym2)
                     break
             for nghb in self.q_ij.keys():
                 for label, child in nghb.group.items():
                     if sym.getName() in child.symbol_dict:
                         name = child.symbol_dict[sym.getName()][1]
                         v = z_ij[nghb.label, label, name]
                         ind = self.q_ij[nghb][child][name]
                         sym2 = MX.zeros(sym.size())
                         sym2[ind] = v
                         sym2 = reshape(sym2, sym.shape)
                         c = substitute(c, sym, sym2)
                         break
             for name, s in self.par_i.items():
                 if s.getName() == sym.getName():
                     c = substitute(c, sym, par['par', name])
         constraints.append(c)
         lb.append(con[1])
         ub.append(con[2])
     self.lb_updz, self.ub_updz = lb, ub
     # construct objective
     obj = 0.
     for child, q_i in self.q_i.items():
         for name in q_i.keys():
             x = x_i[child.label, name]
             z = z_i[child.label, name]
             l = l_i[child.label, name]
             obj += mul(l.T, x-z) + 0.5*rho*mul((x-z).T, (x-z))
     for nghb in self.q_ij.keys():
         for child, q_ij in self.q_ij[nghb].items():
             for name in q_ij.keys():
                 x = x_j[str(nghb), child.label, name]
                 z = z_ij[str(nghb), child.label, name]
                 l = l_ij[str(nghb), child.label, name]
                 obj += mul(l.T, x-z) + 0.5*rho*mul((x-z).T, (x-z))
     # construct problem
     prob, compile_time = self.father.create_nlp(var, par, obj,
                                                 constraints, self.options)
     self.problem_upd_z = prob
Esempio n. 8
0
 def construct_upd_xz(self, problem=None):
     # construct optifather & give reference to problem
     self.father_updx = OptiFather(list(self.group.values()))
     self.problem.father = self.father_updx
     # define z_ij variables
     init = self.q_ij_struct(0)
     for nghb, q_ij in self.q_ij.items():
         for child, q_j in q_ij.items():
             for name, ind in q_j.items():
                 var = np.array(child._values[name])
                 v = var.T.flatten()[ind]
                 init[nghb.label, child.label, name, ind] = v
     z_ij = self.define_variable('z_ij',
                                 self.q_ij_struct.shape[0],
                                 value=np.array(init.cat))
     # define parameters
     l_ij = self.define_parameter('l_ij', self.q_ij_struct.shape[0])
     l_ji = self.define_parameter('l_ji', self.q_ji_struct.shape[0])
     # put them in the struct format
     z_ij = self.q_ij_struct(z_ij)
     l_ij = self.q_ij_struct(l_ij)
     l_ji = self.q_ji_struct(l_ji)
     # get (part of) variables
     x_i = self._get_x_variables(symbolic=True)
     # construct local copies of parameters
     par = {}
     for name, s in self.par_global.items():
         par[name] = self.define_parameter(name, s.shape[0], s.shape[1])
     if problem is None:
         # get time info
         t = self.define_symbol('t')
         T = self.define_symbol('T')
         t0 = t / T
         # transform spline variables: only consider future piece of spline
         tf = lambda cfs, basis: shift_knot1_fwd(cfs, basis, t0)
         self._transform_spline(x_i, tf, self.q_i)
         self._transform_spline([z_ij, l_ij], tf, self.q_ij)
         self._transform_spline(l_ji, tf, self.q_ji)
         # construct objective
         obj = 0.
         for child, q_i in self.q_i.items():
             for name in q_i.keys():
                 x = x_i[child.label][name]
                 for nghb in self.q_ji.keys():
                     l = l_ji[str(nghb), child.label, name]
                     obj += mtimes(l.T, x)
         for nghb, q_j in self.q_ij.items():
             for child in q_j.keys():
                 for name in q_j[child].keys():
                     z = z_ij[str(nghb), child.label, name]
                     l = l_ij[str(nghb), child.label, name]
                     obj -= mtimes(l.T, z)
         self.define_objective(obj)
     # construct constraints
     for con in self.global_constraints:
         c = con[0]
         for sym in symvar(c):
             for label, child in self.group.items():
                 if sym.name() in child.symbol_dict:
                     name = child.symbol_dict[sym.name()][1]
                     v = x_i[label][name]
                     ind = self.q_i[child][name]
                     sym2 = MX.zeros(sym.size())
                     sym2[ind] = v
                     sym2 = reshape(sym2, sym.shape)
                     c = substitute(c, sym, sym2)
                     break
             for nghb in self.q_ij.keys():
                 for label, child in nghb.group.items():
                     if sym.name() in child.symbol_dict:
                         name = child.symbol_dict[sym.name()][1]
                         v = z_ij[nghb.label, label, name]
                         ind = self.q_ij[nghb][child][name]
                         sym2 = MX.zeros(sym.size())
                         sym2[ind] = v
                         sym2 = reshape(sym2, sym.shape)
                         c = substitute(c, sym, sym2)
                         break
             for name, s in self.par_global.items():
                 if s.name() == sym.name():
                     c = substitute(c, sym, par[name])
         lb, ub = con[1], con[2]
         self.define_constraint(c, lb, ub)
     # construct problem
     prob, buildtime = self.father_updx.construct_problem(
         self.options, str(self._index), problem)
     self.problem_upd_xz = prob
     self.father_updx.init_transformations(
         self.problem.init_primal_transform,
         self.problem.init_dual_transform)
     self.init_var_dd()
     return buildtime
Esempio n. 9
0
 def custom_mx_fail(pn):
     if pn.u is None:
         return None
     u = pn.nlp.controls
     return MX.zeros(u.shape), u.cx, MX.zeros(u.shape)
Esempio n. 10
0
    def configure_soft_contact_function(ocp, nlp):
        """
        Configure the soft contact sphere

        Parameters
        ----------
        ocp: OptimalControlProgram
            A reference to the ocp
        nlp: NonLinearProgram
            A reference to the phase
        """

        global_soft_contact_force_func = MX.zeros(
            nlp.model.nbSoftContacts() * 6, 1)
        n = nlp.model.nbQ()
        component_list = ["Mx", "My", "Mz", "Fx", "Fy", "Fz"]

        for i_sc in range(nlp.model.nbSoftContacts()):
            soft_contact = nlp.model.softContact(i_sc)

            global_soft_contact_force_func[i_sc * 6:(i_sc + 1) * 6, :] = (
                biorbd.SoftContactSphere(soft_contact).computeForceAtOrigin(
                    nlp.model, nlp.states.mx_reduced[:n],
                    nlp.states.mx_reduced[n:]).to_mx())
        nlp.soft_contact_forces_func = Function(
            "soft_contact_forces_func",
            [
                nlp.states.mx_reduced, nlp.controls.mx_reduced,
                nlp.parameters.mx
            ],
            [global_soft_contact_force_func],
            ["x", "u", "p"],
            ["soft_contact_forces"],
        ).expand()

        for i_sc in range(nlp.model.nbSoftContacts()):
            all_soft_contact_names = []
            all_soft_contact_names.extend([
                f"{nlp.model.softContactName(i_sc).to_string()}_{name}"
                for name in component_list if nlp.model.softContactName(
                    i_sc).to_string() not in all_soft_contact_names
            ])

            if "soft_contact_forces" in nlp.plot_mapping:
                phase_mappings = nlp.plot_mapping["soft_contact_forces"]
            else:
                soft_contact_names_in_phase = [
                    f"{nlp.model.softContactName(i_sc).to_string()}_{name}"
                    for name in component_list if nlp.model.softContactName(
                        i_sc).to_string() not in all_soft_contact_names
                ]
                phase_mappings = Mapping([
                    i for i, c in enumerate(all_soft_contact_names)
                    if c in soft_contact_names_in_phase
                ])
            nlp.plot[
                f"soft_contact_forces_{nlp.model.softContactName(i_sc).to_string()}"] = CustomPlot(
                    lambda t, x, u, p: nlp.soft_contact_forces_func(x, u, p)[
                        (i_sc * 6):((i_sc + 1) * 6), :],
                    plot_type=PlotType.INTEGRATED,
                    axes_idx=phase_mappings,
                    legend=all_soft_contact_names,
                )
Esempio n. 11
0
 def construct_upd_xz(self, problem=None):
     # construct optifather & give reference to problem
     self.father_updx = OptiFather(self.group.values())
     self.problem.father = self.father_updx
     # define z_ij variables
     init = self.q_ij_struct(0)
     for nghb, q_ij in self.q_ij.items():
         for child, q_j in q_ij.items():
             for name, ind in q_j.items():
                 var = np.array(child._values[name])
                 v = var.T.flatten()[ind]
                 init[nghb.label, child.label, name, ind] = v
     z_ij = self.define_variable(
         'z_ij', self.q_ij_struct.shape[0], value=np.array(init.cat))
     # define parameters
     l_ij = self.define_parameter('l_ij', self.q_ij_struct.shape[0])
     l_ji = self.define_parameter('l_ji', self.q_ji_struct.shape[0])
     # put them in the struct format
     z_ij = self.q_ij_struct(z_ij)
     l_ij = self.q_ij_struct(l_ij)
     l_ji = self.q_ji_struct(l_ji)
     # get (part of) variables
     x_i = self._get_x_variables(symbolic=True)
     # construct local copies of parameters
     par = {}
     for name, s in self.par_global.items():
         par[name] = self.define_parameter(name, s.shape[0], s.shape[1])
     if problem is None:
         # get time info
         t = self.define_symbol('t')
         T = self.define_symbol('T')
         t0 = t/T
         # transform spline variables: only consider future piece of spline
         tf = lambda cfs, basis: shift_knot1_fwd(cfs, basis, t0)
         self._transform_spline(x_i, tf, self.q_i)
         self._transform_spline([z_ij, l_ij], tf, self.q_ij)
         self._transform_spline(l_ji, tf, self.q_ji)
         # construct objective
         obj = 0.
         for child, q_i in self.q_i.items():
             for name in q_i.keys():
                 x = x_i[child.label][name]
                 for nghb in self.q_ji.keys():
                     l = l_ji[str(nghb), child.label, name]
                     obj += mtimes(l.T, x)
         for nghb, q_j in self.q_ij.items():
             for child in q_j.keys():
                 for name in q_j[child].keys():
                     z = z_ij[str(nghb), child.label, name]
                     l = l_ij[str(nghb), child.label, name]
                     obj -= mtimes(l.T, z)
         self.define_objective(obj)
     # construct constraints
     for con in self.global_constraints:
         c = con[0]
         for sym in symvar(c):
             for label, child in self.group.items():
                 if sym.name() in child.symbol_dict:
                     name = child.symbol_dict[sym.name()][1]
                     v = x_i[label][name]
                     ind = self.q_i[child][name]
                     sym2 = MX.zeros(sym.size())
                     sym2[ind] = v
                     sym2 = reshape(sym2, sym.shape)
                     c = substitute(c, sym, sym2)
                     break
             for nghb in self.q_ij.keys():
                 for label, child in nghb.group.items():
                     if sym.name() in child.symbol_dict:
                         name = child.symbol_dict[sym.name()][1]
                         v = z_ij[nghb.label, label, name]
                         ind = self.q_ij[nghb][child][name]
                         sym2 = MX.zeros(sym.size())
                         sym2[ind] = v
                         sym2 = reshape(sym2, sym.shape)
                         c = substitute(c, sym, sym2)
                         break
             for name, s in self.par_global.items():
                 if s.name() == sym.name():
                     c = substitute(c, sym, par[name])
         lb, ub = con[1], con[2]
         self.define_constraint(c, lb, ub)
     # construct problem
     prob, buildtime = self.father_updx.construct_problem(
         self.options, str(self._index), problem)
     self.problem_upd_xz = prob
     self.father_updx.init_transformations(self.problem.init_primal_transform,
                                      self.problem.init_dual_transform)
     self.init_var_dd()
     return buildtime
Esempio n. 12
0
 def custom_mx_fail(pn):
     if pn.u is None:
         return None
     return MX.zeros(pn.u.shape), pn.u, MX.zeros(pn.u.shape)