An example from A Morphable Model For The Synthesis of 3D Faces Eq. 5
The original equation:
I❤️LA implementation:
E = 1/`σ_N`²`E_I` + ∑_j α_j²/`σ_S`_j² + ∑_j β_j²/`σ_T`_j² + ∑_j (ρ_j-ρ̄_j)²/`σ_ρ`_j²
where
`σ_N` ∈ ℝ
`E_I` ∈ ℝ
α_i ∈ ℝ
β_i ∈ ℝ
`σ_S`_i ∈ ℝ
`σ_T`_i ∈ ℝ
ρ_j ∈ ℝ
ρ̄_j ∈ ℝ
`σ_ρ`_j ∈ ℝ
I❤️LA compiled to C++/Eigen:
/*
E = 1/`σ_N`²`E_I` + ∑_j α_j²/`σ_S`_j² + ∑_j β_j²/`σ_T`_j² + ∑_j (ρ_j-ρ̄_j)²/`σ_ρ`_j²
where
`σ_N` ∈ ℝ
`E_I` ∈ ℝ
α_i ∈ ℝ
β_i ∈ ℝ
`σ_S`_i ∈ ℝ
`σ_T`_i ∈ ℝ
ρ_j ∈ ℝ
ρ̄_j ∈ ℝ
`σ_ρ`_j ∈ ℝ
*/
#include <Eigen/Core>
#include <Eigen/Dense>
#include <Eigen/Sparse>
#include <iostream>
#include <set>
struct morphable_model_5ResultType {
double E;
morphable_model_5ResultType(const double & E)
: E(E)
{}
};
morphable_model_5ResultType morphable_model_5(
const double & σ_N,
const double & E_I,
const std::vector<double> & α,
const std::vector<double> & β,
const std::vector<double> & σ_S,
const std::vector<double> & σ_T,
const std::vector<double> & ρ,
const std::vector<double> & ρ̄,
const std::vector<double> & σ_ρ)
{
const long dim_0 = α.size();
const long dim_1 = ρ.size();
assert( β.size() == dim_0 );
assert( σ_S.size() == dim_0 );
assert( σ_T.size() == dim_0 );
assert( ρ̄.size() == dim_1 );
assert( σ_ρ.size() == dim_1 );
double sum_0 = 0;
for(int j=1; j<=α.size(); j++){
sum_0 += pow(α.at(j-1), 2) / double(pow(σ_S.at(j-1), 2));
}
double sum_1 = 0;
for(int j=1; j<=β.size(); j++){
sum_1 += pow(β.at(j-1), 2) / double(pow(σ_T.at(j-1), 2));
}
double sum_2 = 0;
for(int j=1; j<=ρ.size(); j++){
sum_2 += pow((ρ.at(j-1) - ρ̄.at(j-1)), 2) / double(pow(σ_ρ.at(j-1), 2));
}
double E = 1 / double(pow(σ_N, 2)) * E_I + sum_0 + sum_1 + sum_2;
return morphable_model_5ResultType(E);
}
void generateRandomData(double & σ_N,
double & E_I,
std::vector<double> & α,
std::vector<double> & β,
std::vector<double> & σ_S,
std::vector<double> & σ_T,
std::vector<double> & ρ,
std::vector<double> & ρ̄,
std::vector<double> & σ_ρ)
{
σ_N = rand() % 10;
E_I = rand() % 10;
const int dim_0 = rand()%10;
const int dim_1 = rand()%10;
α.resize(dim_0);
for(int i=0; i<dim_0; i++){
α[i] = rand() % 10;
}
β.resize(dim_0);
for(int i=0; i<dim_0; i++){
β[i] = rand() % 10;
}
σ_S.resize(dim_0);
for(int i=0; i<dim_0; i++){
σ_S[i] = rand() % 10;
}
σ_T.resize(dim_0);
for(int i=0; i<dim_0; i++){
σ_T[i] = rand() % 10;
}
ρ.resize(dim_1);
for(int i=0; i<dim_1; i++){
ρ[i] = rand() % 10;
}
ρ̄.resize(dim_1);
for(int i=0; i<dim_1; i++){
ρ̄[i] = rand() % 10;
}
σ_ρ.resize(dim_1);
for(int i=0; i<dim_1; i++){
σ_ρ[i] = rand() % 10;
}
}
int main(int argc, char *argv[])
{
srand((int)time(NULL));
double σ_N;
double E_I;
std::vector<double> α;
std::vector<double> β;
std::vector<double> σ_S;
std::vector<double> σ_T;
std::vector<double> ρ;
std::vector<double> ρ̄;
std::vector<double> σ_ρ;
generateRandomData(σ_N, E_I, α, β, σ_S, σ_T, ρ, ρ̄, σ_ρ);
morphable_model_5ResultType func_value = morphable_model_5(σ_N, E_I, α, β, σ_S, σ_T, ρ, ρ̄, σ_ρ);
std::cout<<"return value:\n"<<func_value.E<<std::endl;
return 0;
}
I❤️LA compiled to Python/NumPy/SciPy:
"""
E = 1/`σ_N`²`E_I` + ∑_j α_j²/`σ_S`_j² + ∑_j β_j²/`σ_T`_j² + ∑_j (ρ_j-ρ̄_j)²/`σ_ρ`_j²
where
`σ_N` ∈ ℝ
`E_I` ∈ ℝ
α_i ∈ ℝ
β_i ∈ ℝ
`σ_S`_i ∈ ℝ
`σ_T`_i ∈ ℝ
ρ_j ∈ ℝ
ρ̄_j ∈ ℝ
`σ_ρ`_j ∈ ℝ
"""
import numpy as np
import scipy
import scipy.linalg
from scipy import sparse
from scipy.integrate import quad
from scipy.optimize import minimize
class morphable_model_5ResultType:
def __init__( self, E):
self.E = E
def morphable_model_5(σ_N, E_I, α, β, σ_S, σ_T, ρ, ρ̄, σ_ρ):
α = np.asarray(α, dtype=np.float64)
β = np.asarray(β, dtype=np.float64)
σ_S = np.asarray(σ_S, dtype=np.float64)
σ_T = np.asarray(σ_T, dtype=np.float64)
ρ = np.asarray(ρ, dtype=np.float64)
ρ̄ = np.asarray(ρ̄, dtype=np.float64)
σ_ρ = np.asarray(σ_ρ, dtype=np.float64)
dim_0 = α.shape[0]
dim_1 = ρ.shape[0]
assert np.ndim(σ_N) == 0
assert np.ndim(E_I) == 0
assert α.shape == (dim_0,)
assert β.shape == (dim_0,)
assert σ_S.shape == (dim_0,)
assert σ_T.shape == (dim_0,)
assert ρ.shape == (dim_1,)
assert ρ̄.shape == (dim_1,)
assert σ_ρ.shape == (dim_1,)
sum_0 = 0
for j in range(1, len(α)+1):
sum_0 += np.power(α[j-1], 2) / np.power(σ_S[j-1], 2)
sum_1 = 0
for j in range(1, len(β)+1):
sum_1 += np.power(β[j-1], 2) / np.power(σ_T[j-1], 2)
sum_2 = 0
for j in range(1, len(ρ)+1):
sum_2 += np.power((ρ[j-1] - ρ̄[j-1]), 2) / np.power(σ_ρ[j-1], 2)
E = 1 / np.power(σ_N, 2) * E_I + sum_0 + sum_1 + sum_2
return morphable_model_5ResultType(E)
def generateRandomData():
σ_N = np.random.randn()
E_I = np.random.randn()
dim_0 = np.random.randint(10)
dim_1 = np.random.randint(10)
α = np.random.randn(dim_0)
β = np.random.randn(dim_0)
σ_S = np.random.randn(dim_0)
σ_T = np.random.randn(dim_0)
ρ = np.random.randn(dim_1)
ρ̄ = np.random.randn(dim_1)
σ_ρ = np.random.randn(dim_1)
return σ_N, E_I, α, β, σ_S, σ_T, ρ, ρ̄, σ_ρ
if __name__ == '__main__':
σ_N, E_I, α, β, σ_S, σ_T, ρ, ρ̄, σ_ρ = generateRandomData()
print("σ_N:", σ_N)
print("E_I:", E_I)
print("α:", α)
print("β:", β)
print("σ_S:", σ_S)
print("σ_T:", σ_T)
print("ρ:", ρ)
print("ρ̄:", ρ̄)
print("σ_ρ:", σ_ρ)
func_value = morphable_model_5(σ_N, E_I, α, β, σ_S, σ_T, ρ, ρ̄, σ_ρ)
print("return value: ", func_value.E)
I❤️LA compiled to MATLAB:
function output = morphable_model_5(sigma_N, E_I, alpha, beta, sigma_S, sigma_T, rho, rho_bar, sigma_rho)
% output = morphable_model_5(`σ_N`, `E_I`, α, β, `σ_S`, `σ_T`, ρ, ρ̄, `σ_ρ`)
%
% E = 1/`σ_N`²`E_I` + ∑_j α_j²/`σ_S`_j² + ∑_j β_j²/`σ_T`_j² + ∑_j (ρ_j-ρ̄_j)²/`σ_ρ`_j²
%
% where
%
% `σ_N` ∈ ℝ
% `E_I` ∈ ℝ
% α_i ∈ ℝ
% β_i ∈ ℝ
% `σ_S`_i ∈ ℝ
% `σ_T`_i ∈ ℝ
% ρ_j ∈ ℝ
% ρ̄_j ∈ ℝ
% `σ_ρ`_j ∈ ℝ
if nargin==0
warning('generating random input data');
[sigma_N, E_I, alpha, beta, sigma_S, sigma_T, rho, rho_bar, sigma_rho] = generateRandomData();
end
function [sigma_N, E_I, alpha, beta, sigma_S, sigma_T, rho, rho_bar, sigma_rho] = generateRandomData()
sigma_N = randn();
E_I = randn();
dim_0 = randi(10);
dim_1 = randi(10);
alpha = randn(dim_0,1);
beta = randn(dim_0,1);
sigma_S = randn(dim_0,1);
sigma_T = randn(dim_0,1);
rho = randn(dim_1,1);
rho_bar = randn(dim_1,1);
sigma_rho = randn(dim_1,1);
end
alpha = reshape(alpha,[],1);
beta = reshape(beta,[],1);
sigma_S = reshape(sigma_S,[],1);
sigma_T = reshape(sigma_T,[],1);
rho = reshape(rho,[],1);
rho_bar = reshape(rho_bar,[],1);
sigma_rho = reshape(sigma_rho,[],1);
dim_0 = size(alpha, 1);
dim_1 = size(rho, 1);
assert(numel(sigma_N) == 1);
assert(numel(E_I) == 1);
assert( size(alpha,1) == dim_0 );
assert( size(beta,1) == dim_0 );
assert( size(sigma_S,1) == dim_0 );
assert( size(sigma_T,1) == dim_0 );
assert( size(rho,1) == dim_1 );
assert( size(rho_bar,1) == dim_1 );
assert( size(sigma_rho,1) == dim_1 );
sum_0 = 0;
for j = 1:size(alpha, 1)
sum_0 = sum_0 + alpha(j).^2 / sigma_S(j).^2;
end
sum_1 = 0;
for j = 1:size(beta, 1)
sum_1 = sum_1 + beta(j).^2 / sigma_T(j).^2;
end
sum_2 = 0;
for j = 1:size(rho, 1)
sum_2 = sum_2 + (rho(j) - rho_bar(j)).^2 / sigma_rho(j).^2;
end
E = 1 / sigma_N.^2 * E_I + sum_0 + sum_1 + sum_2;
output.E = E;
end
I❤️LA compiled to LaTeX:
\documentclass[12pt]{article}
\usepackage{mathdots}
\usepackage[bb=boondox]{mathalfa}
\usepackage{mathtools}
\usepackage{amssymb}
\usepackage{libertine}
\DeclareMathOperator*{\argmax}{arg\,max}
\DeclareMathOperator*{\argmin}{arg\,min}
\usepackage[paperheight=8in,paperwidth=4in,margin=.3in,heightrounded]{geometry}
\let\originalleft\left
\let\originalright\right
\renewcommand{\left}{\mathopen{}\mathclose\bgroup\originalleft}
\renewcommand{\right}{\aftergroup\egroup\originalright}
\begin{document}
\begin{center}
\resizebox{\textwidth}{!}
{
\begin{minipage}[c]{\textwidth}
\begin{align*}
\mathit{E} & = \frac{1}{{\textit{σ\_N}}^{2}}\textit{E\_I} + \sum_\mathit{j} \frac{{\mathit{α}_{ \mathit{j} }}^{2}}{{\textit{σ\_S}_{ \mathit{j} }}^{2}} + \sum_\mathit{j} \frac{{\mathit{β}_{ \mathit{j} }}^{2}}{{\textit{σ\_T}_{ \mathit{j} }}^{2}} + \sum_\mathit{j} \frac{{\left( \mathit{ρ}_{ \mathit{j} } - \textit{ρ̄}_{ \mathit{j} } \right)}^{2}}{{\textit{σ\_ρ}_{ \mathit{j} }}^{2}} \\
\intertext{where}
\textit{σ\_N} & \in \mathbb{R} \\
\textit{E\_I} & \in \mathbb{R} \\
\mathit{α}_{\mathit{i}} & \in \mathbb{R} \\
\mathit{β}_{\mathit{i}} & \in \mathbb{R} \\
\textit{σ\_S}_{\mathit{i}} & \in \mathbb{R} \\
\textit{σ\_T}_{\mathit{i}} & \in \mathbb{R} \\
\mathit{ρ}_{\mathit{j}} & \in \mathbb{R} \\
\textit{ρ̄}_{\mathit{j}} & \in \mathbb{R} \\
\textit{σ\_ρ}_{\mathit{j}} & \in \mathbb{R} \\
\\
\end{align*}
\end{minipage}
}
\end{center}
\end{document}
I❤️LA LaTeX output: