Mostrando entradas con la etiqueta modulo. Mostrar todas las entradas
Mostrando entradas con la etiqueta modulo. Mostrar todas las entradas

miércoles, 24 de agosto de 2011

Math Engine : Capitulo 2. Clase LPVector

Capítulo perteneciente al math engine LordPakus

Hola a todos,

Bienvenidos a un nuevo capitulo del math engine.

El capitulo de hoy trata sobre la clase LPVector que es la que se encarga de almacenar un vector de cualquier tamaño y poder opera con el.

La lista de operaciones que he considerado imprescindibles son las siguientes, todas las que querais que pongamos adicionales las ponemos... a la que tengamos una lista estable de operaciones nos dedicaremos a optimizarlas con SSE.:
//Funciones anexas.
    void Set(int t, float* vector); //Funcion para inicializar un vector de n elementos
    void Delete();                    //Función para limpiar la variable vector
    void print();                    //Función para imprimir el vector por la consola


    //OPERACIONES DE AMULACIÓN DE RESULTADO (+=,-=,etc...), devuelven void como norma general
    //Operaciones vectoriales
    void operator +=(LPVector vector);           
    void operator -=(LPVector vector);           
    void sqrt_vec();                        //Calculamos la raíz cuadrada de todo los elementos del vector
    void normalize();                        //Normaliza el vector (hace que el módulo sea 1)

    //Operaciones con escalares ( sumar , restar , etc ... todo un vector por un escalar)
    void operator +=(float scal);
    void operator -=(float scal);
    void operator *=(float scal);
    void operator /=(float scal);


    //OPERACIONES QUE DEVUELVEN ALGO (NO ACUMULADORES: +,-,*, etc...)
    //Operaciones vectoriales que devuelven escalares
    float operator ^(LPVector vector);            //Operador producto escalar.
    float module();                                //Calcula el módulo del vector

El código se organiza en dos archivos LPVector (.cpp y .h) junto con los cambios del main para demostrar que funcionan:

main.cpp:
/**************************************************************************************************/
//        Código creado por F.Bordas (LordPakus) como ejemplo de creación de un math engine
//        para el blog LordPakus (http://lordpakus.blogspot.com/).
//        Prohibida la distribución fuera de este blog sin el permiso expreso del autor
/**************************************************************************************************/

/**************************************************************************************************/
// main.cpp : Main de nuestro MathEngine
/**************************************************************************************************/

//Include del Math engine
#include "LPMath.h"

//Delete console
//#pragma comment(linker, "/subsystem:\"windows\" /entry:\"mainCRTStartup\"")

#include <iostream>                //Usada para imprimir por consola

using namespace std;

int main (int argc, char* argv[])
{
    LPVector v1,v2;
    float vec1[4] = { 1.0f ,1.1f ,1.5f ,2.5f };
    float vec2[4] = { 3.0f ,4.1f ,0.5f ,0.4f };

    float n;

    //Creamos los vectores
    v1.Set(4,vec1);
    v2.Set(4,vec2);

    cout << "Vector 1: ";
    v1.print();
    cout << "\n";

    cout << "Vector 2: ";
    v2.print();
    cout << "\n";
   
    n = v1^v2;
    cout << "Producto escalar: " <<    n << "\n";

    n = v1.module();
    cout << "Modulo vector 1: " <<    n << "\n";

    n = v2.module();
    cout << "Modulo vector 2: " <<    n << "\n";

    v1.normalize();
    n = v1.module();
    cout << "Modulo vector 1 normalizado: " <<    n << "\n";

    v2.normalize();
    n = v2.module();
    cout << "Modulo vector 2 normalizado: " <<    n << "\n";

    v2 += v1;
    cout << "Suma de vectores: ";
    v2.print();
    cout << "\n";

    n = v2.module();
    cout << "Modulo de suma de vectores: " <<    n << "\n";

    v2.normalize();
    n = v2.module();
    cout << "Modulo de suma de vectores normalizado: " <<    n << "\n";


    //Eliminamos los vectores
    v1.Delete();
    v2.Delete();

    system("PAUSE");
}

LPVector.cpp
/**************************************************************************************************/
//        Código creado por F.Bordas (LordPakus) como ejemplo de creación de un math engine
//        para el blog LordPakus (http://lordpakus.blogspot.com/).
//        Prohibida la distribución fuera de este blog sin el permiso expreso del autor
/**************************************************************************************************/

#include "LPVector.h"
#include <math.h>
#include <iostream>                //Usada para imprimir por consola

using namespace std;

//Constructor
LPVector::LPVector()
{
    n = 0;
    v = NULL;
}

//Destructor
LPVector::~LPVector()
{
    //if (n)
    //{
    //    if( v != NULL )
    //        free(v);
    //}
}

//Funcion para inicializar un vector de n elementos
void LPVector::Set(int t, float* vector)
{
    n = t; //Inicializamos el número de elementos del vector

    //Creamos un vector de memoria dinámica.
    v = (float*) malloc( sizeof(float) * n );

    //Copiamos el vector externo en el vector interno
    memcpy(v,vector,sizeof(float) * n );
}

//Función para limpiar la variable vector
void LPVector::Delete()
{
    n=0;
    free(v);
}

//Imprimimos el valor del vector
void LPVector::print()
{
    for(int i = 0 ; i < n ; ++i)
    {
        cout << (float) v[i] << " ";
    }
}

void LPVector::random(int t, float min, float max)
{
    n = t; //Inicializamos el número de elementos del vector

    //Creamos un vector de memoria dinámica.
    v = (float*) malloc( sizeof(float) * n );

    for(int i = 0 ; i < n ; ++i)
        v[i] = (float)(rand()%(int)(max*1000 - min*1000))/1000 + min;

}

void LPVector::cross(LPVector vector)
{
    //POR IMPLEMENTAR
}

void LPVector::sqrt_vec()
{
    for(int i = 0 ; i < n ; ++i)
        v[i] = sqrt(v[i]);
}

void LPVector::normalize()
{
    //Dividimos cada componente por el módulo
    *this /= this->module();
}

//Sobrecarga operador +=
void LPVector::operator +=(LPVector vector)
{
    //Si las dimensiones son diferentes , tenemos un problema grave.
    if (n != vector.n)
    {
        cout << "ERROR DIMENSIONAL ENTRE VECTORES\n";
        return;
    }

    for(int i = 0 ; i < n ; ++i)
        v[i] += vector.v[i];
  
}

//Sobrecarga operador -=
void LPVector::operator -=(LPVector vector)
{
    //Si las dimensiones son diferentes , tenemos un problema grave.
    if (n != vector.n)
    {
        cout << "ERROR DIMENSIONAL ENTRE VECTORES\n";
        return;
    }

    for(int i = 0 ; i < n ; ++i)
        v[i] -= vector.v[i];
}

//Sobrecarga operador +=
void LPVector::operator +=(float scal)
{
    for(int i = 0 ; i < n ; ++i)
        v[i] += scal;
}

//Sobrecarga operador -=
void LPVector::operator -=(float scal)
{
    for(int i = 0 ; i < n ; ++i)
        v[i] -= scal;
}

//Sobrecarga operador *=
void LPVector::operator *=(float scal)
{
    for(int i = 0 ; i < n ; ++i)
        v[i] *= scal;
  
}

//Sobrecarga operador /=
void LPVector::operator /=(float scal)
{
    for(int i = 0 ; i < n ; ++i)
        v[i] /= scal;
  
}
//Sobrecarga operador *= //Este operador es el que nos devolverá matrices como resultado del producto de una columna por un fila.
                         //Es decir, es el producto vectorial. Ya lo veremos a su momento
/*void LPVector::operator *=(LPVector vector)
{
    //Si las dimensiones son diferentes , tenemos un problema grave.
    if (n != vector.n)
    {
        cout << "ERROR DIMENSIONAL ENTRE VECTORES\n";
        return;
    }

    for(int i = 0 ; i < n ; ++i)
        v[i] += vector.v[i];
}
*/

//Sobrecarga operador ^ A partir de ahora se entederá que es el producto escalar.
float LPVector::operator ^(LPVector vector)
{
    float a = 0.0;

    //Si las dimensiones son diferentes , tenemos un problema grave.
    if (n != vector.n)
    {
        cout << "ERROR DIMENSIONAL ENTRE VECTORES\n";
        return 0.0;
    }

    for(int i = 0 ; i < n ; ++i)
        a += v[i] * vector.v[i];

    return a;
}

float LPVector::module()
{
    float a = 0.0;

    for(int i = 0 ; i < n ; ++i)
        a += v[i] * v[i];

    return sqrt(a);
}

float LPVector::distance(LPVector vector)
{
    float a = 0.0;
    float temp = 0.0;

    //Si las dimensiones son diferentes , tenemos un problema grave.
    if (n != vector.n)
    {
        cout << "ERROR DIMENSIONAL ENTRE VECTORES\n";
        return (-1.0);
    }

    for(int i = 0 ; i < n ; ++i)
    {
        temp = (v[i] - vector.v[i]);
        a+=temp*temp;
    }

    return sqrt(a);
}


LPVector.h
/**************************************************************************************************/
//        Código creado por F.Bordas (LordPakus) como ejemplo de creación de un math engine
//        para el blog LordPakus (http://lordpakus.blogspot.com/).
//        Prohibida la distribución fuera de este blog sin el permiso expreso del autor
/**************************************************************************************************/


/**************************************************************************************************/
// LPVector.h
/**************************************************************************************************/

#ifndef __LPVector__
#define __LPVector__

class LPVector
{
public:
    LPVector();
    ~LPVector();

    //Funciones anexas.
    void Set(int t, float* vector); //Funcion para inicializar un vector de n elementos
    void Delete();                    //Función para limpiar la variable vector
    void print();                    //Función para imprimir el vector por la consola
    void random(int t,float min, float max);                //Función para rellenar de random un vector de t posiciones

    //OPERACIONES DE AMULACIÓN DE RESULTADO (+=,-=,etc...), devuelven void como norma general
    //Operaciones vectoriales
    void operator +=(LPVector vector);          
    void operator -=(LPVector vector);  
    void cross(LPVector vector);            //Calculamos el producto vectorial (cross) POR HACER
    void sqrt_vec();                        //Calculamos la raíz cuadrada de todo los elementos del vector
    void normalize();                        //Normaliza el vector (hace que el módulo sea 1)
          

    //Operaciones con escalares ( sumar , restar , etc ... todo un vector por un escalar)
    void operator +=(float scal);
    void operator -=(float scal);
    void operator *=(float scal);
    void operator /=(float scal);


    //OPERACIONES QUE DEVUELVEN ALGO (NO ACUMULADORES: +,-,*, etc...)
    //Operaciones vectoriales que devuelven escalares
    float operator ^(LPVector vector);            //Operador producto escalar.
    float module();                                //Calcula el módulo del vector
    float distance(LPVector vector);

public:
    int n;         //número de elementos del vector
    float *v;    //puntero a memoria dinámica
};

#endif
Cualquier otra cosa que se os ocurra que le pongamos o cualquier fallo que veais, hacedmelo llegar

Espero que os haya gustado,

Nos vemos

EDIT:
27-08-2011:Se han añadido las funciones siguientes:
       - vector de randoms
       - distancia entre vectores
       - se deja a la espera el cross product (alguíen tiene el código y me lo quiere pasar??)

Entradas populares