function c = catalan ( n )

%*****************************************************************************80
%
%% CATALAN computes the Catalan numbers, from C(0) to C(N).
%
%  First values:
%
%     C(0)     1
%     C(1)     1
%     C(2)     2
%     C(3)     5
%     C(4)    14
%     C(5)    42
%     C(6)   132
%     C(7)   429
%     C(8)  1430
%     C(9)  4862
%    C(10) 16796
%
%  Formula:
%
%    C(N) = (2*N)! / ( (N+1) * (N!) * (N!) )
%         = 1 / (N+1) * COMB ( 2N, N )
%         = 1 / (2N+1) * COMB ( 2N+1, N+1).
%
%  Recursion:
%
%    C(N) = 2 * (2*N-1) * C(N-1) / (N+1)
%    C(N) = sum ( 1 <= I <= N-1 ) C(I) * C(N-I)
%
%  Discussion:
%
%    The Catalan number C(N) counts:
%
%    1) the number of binary trees on N vertices;
%    2) the number of ordered trees on N+1 vertices;
%    3) the number of full binary trees on 2N+1 vertices;
%    4) the number of well formed sequences of 2N parentheses;
%    5) number of ways 2N ballots can be counted, in order,
%       with N positive and N negative, so that the running sum
%       is never negative;
%    6) the number of standard tableaus in a 2 by N rectangular Ferrers diagram;
%    7) the number of monotone functions from [1..N} to [1..N} which
%       satisfy f(i) <= i for all i;
%    8) the number of ways to triangulate a polygon with N+2 vertices.
%
%  Example:
%
%    N = 3
%
%    ()()()
%    ()(())
%    (()())
%    (())()
%    ((()))
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    04 June 2004
%
%  Author:
%
%    John Burkardt
%
%  Reference:
%
%    Dennis Stanton and Dennis White,
%    Constructive Combinatorics,
%    Springer Verlag, New York, 1986.
%
%  Parameters:
%
%    Input, integer N, the number of Catalan numbers desired.
%
%    Output, integer C(1:N+1), the Catalan numbers from C(0) to C(N).
%
  if ( n < 0 )
    c = [];
    return;
  end

  c(1) = 1;
%
%  The extra parentheses ensure that the integer division is
%  done AFTER the integer multiplication.
%
  for i = 1 : n
    c(i+1) = ( c(i) * 2 * ( 2 * i - 1 ) ) / ( i + 1 );
  end

  return
end


function [ a, b, c ] = sphere_triangle_vertices_to_angles ( r, v1, v2, v3 )

%*****************************************************************************80
%
%% SPHERE_TRIANGLE_VERTICES_TO_ANGLES computes the angles of a spherical triangle.
%
%  Discussion:
%
%    A sphere centered at 0 in 3D satisfies the equation:
%
%      X * X + Y * Y + Z * Z = R * R
%
%    A spherical triangle is specified by three points on the surface
%    of the sphere.
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    24 August 2010
%
%  Author:
%
%    John Burkardt
%
%  Parameters:
%
%    Input, real R, the radius of the sphere.
%
%    Input, real V1(3), V2(3), V3(3), the vertices of the triangle.
%
%    Output, real A, B, C, the angles of the spherical triangle.
%

%
%  Compute the lengths of the sides of the spherical triangle.
%
  [ as, bs, cs ] = sphere_triangle_vertices_to_sides ( r, v1, v2, v3 );
%
%  Get the spherical angles.
%
  [ a, b, c ] = sphere_triangle_sides_to_angles ( r, as, bs, cs );

  return
end


% Derive  -- Equations of Motion - 2D (planar) quad-rotor
%
% Model:
%   We will assume that the quadrotor is modeled by two point-masses that
%   are connected by a rigid mass-less bar. There are two motors, each of
%   which apply a force orthogonal to the connecting bar. Assume that air
%   drag is negligable.
%

clc; clear;

%%%% Create symbolic variables:
syms x y q 'real'  % horizontal and vertical position, angle (+i axis = 0)
syms dx dy dq 'real'  % rates
syms ddx ddy ddq 'real' % accelerations
syms u1 u2 'real'  % force applied by rotors
syms d m g 'real'  % distance from center to rotor, rotor mass, gravity

%%%% Unit vectors:

% Inertial reference frame:
i = sym([1;0;0]);
j = sym([0;1;0]);
k = sym([0;0;1]);

% Body reference frame:
e = cos(q)*i + sin(q)*j;  % Unit vector from center to rotor 2
n = -sin(q)*i + cos(q)*j;  % Unit vector orthogonal to e

%%%% Position vectors:
Pc = x*i + y*j;   % Position of the center of the quad rotor
P1 = Pc - d*e;  % Position of rotor 1
P2 = Pc + d*e;  % Position of rotor 2

%%%% Define the state vector and its derivative
z = [x;y;q;dx;dy;dq];  %State
dz = [dx;dy;dq;ddx;ddy;ddq];  %Derivative of state

%%%% Kinematics:

% Define the derivative operator. CHAIN RULE.
derivative = @(f)( jacobian(f,z)*dz );

% Velocities
dPc = derivative(Pc);
dP1 = derivative(P1);
dP2 = derivative(P2);

% Accelerations
ddPc = derivative(dPc);
ddP1 = derivative(dP1);
ddP2 = derivative(dP2);

%%%% Define all force vectors:
Fg1 = -m*g*j;  %Force of gravity on mass 1
Fg2 = -m*g*j;  %Force of gravity on mass 2
Fu1 = u1*n;  %Force due to rotor 1
Fu2 = u2*n;  %Force due to rotor 1

%%%% Force Balance:
sumForces = Fg1 + Fg2 + Fu1 + Fu2;
massAccel = m*ddPc;
eqn1 = dot(sumForces-massAccel,i);
eqn2 = dot(sumForces-massAccel,j);

%%%% Angular Momentum Balance:   (about center of quad rotor)
sumTorques = ...
    cross(P1-Pc, Fg1) + ...
    cross(P2-Pc, Fg2) + ...
    cross(P1-Pc, Fu1) + ...
    cross(P2-Pc, Fu2);
angMomentum = ...
    cross(P1-Pc, m*ddP1) + ...
    cross(P2-Pc, m*ddP2);
eqn3 = simplify(dot(sumTorques-angMomentum, k));

%%%% Collect and solve equations:
vars = [ddx;ddy;ddq];  %This is what we want to find  (the accelerations)
eqns = [eqn1;eqn2;eqn3];  %These are the dynamics equations
[M,f] = equationsToMatrix(eqns, vars); % EoM are linear in acceleration

% In this problem, the equations of motion are simple, so we can solve them
% analytically using the "\" command. For more complicated systems, it is
% typically much faster to do this solve numerically at run-time.
soln = simplify(M\f);
ddxSoln = soln(1);
ddySoln = soln(2);
ddqSoln = soln(3);

%%%% Automatically write out dynamics function:
% This will automatically optimize the function to minimize computation
% time. Not too important here, but makes a big difference for complicated
% functions. It also prevents copy-paste errors.
matlabFunction(...
    ddxSoln, ddySoln, ddqSoln,...
    'file','autoGen_dynamics.m',...
    'vars',{q,u1,u2,m,g,d},...
    'outputs',{'ddx','ddy','ddq'});

%%%% Display the solution to the user:
disp(['ddx = ' ddxSoln]);
disp(['ddy = ' ddySoln]);
disp(['ddq = ' ddqSoln]);


function v=polyValNewton(z,a,c)
%POLYVALNEWTON Evaluate a set of polynomial given in Newton's form at a
%              desired set of points. This is useful when given a set of
%              Hermite interpolating polynomials for interpolating a
%              vector.
%
%INPUTS: z A numPointsX1 or 1XnumPoints vector of scalar points where the
%          values of the numDim polynomials are desired.
%        a A numDimXn matrix of polynomial coefficients for numDim
%          polynomials, as described below.
%        c A numDim X(n-1) matrix of the control points associated with
%          each of the numDim polynomial in Newton's form, which might be
%          the control points used in the HermiteInterpPoly function.
%
%OUTPUTS: v The numDimXnumPoints matrix of values of the polynomials
%           evaluated at the points in z.
%
%A polynomial function in Newton's form evaluated at point z has the form
%y(z)=a(1)+sum_{k=1}^{n-1}a(k+1)(z-c(1))*(z-c(2))*...*(z-c(k))
%This function just evaluates multiple scalar polynomials.
%
%The algorithm is based on  VALUE from Chapter 19 of [1] to handle vector
%values; a loop is used here.
%
%Newton's polynomial form arises when dealing with Hermite interpolating
%polynomials as is discussed in Section 2.1.3 of [2] and in Chapters 3.3
%and 3.4 of [3].
%
%REFERENCES:
%[1] A. Nijenhuis and H. S. Wilf, Combinatorial Algorithms for Computers
%    and Calculators, 2nd ed. New York: Academic press, 1978.
%[2] J. Stoer and R. Bulirsch, Introduction to Numerical Analysis, 3rd ed.
%    New York: Springer, 2002.
%[3] R. L. Burden and J. D. Faires, Numerical Analysis, 9th ed. Boston, MA:
%    Brooks/Cole, 2011.
%
%March 2015 David F. Crouse, Naval Research Laboratory, Washington D.C.
%(UNCLASSIFIED) DISTRIBUTION STATEMENT A. Approved for public release.

numDim=size(a,1);
numPoints=length(z);

v=zeros(numDim,numPoints);
for curDim=1:numDim
   v(curDim,:)=polyValNewtonScalar(z,a(curDim,:),c(curDim,:));
end
end

function v=polyValNewtonScalar(z,a,c)
%Below is VALUE from Chapter 19 of [1]
%
%REFERENCES:
%A. Nijenhuis and H. S. Wilf, Combinatorial Algorithms for Computers
%and Calculators, 2nd ed. New York: Academic press, 1978.

n=length(a);

v=ones(size(z))*a(n);
for k=(n-1):-1:1
    v=(z-c(k)).*v+a(k);
end

end

%LICENSE:
%
%The source code is in the public domain and not licensed or under
%copyright. The information and software may be used freely by the public.
%As required by 17 U.S.C. 403, third parties producing copyrighted works
%consisting predominantly of the material produced by U.S. government
%agencies must provide notice with such work(s) identifying the U.S.
%Government material incorporated and stating that such material is not
%subject to copyright protection.
%
%Derived works shall not identify themselves in a manner that implies an
%endorsement by or an affiliation with the Naval Research Laboratory.
%
%RECIPIENT BEARS ALL RISK RELATING TO QUALITY AND PERFORMANCE OF THE
%SOFTWARE AND ANY RELATED MATERIALS, AND AGREES TO INDEMNIFY THE NAVAL
%RESEARCH LABORATORY FOR ALL THIRD-PARTY CLAIMS RESULTING FROM THE ACTIONS
%OF RECIPIENT IN THE USE OF THE SOFTWARE.


function y = mnorm_pdf(x,mu,S)
%MNORM_PDF Multivariate-Normal probability density function (pdf).
%
%   Description
%   Y = MNORM_PDF(X,MU,SIGMA) Returns the multivariate-normal
%   pdf with mean, MU, and covariance matrix, SIGMA, at the values in X.
%
%   Default values for MU and SIGMA are 0 and 1 respectively.
%
% Copyright (c) 1998-2005 Aki Vehtari

% This software is distributed under the GNU General Public
% License (version 3 or later); please refer to the file
% License.txt, included with the software, for details.

if nargin < 3,
  S = 1;
end

if nargin < 2;
  mu = 0;
end

if nargin < 1,
  error('Requires at least one input argument.');
end

[n,m]=size(x);
xmu=x-repmat(mu,n,1);
if ~issparse(S)
    % Use Cholesky decomposition, since it is faster and
    % numerically more stable.
    L=chol(S,'lower');
    y=zeros(n,1);
    for i1=1:n
      b=L\xmu(i1,:)';
      y(i1)=-b'*b;
    end
    y=exp(.5*y-sum(log(diag(L)))-.5*m*log(2*pi));
else
    LD = ldlchol(S);
    y=zeros(n,1);
    for i1=1:n
        xmui1=xmu(i1,:)';
      y(i1)=-xmui1'*ldlsolve(LD,xmui1);
    end
    y=exp(0.5*(y-sum(log(diag(LD)))-m*log(2*pi)));
end


function [J, grad] = costFunction(theta, X, y)
%COSTFUNCTION Compute cost and gradient for logistic regression
%   J = COSTFUNCTION(theta, X, y) computes the cost of using theta as the
%   parameter for logistic regression and the gradient of the cost
%   w.r.t. to the parameters.

% Initialize some useful values
m = length(y); % number of training examples

% You need to return the following variables correctly
J = 0;
grad = zeros(size(theta));

% ====================== YOUR CODE HERE ======================
% Instructions: Compute the cost of a particular choice of theta.
%               You should set J to the cost.
%               Compute the partial derivatives and set grad to the partial
%               derivatives of the cost w.r.t. each parameter in theta
%
% Note: grad should have the same dimensions as theta
%

% X.shape = [m, n], y.shape = [m, 1], theta.shape = [n, 1]
% y_pred = sigmoid(X*theta), y_pred.shape = [m, 1]
y_pred = sigmoid(X*theta);
J = -1.0 / m * sum( y.*log(y_pred) + (1-y).*log(1-y_pred) );
grad = 1.0 / m .* (X' * (y_pred - y));

% =============================================================

end


function [U, S] = pca(X)
%PCA Run principal component analysis on the dataset X
%   [U, S, X] = pca(X) computes eigenvectors of the covariance matrix of X
%   Returns the eigenvectors U, the eigenvalues (on diagonal) in S
%

% Useful values
[m, n] = size(X);

% You need to return the following variables correctly.
U = zeros(n);
S = zeros(n);

% ====================== YOUR CODE HERE ======================
% Instructions: You should first compute the covariance matrix. Then, you
%               should use the "svd" function to compute the eigenvectors
%               and eigenvalues of the covariance matrix.
%
% Note: When computing the covariance matrix, remember to divide by m (the
%       number of examples).
%

Sigma = (1/m) * (X'*X);
[U, S, V] = svd(Sigma);

% =========================================================================

end


function [ mD ] = CreateGradientOperator( numRows, numCols )
% ----------------------------------------------------------------------------------------------- %
% [ mD ] = CreateGradientOperator( numRows, numCols )
% Generates a Convolution Matrix for the 2D Gradient of the form [-1, 1].
% Input:
%   - numRows           -   Number of Rows.
%                           Number of rows of the image to be convolved.
%                           Structure: Scalar.
%                           Type: 'Single' / 'Double'.
%                           Range: {1, 2, 3, ...}.
%   - numCols           -   Number of Columns.
%                           Number of columns of the image to be convolved.
%                           Structure: Scalar.
%                           Type: 'Single' / 'Double'.
%                           Range: {1, 2, 3, ...}.
% Output:
%   - mD                -   Convolution Matrix.
%                           The output convolution matrix. The product of
%                           the matrix 'mD' and and image 'mI' in its
%                           column stack form ('mD * mI(:)') is equivalent
%                           to the convolution of 'mI' with the kernel
%                           using the valid convolution shape
%                           ('conv2(mI, mH, 'valid')').
%                           Structure: Matrix (Sparse).
%                           Type: 'Single' / 'Double'.
%                           Range: (-inf, inf).
% References:
%   1.  See my notes - 'Matrix Form of Image Gradient.md'.
% Remarks:
%   1.  The function basically calculates the Convolution Matrix for the
%       kernel [-1, 1] with operation mode of Valid Convolution. See
%       'CreateGradientOperatorUnitTest()' for the exact operation.
%   2.  The matrix 'mT' is the template for creating Vertical / Horizontal
%       derivative operator.
% TODO:
%   1.
%   Release Notes:
%   -   1.0.000     25/03/2020  Royi Avital
%       *   First release version.
% ----------------------------------------------------------------------------------------------- %

% Vertical Operator - T(numRows)
mT  = spdiags([ones(numRows - 1, 1), -ones(numRows - 1, 1)], [0, 1], numRows - 1, numRows);
mDv = kron(eye(numCols), mT);

% Vertical Operator - T(numCols)
mT  = spdiags([ones(numCols, 1), -ones(numCols, 1)], [0, 1], numCols - 1, numCols);
mDh = kron(mT, eye(numRows));

mD = [mDv; mDh];

end


function [U, S] = pca(X)
%PCA Run principal component analysis on the dataset X
%   [U, S, X] = pca(X) computes eigenvectors of the covariance matrix of X
%   Returns the eigenvectors U, the eigenvalues (on diagonal) in S
%

% Useful values
[m, n] = size(X);

% You need to return the following variables correctly.
U = zeros(n);
S = zeros(n);

% ====================== YOUR CODE HERE ======================
% Instructions: You should first compute the covariance matrix. Then, you
%               should use the "svd" function to compute the eigenvectors
%               and eigenvalues of the covariance matrix.
%
% Note: When computing the covariance matrix, remember to divide by m (the
%       number of examples).
%

Sigma = 1 / m * X' * X;
[U, S, V] = svd(Sigma);

% =========================================================================

end


function [theta] = normalEqn(X, y)
%NORMALEQN Computes the closed-form solution to linear regression
%   NORMALEQN(X,y) computes the closed-form solution to linear
%   regression using the normal equations.

theta = zeros(size(X, 2), 1);

% ====================== YOUR CODE HERE ======================
% Instructions: Complete the code to compute the closed form solution
%               to linear regression and put the result in theta.
%

% ---------------------- Sample Solution ----------------------

theta = pinv((X'*X))*X'*y;

% -------------------------------------------------------------

% ============================================================

end


%% Factorial
function [f] = find_factorial(n)
% calculate the factorial of a positive integer n
% factorial(n)can be used directly as a default function of Matlab

integerTest= ~mod(n,1); %it returns 0 if value is not an integer.
if integerTest== 0 || n < 0;   % checking n to be positive & integer
    disp('Error! your number muss be positive and integer');
else
    f = 1;
    for i = 1:n
        f = f*i;
    end
    disp(['factorial of ',num2str(n),' is: ',num2str(f)]);
end
end


% ------------------------GOLDEN SECTION METHOD----------------------------
% -------------------------------------------------------------------------
% Copyright (c) 2009, Katarzyna Zarnowiec, all rights reserved
% mailto: katarzyna.zarnowiec@gmail.com
% -------------------------------------------------------------------------

figure; hold on;

a=0;                            % start of interval
b=2;                            % end of interval
epsilon=0.000001;               % accuracy value
iter= 50;                       % maximum number of iterations
tau=double((sqrt(5)-1)/2);      % golden proportion coefficient, around 0.618
k=0;                            % number of iterations

x1=a+(1-tau)*(b-a);             % computing x values
x2=a+tau*(b-a);

f_x1=f(x1);                     % computing values in x points
f_x2=f(x2);

plot(x1,f_x1,'rx')              % plotting x
plot(x2,f_x2,'rx')

while ((abs(b-a)>epsilon) && (k<iter))
    k=k+1;
    if(f_x1<f_x2)
        b=x2;
        x2=x1;
        x1=a+(1-tau)*(b-a);

        f_x1=f(x1);
        f_x2=f(x2);

        plot(x1,f_x1,'rx');
    else
        a=x1;
        x1=x2;
        x2=a+tau*(b-a);

        f_x1=f(x1);
        f_x2=f(x2);

        plot(x2,f_x2,'rx')
    end

    k=k+1;
end

% chooses minimum point
if(f_x1<f_x2)
    sprintf('x_min=%f', x1)
    sprintf('f(x_min)=%f ', f_x1)
    plot(x1,f_x1,'ro')
else
    sprintf('x_min=%f', x2)
    sprintf('f(x_min)=%f ', f_x2)
    plot(x2,f_x2,'ro')
end


function bx = bernoulli_poly2 ( n, x )

%*****************************************************************************80
%
%% BERNOULLI_POLY2 evaluates the N-th Bernoulli polynomial at X.
%
%  Discussion:
%
%    Thanks to Bart Vandewoestyne for pointing out an error in the previous
%    documentation, 31 January 2008.
%
%    Special values of the Bernoulli polynomial include:
%
%      B(N,0) = B(N,1) = B(N), the N-th Bernoulli number.
%
%      B'(N,X) = N * B(N-1,X)
%
%      B(N,X+1) - B(N,X) = N * X^(N-1)
%      B(N,X) = (-1)^N * B(N,1-X)
%
%    A formula for the Bernoulli polynomial in terms of the Bernoulli
%    numbers is:
%
%      B(N,X) = sum ( 0 <= K <= N ) B(K) * C(N,K) * X^(N-K)
%
%    The first few polynomials include:
%
%      B(0,X) = 1
%      B(1,X) = X    - 1/2
%      B(2,X) = X^2 -   X      +  1/6
%      B(3,X) = X^3 - 3/2*X^2 +  1/2*X
%      B(4,X) = X^4 - 2*X^3   +      X^2 - 1/30
%      B(5,X) = X^5 - 5/2*X^4 +  5/3*X^3 - 1/6*X
%      B(6,X) = X^6 - 3*X^5   +  5/2*X^4 - 1/2*X^2 + 1/42
%      B(7,X) = X^7 - 7/2*X^6 +  7/2*X^5 - 7/6*X^3 + 1/6*X
%      B(8,X) = X^8 - 4*X^7   + 14/3*X^6 - 7/3*X^4 + 2/3*X^2 - 1/30
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    31 January 2008
%
%  Author:
%
%    John Burkardt
%
%  Parameters:
%
%    Input, integer N, the order of the Bernoulli polynomial to
%    be evaluated.  N must be 0 or greater.
%
%    Input, real X, the value at which the polynomial is to
%    be evaluated.
%
%    Output, real BX, the value of B(N,X).
%
  fact = 1.0;

  b = bernoulli_number3 ( 0 );

  bx = b;

  for i = 1 : n
    fact = fact * ( n + 1 - i ) / i;
    b = bernoulli_number3 ( i );
    bx = bx * x + fact * b;
  end

  return
end


function fx = p56_fun ( n, x )

%*****************************************************************************80
%
%% P56_FUN evaluates the integrand for problem 56.
%
%  Interval:
%
%    -1 <= x <= 1
%
%  Integrand:
%
%    1 / ( x^6 + 0.9 )
%
%  Approximate Integral (20 digits):
%
%    1.9922524079504000171...
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    12 November 2009
%
%  Author:
%
%    John Burkardt
%
%  Reference:
%
%    David Kahaner,
%    Comparison of Numerical Quadrature Formulas,
%    in Mathematical Software,
%    edited by John R Rice,
%    Academic Press, 1971.
%
%  Parameters:
%
%    Input, integer N, the number of evaluation points.
%
%    Input, real X(N), the evaluation points.
%
%    Output, real FX(N), the integrand values.
%
  fx(1:n) = 1.0 ./ ( x(1:n).^6 + 0.9 );

  return
end


function s = cardinal_sin ( j, m, n, t )

%*****************************************************************************80
%
%% CARDINAL_SIN evaluates the J-th cardinal sine basis function.
%
%  Discussion:
%
%    The base points are T(I) = pi * I / ( M + 1 ), 0 <= I <= M + 1.
%    Basis function J is 1 at T(J), and 0 at T(I) for I /= J
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    12 May 2014
%
%  Author:
%
%    John Burkardt
%
%  Reference:
%
%    John Boyd,
%    Exponentially convergent Fourier-Chebyshev quadrature schemes on
%    bounded and infinite intervals,
%    Journal of Scientific Computing,
%    Volume 2, Number 2, 1987, pages 99-109.
%
%  Parameters:
%
%    Input, integer J, the index of the basis function.
%    0 <= J <= M + 1.
%
%    Input, integer M, indicates the size of the basis set.
%
%    Input, integer N, the number of evaluation points.
%
%    Input, real T(N), one or more points in [0,pi] where the
%    basis function is to be evaluated.
%
%    Output, real S(N), the value of the function at T.
%
  tj = pi * j / ( m + 1 );

  s = ( -1.0 ) ^ mod ( j + 1, 2 ) ...
    * sin ( tj ) ...
    * sin ( ( m + 1 ) * t ) ...
    / ( m + 1 ) ...
    ./ ( cos ( t ) - cos ( tj ) );

  i = find ( abs ( t - tj ) < eps );
  s(i) = 1.0;

  return
end