Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   Varios (https://www.clubdelphi.com/foros/forumdisplay.php?f=11)
-   -   Problemas con el error: access violation at 0x77d9dede: write of address 0x00090fec (https://www.clubdelphi.com/foros/showthread.php?t=80988)

TecnoBestia 29-09-2012 22:50:33

Problemas con el error: access violation at 0x77d9dede: write of address 0x00090fec
 
Hola, tengo un problema que hace que mi programa se caiga.

Tengo el siguiente procedimiento

Código:

procedure clsHormiga.CamineYClasifique();
    var
      i,NumDeNodo:Integer;
      Suma:Double;
      VecDeProbabilidades:VectorIR;
    begin
      SetLength(VecDeProbabilidades,3);
      for i:=1 to R do begin
        VecDeProbabilidades[i-1]:=1
      end;
    end;

resulta que cuando pasa por la instrucción SetLength(VecDeProbabilidades,3); se muestra el siguiente mensaje:



e inmediatamente se muestra



El problema que no sé a que se debe el error, ya muchas otras veces he trabajado con vectores y nunca me ha pasado algo similar. Si alguien puede ayudarme se los estaría muy agradecido. No tengo la menor idea de porqué o qué hacer. No entiendo los mensajes ni que hacer.

Un detalle es que
VectorIR=array of Double;

Gracias de antemano.

Casimiro Notevi 29-09-2012 23:05:21

¿Y qué es la R del bucle?, ¿cuánto vale?, ¿de dónde saca el valor?

Código Delphi [-]
for i := 1 to R do

TecnoBestia 29-09-2012 23:45:33

Es una variable global, tiene un valor de 3.

TecnoBestia 29-09-2012 23:49:31

De hecho, el for no importa, lo he quitado y el problema se da al redefinir el tamaño del vector. De hecho, el código dado por:
Código:

procedure clsHormiga.CamineYClasifique();
    var
      i,NumDeNodo:Integer;
      Suma:Double;
      VecDeProbabilidades:VectorIR;
    begin
      SetLength(VecDeProbabilidades,3);
    end;

El problema se sigue dando, el mismo para ser preciso.
Gracias por responder.

Casimiro Notevi 30-09-2012 00:11:38

¿Y por qué usas VecDeProbabilidades en lugar de VectorIR?

ecfisa 30-09-2012 01:16:18

Hola.

Te faltó incluir algo importante. De tu código se podría inferir que VectorIR está declarado como:
Código Delphi [-]
type
   VectorIR = array of Integer;
Pero si fuera así, las líneas:
Código Delphi [-]
var
  VecDeProbabilidades:VectorIR;
begin
  SetLength(VecDeProbabilidades,3)
end;
no generarían ningún error...

¿ Que es VectorIR ?

Saludos.

TecnoBestia 30-09-2012 02:44:07

Ese es el problema, yo considero que no debería haber ningún problema. La unidad completa es la siguiente:

Código Delphi [-]
unit Declaraciones;

interface
uses
  Classes,Math;

type
  VectorIR=array of Double;    //Tipo de Vector de Reales
  VectorINT=array of Integer;  //Tipo Vector de Enteros
  MatrizIR=array of VectorIR;  //Tipo Matriz de reales, para la Tabla de Datos

  //*******************************************************************************************
  //############################   Objeto clsParticula ########################################
  //*******************************************************************************************
  clsHormiga=class(TObject)  //Objeto clsPartícula.
  private
    function DistanciaAlCudrado(k_Individuo:Integer; k_CG:Integer):Double;
    {procedure CalcularCG_dada_Clasificacion;   }
  protected
  public

    {Definición de Variables del objeto clsParticulas}
    {Idea básica del algoritmo:
    Considere R centros de gravedad (generados aleatoriamente, o tomando R individuos al azar) y coloque en forma
    aleatoria una hormiga en cada un de los vértices (los vertices son los indiviuos de la tabla a clasificar). Una hormiga
    intentará viajar a cada uno de los nodos (otros individuos). La forma en que un hormiga viaja de un nodo a otro se hace
    con la regla de desplazamiento de la hormiga (visión, feromona y aleatorio). Cuando una hormiga llega a un nodo, se debe
    clasificar en alguno de los R centros, dicha clasificación deberá ser calculada al llegar la hormiga y antes de ir al
    siguiente nodo. La regla para la clasificación, de un nodo debe de retroalimentarse de un segundo rastro de feromona que
    han dejado otras hormigas que han clasificado dicho nodo anteriormente, además, deberá utilizar la visibilidad, esto es
    la cercanía del nodo al centro de gravedad deberá ser considerada}


    {VectorDeProbaDe_Nodoi_Nodoj:VectorIR;                         {Es un vector de tamaña 1xM (número de individos por clasificar)
                                                                  En la entrada i se encuentra la probabilidad de dirigirse de la
                                                                  posición acutal al nodo i de la lista. Los nodos que ya fueron
                                                                  clasificados tienen un cero en su probabilidad de ser visitados
                                                                  nuevamente}
    ListaDeNodosAClasificar:VectorINT;                            {Contienes una lista de "tamaño variante" con los nodos
                                                                  que faltan de clasificar}
    NumeroNodosPorClasificar:Integer;                             {Es un entero que contiene el número de nodos a clasificar en la Lista anterior
                                                                  cada vez que se clasifica un nodo, este contador disminuye en una unidad}
    Tk:VectorINT;                                                 {Clasificación construida por la k-ésima hormiga
                                                                  En este caso, cada hormiga realiza construye una
                                                                  clasificación, esta se va guardando en la lista Tk
                                                                  Tk=(2,3,4,2,...) indica la clasificación indi1 en cls2
                                                                  indi 2 en cls3 indi 3 en cls4...}
    PosicionActualDeLaHormiga:Integer;                            {Último dato clasificado, último nodo que fue clasificado,
                                                                  de aquí, deberá seleccionar otro nodo para clasificar.}
    MatrizCG:MatrizIR;                                            {Es una matriz de tamaño R x N. (Número de Clases por Variables) Cada una de las filas
                                                                  filas de la matriz es un CG. De hecho la fila i es el CG de la clase i+1.}
    VCardinalidades:VectorINT;                                    {Es de tamaño R y en la posición i posee la cadi del grupo i+1}




    {Definición de procedimientos y funciones}
   { procedure Inicializacion;
    procedure DeterminarVClasificacionYVDistancias;
    procedure Apliquese_K_Medias;
    procedure Muevase_A_NuevaPosicion(IndiceParticulaEnMovimiento:Integer);
    function Clon():clsParticula ; {Se encarga de hacer un clon}
    procedure IniciarCG;
    procedure CamineYClasifique;
  published
  end;

var
    PoblacionOriginaldeIndi:MatrizIR;   {Matriz que posee tamaño MxN, donde M:Número de Individuos y
                                         N:Número de Variables}

    M,N,R:Integer;                      {M:Número de Individuos. N:Número de variables y R:Número de Clases}

    //Matriz_FeromonaIndi_Indi:MatrizIR;    {Esta matriz es de tamaño MxM (M: Número de individuos a clasificar)
                                         {En la posición i,j de la matriz, tendrá la cantidad de feromona depositada
                                         por las hormigas cuando se dirigieron del nodo i ya clasificada y al nodo
                                         j próximo en ser clasificado.}
    Matriz_FeromonaIndi_CG:MatrizIR;     {Esta es una matriz de tamaño MxR, (Individuos x Centros de Gravedad) en la posición
                                         i,j de la matriz se encuentra la canditdad de feromona que han depositado las hormigas
                                         al clasificar el nodo i en el centro de gravedad j.}
    MatrizDeAcotaciones:MatrizIR;

    Alpha,Beta:Double;                    {Parámetros de la visibilidad y la feromona}







implementation
//------------------------------------------------------------------------------

    function clsHormiga.DistanciaAlCudrado(k_Individuo:Integer; k_CG:Integer):Double;
    {Esta función recibe el índice del Individuo y el índice del CG, retorna La Distancia  al Cuadrado
    Entre el Individuo y el CG.}
    var
      i:Integer;
      suma0:Double;
    begin
      suma0:=0;
      for i:=0 to N-1 do  begin
        suma0:=suma0+sqr(PoblacionOriginaldeIndi[k_Individuo-1,i]-Self.MatrizCG[k_CG-1,i]);
      end;
      Result:=suma0;
    end;

//------------------------------------------------------------------------------

    procedure clsHormiga.IniciarCG();
    var
      i,j:Integer;
    begin
      SetLength(Self.MatrizCG,R,N);
      SetLength(Self.ListaDeNodosAClasificar,M);
      SetLength(Self.VCardinalidades,R);
      Randomize;
      for i:=0 to R-1 do begin
        for j:=0 to N-1 do begin
          MatrizCG[i,j]:=Random*(MatrizDeAcotaciones[1,i]-MatrizDeAcotaciones[0,i])+ MatrizDeAcotaciones[0,i];
        end;
      end;

      for i:=0 to M do begin
        Self.ListaDeNodosAClasificar[i]:=i+1;
      end;

      Self.NumeroNodosPorClasificar:=M;
      Alpha:=1;
      Beta:=1;
      //Self.PosicionActualDeLaHormiga:=Random(M);
    end;

//------------------------------------------------------------------------------

    procedure clsHormiga.CamineYClasifique();
    var
      i,NumDeNodo:Integer;
      Suma:Double;
      VecDeProbabilidades:VectorIR;
    begin
      SetLength(VecDeProbabilidades,3);


    end;


//------------------------------------------------------------------------------


end.

Es claro que este último porcedure no está completo, el debe hacer varias cosas que he quitado para mostrar el error. Este error se genera cuando redefino el tamaño del vector VecDeProbabilidades, sin embargo, ese mismo trabajo se hace con otros vectores y no se genera el problema.

Sin embargo, me sigue lanzando el error, les agradezco que intenten ayudarme. Ya he realizado varios programas en Delphi 7 y esta es la primera vez que me pasa algo así, lo que trataré de hacer es iniciar de cero, reescribiré el código de nuevo esperando que el error no se repita. Gracias de todos modos y saludos...

ecfisa 30-09-2012 07:47:15

Hola.

Según lo que pude ver de la clase clsHormiga, ya tendrías un error al llamar al método IniciarCG:
Código Delphi [-]
procedure clsHormiga.IniciarCG();
var
 i,j:Integer;
begin
  SetLength(Self.MatrizCG, R, N);
  SetLength(Self.ListaDeNodosAClasificar, M); // Aqui M es igual a 0 !!
  SetLength(Self.VCardinalidades, R);
  Randomize;
  for i:=0 to R-1 do
    for j:=0 to N-1 do
      MatrizCG[i,j]:= Random*(MatrizDeAcotaciones[1,i]-MatrizDeAcotaciones[0,i])+MatrizDeAcotaciones[0,i];
  for i:=0 to M do
   Self.ListaDeNodosAClasificar[i]:= i + 1;  // <- Error!, aún si M = 0 la línea se ejecuta una vez
  Self.NumeroNodosPorClasificar:= M;
  Alpha:=1;
  Beta:=1;
  //Self.PosicionActualDeLaHormiga:=Random(M);
end;
Tal vez M tome algún valor en el constructor (si existe) o en el método Inicializacion. Pero lamentablemente no puedo verificarlo por que en el código que adjuntaste, falta la definición de este último.

Saludos.

TecnoBestia 30-09-2012 17:30:37

Muchísimas gracias. Es claro que le atinaste al error, M corresponde al tamaño de un vector dinámico, y el for que mencionas recorre el vector de modo que si inicia en i:=0 debería terminar en M-1 y no en M. De esta manera estaba guardando un dato extra en una posición de memoria fuera del vector, lo que ocasiona el error. Como el error lo marcaba en otra línea, no me había percatado de lo anterior.

Pero de verdad le agradezco demasiado. Ya estaba a punto de reescribir el código nuevamente a ver si acaso.

Saludos...


La franja horaria es GMT +2. Ahora son las 18:18:26.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi