/**
 *  A class that is extended to create specific objective functions
 *
 *  @author  Prof. David Bernstein, James Madison University
 *  @version 1.0
 */
public abstract class Objective
{

    private  double[] d, x, y;
    private  int n;




    /**
     * Explicit Value Constructor
     *
     * @param   size The dimension of the function's domain
     */
    public Objective(int size)
    {
       n = size;
       x = new double[n];
       d = new double[n];
       y = new double[n];
    }




    
    /**
     * Evalue this function
     *
     * This method must be overriden for functions that map from R^n to R
     *
     * @param x    The n-dimensional vector argument of the function
     * @return     The function evaluated at x
     */
    public double evaluate(double[] x)
    {
       double result;
       
       
       result = 0.0;
       return result;
    }




    /**
     * Evalue this function
     *
     * This method must be overriden for functions that map from R to R
     * so that it returns the function evaluation.
     *
     * For functions that map from R^n to R it should not be overriden
     * because it will return the function evalued at x + lambda * d
     *
     * @param lambda  The 1-dimensional argument of the function
     * @return        The function evaluation
     */
    public double evaluate(double lambda)
    {
       for (int i=0; i <= n-1; i++)
       {
          y[i] = x[i] + lambda*d[i];
       }

       return evaluate(y);
    }



    /**
     * @return  The dimension of the function's domain
     */
    public int getn()
    {
       return n;
    }




    /**
     * Sets a component of the x vector
     *
     * @param i    The index to set
     * @param val  The new value of component i
     */
    public void setxi(int i, double val)
    {
       x[i] = val;
    }



    /**
     * Sets the function's x vector
     *
     * @param val  The new value of the argument
     */
    public void setx(double[] val)
    {
       for (int i=0; i <= n-1; i++)
       {
          x[i] = val[i];
       }
    }
    


    /**
     * Sets a component of the direction vector associated with this function
     *
     * @param i    The index to set
     * @param val  The new value of component i
     */
    public void setdi(int i, double val)
    {
       d[i] = val;
    }



    /**
     * Sets the direction vector associated with this function
     *
     * @param val  The new direction vector
     * @see   v11
     */
    public void setd(double[] val)
    {
       for (int i=0; i <= n-1; i++) 
       {
          d[i] = val[i];
       }
    }



    /**
     * Returns a component of the function's x vector
     *
     * @param i    The index to retrieve
     * @return     The value of component i
     * @see   v11
     */
    public double getxi(int i)
    {
       return x[i];
    }



    /**
     * Returns the function's x vector
     *
     * @return     The vector argument
     * @see   v11
     */
    public double[] getx()
    {
       return x;
    }



    /**
     * Returns a component of the direction vector associated with 
     * this function
     *
     * @param i    The index to retrieve
     * @return     component i of the direction vector
     * @see   v11
     */
    public double getdi(int i)
    {
       return d[i];
    }



    /**
     * Returns the direction vector associated with this function
     *
     * @return     The direction vector
     * @see   v11
     */
    public double[] getd()
    {
       return d;
    }




}
