Haciendo una encuesta para un blog me encontré con un problema en flash, el cual tenia que resolver para poder graficar esa encuesta, cual fue ese problema, pues básicamente se escuchaba bastante sencillo y era el siguiente.

Hacer una Clase que pasándole como parámetro un Array Numérico, me devolviera el número mayor de ese Array y la posición (índice) donde se encuentra ese número mayor.

Bueno después de varios intentos fallidos me decidí a buscar en la red algo así y encontré una pagina que tenia algo como esto ORDENACION POR EL METODO QUICKSORT (Bastante bueno el algoritmo) les dejo la Pagina.
http://members.fortunecity.com/albertoduran/orden/quicksort.htm.

Bueno ya en este punto era sencillo usando el método QUICKSORT Podía ordenar un Array en forma ascendente y así obtener el numero mayor. Esto por lógica se lograba sacando el último número de ese Array ya ordenado puesto que ese último número será el mayor de todos.

Pues bien me di a la tarea de empezar a realizar la clase.

Código :

class QuickSort
{
   /////Creamos las Variables que vamos a Ocupar 
   private var vArrayOrdenado:Array;
   private var vArrayElementos:String;
   public var ArraySinOrdenar:String;
   /////Aquí hacemos la Funcion Constructora
   public function QuickSort (pArrayAOrdenar:Array)
   {
      this.ArraySinOrdenar = pArrayAOrdenar;
      this.vArrayOrdenado = pArrayAOrdenar;
//////////////////////////Llamamos a la función ordenaArray 
      this.ordenaArray (0, pArrayAOrdenar.length - 1);
   }
   /////////////////////Aquí Obtenemos el Numero mayor del Array una vez Ordenado el mismo
   public function getHigher ():Number
   {
      return this.vArrayOrdenado[vArrayOrdenado.length - 1];
   }
   ////////////////Aquí Obtenemos la posición de ese numero mayor 
   public function getPositionHigher ():Number
   {
      var index:Number;
      var seekValue = getHigher ();
      //trace("Dentro1 "+this. ArraySinOrdenar);
      for (index = 0; index < ArraySinOrdenar.length; index++)
      {
         if (ArraySinOrdenar [index] == seekValue)
         {
            break;
         }
      }
      return index;
   }
   ////////////////Aquí implementamos el Método  QUICKSORT
   private function ordenaArray (pIzquierda:Number, pDerecha:Number)
   {
      var pivote, pivoteIzquierdo, pivoteDerecho:Number;
      pivoteIzquierdo = pIzquierda;
      pivoteDerecho = pDerecha;
      pivote = this.vArrayOrdenado[pIzquierda];
      while (pIzquierda < pDerecha)
      {
         while ((vArrayOrdenado[pDerecha] >= pivote) && (pIzquierda < pDerecha))
         {
            pDerecha--;
         }
         if (pIzquierda != pDerecha)
         {
            this.vArrayOrdenado[pIzquierda] = this.vArrayOrdenado[pDerecha];
            pIzquierda++;
         }
         while ((this.vArrayOrdenado[pIzquierda] <= pivote) && (pIzquierda < pDerecha))
         {
            pIzquierda++;
         }
         if (pIzquierda != pDerecha)
         {
            this.vArrayOrdenado[pDerecha] = this.vArrayOrdenado[pIzquierda];
            pDerecha--;
         }
      }
      this.vArrayOrdenado[pIzquierda] = pivote;
      pivote = pIzquierda;
      pIzquierda = pivoteIzquierdo;
      pDerecha = pivoteDerecho;
      if (pIzquierda < pivote)
      {
         ordenaArray (pIzquierda, pivote - 1);
      }
      if (pDerecha > pivote)
      {
         ordenaArray (pivote + 1, pDerecha);
      }
   }
}

Bueno Aparentemente la clase estaba bien, me retornaba el número mayor del Array solo con mandar a llamar al método getHigher();

Pero había un problema enorme que al mandar a llamar al método getPositionHigher(); no me regresaba la posición original de ese numero mayor, sino que me regresaba la posición del Array ya ordenado por ejemplo si mi Array es así:

var serie:Array = new Array(0,5,7,12,65,78,32,45,12,10) El numero mayor es 78 y su posición es 5 Tomando en cuenta que las posiciones de los Arrays empiezan en 0, pero lo que la clase me regresaba era lo siguiente.

getHigher = 78;
getPositionHigher = 9; :shock:

Esto como ya lo comente era por que me regresaba la posición del Array ya ordenado, la pregunta era ¿Por que? Si en la clase al momento de crear las variables había una variable llamada ArraySinOrdenar, la cual nunca pasaba por el proceso de ordenamiento y por consecuencia no tenia por que ordenarse ese Array.
Me explico, la variable vArrayOrdenado era asignada al array que traigo como parámetro y era la que se sometía al proceso de ordenamiento, pero la variable ArraySinOrdenar, que también era asignara al Array que traigo como parámetro no se sometía a este proceso pero sin embargo también se ordenaba y por consecuencia al ser también ordenada pues la posición de ese número mayor era la ultima y no la realmente original. :crap:

Después de varias horas de análisis entre mi gran amigo Raúl (Shivan) y yo (Dalinet), llegamos a la conclusión que el problema era una cuestión de herencia. (Maldita herencia), si esa maravillosa cosa que tienen los objetos llamada herencia, que te permite tener todas las propiedades eventos y métodos de un objeto en todas sus instancias, ahora eso era el problema, explico por que:

Bastante sencillo y lógico según nuestra lógica (Valga la redundancia)

En la función constructora hicimos esto:

Código :

/////Aquí hacemos la Funcion Constructora
   public function QuickSort (pArrayAOrdenar:Array)
   {
      this.ArraySinOrdenar = pArrayAOrdenar;
      this.vArrayOrdenado = pArrayAOrdenar;
//////////////////////////Llamamos a la función ordenaArray 
      this.ordenaArray (0, pArrayAOrdenar.length - 1);
   }

El Array que traemos como parámetro fue asignado a dos variables aun que diferentes eran dos instancias diferentes de un mismo Objeto ¿cual objeto? Pues pArrayAOrdenar ose a al hacer esto:

this.ArraySinOrdenar = pArrayAOrdenar;
this.vArrayOrdenado = pArrayAOrdenar;

Lo que hicimos fue de un mismo objeto crear dos instancias, por lógica al cambiar cualquiera de esas dos instancias en su estructura cambiaba el objeto en si y por consecuencia todas sus instancias también cambiaban.

Ahora el reto era romper esa herencia, aquí se los cuento muy rápido pero la solución fue tan sencilla que era casi imposible encontrarla, ¿cual fue la solución?, Aquí se las dejo:

Código :

public function QuickSort (pArrayAOrdenar:Array)
   {
      this.ArraySinOrdenar = pArrayAOrdenar.toString();
      this.ArrayNoOrdenado = ArraySinOrdenar.split(",");
      this.vArrayOrdenado = pArrayAOrdenar;
      this.ordenaArray (0, pArrayAOrdenar.length - 1);
   }

Sencillo no?, jejejeje les explico dentro de la función constructora a la variable ArraySinOrdenar le asignamos el Array que traemos como parámetro pero convertido en un String con la función toString() Después creamos otra variable llamada ArrayNoOrdenado a la cual se le fue asignada la variable ArraySinOrdenar que ya era un String pero con la función split(“,”), tomando en cuanta que un Array convertido a string se convierte en una cadena de todos los elementos de ese Array separados por comas y al someter a una cadena a la función split() esa cadena se convierte en un Array separando a todos los elementos por el parámetro que se le pasa al split en este caso la coma (“,”) Bendita coma jejejejejej Pues al final tenemos un nuevo Array llamado ArrayNoOrdenado que no tiene nada que ver con la instancia primaria.

Y pues al final de esta peripecia la clase quedo así y completamente funcional.

Código :

class QuickSort
{
   private var vArrayOrdenado:Array;
   private var vArrayElementos:String;
   public var ArraySinOrdenar:String;
   public var ArrayNoOrdenado:Array;
   public function QuickSort (pArrayAOrdenar:Array)
   {
      this.ArraySinOrdenar = pArrayAOrdenar.toString();
      this.ArrayNoOrdenado = ArraySinOrdenar.split(",");
      this.vArrayOrdenado = pArrayAOrdenar;
      this.ordenaArray (0, pArrayAOrdenar.length - 1);
   }
   /////////////////////
   public function getHigher ():Number
   {
      return this.vArrayOrdenado[vArrayOrdenado.length - 1];
   }
   ////////////////
   public function getPositionHigher ():Number
   {
      var index:Number;
      var seekValue = getHigher ();
      //trace("Dentro1 "+this.ArrayNoOrdenado);
      for (index = 0; index < ArrayNoOrdenado.length; index++)
      {
         if (ArrayNoOrdenado[index] == seekValue)
         {
            break;
         }
      }
      return index;
   }
   ////////////////
   private function ordenaArray (pIzquierda:Number, pDerecha:Number)
   {
      var pivote, pivoteIzquierdo, pivoteDerecho:Number;
      pivoteIzquierdo = pIzquierda;
      pivoteDerecho = pDerecha;
      pivote = this.vArrayOrdenado[pIzquierda];
      while (pIzquierda < pDerecha)
      {
         while ((vArrayOrdenado[pDerecha] >= pivote) && (pIzquierda < pDerecha))
         {
            pDerecha--;
         }
         if (pIzquierda != pDerecha)
         {
            this.vArrayOrdenado[pIzquierda] = this.vArrayOrdenado[pDerecha];
            pIzquierda++;
         }
         while ((this.vArrayOrdenado[pIzquierda] <= pivote) && (pIzquierda < pDerecha))
         {
            pIzquierda++;
         }
         if (pIzquierda != pDerecha)
         {
            this.vArrayOrdenado[pDerecha] = this.vArrayOrdenado[pIzquierda];
            pDerecha--;
         }
      }
      this.vArrayOrdenado[pIzquierda] = pivote;
      pivote = pIzquierda;
      pIzquierda = pivoteIzquierdo;
      pDerecha = pivoteDerecho;
      if (pIzquierda < pivote)
      {
         ordenaArray (pIzquierda, pivote - 1);
      }
      if (pDerecha > pivote)
      {
         ordenaArray (pivote + 1, pDerecha);
      }
   }
}


Espero les sirva. jejejeje :D