Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   OOP (https://www.clubdelphi.com/foros/forumdisplay.php?f=5)
-   -   Problea con Clase creada dentro de otra. (https://www.clubdelphi.com/foros/showthread.php?t=18174)

Holderhek 03-02-2005 21:33:29

Problema con Clase creada dentro de otra.
 
Hola

Cree una clase que maneja la estructura de categorias y subcategorias.

Cada categoria tiene asociadas ciertas propiedades (Nombre, ID, Indice de Icono, Campos, etc) y ademas un Arreglo de SubCategorias.

Cada SubCategoria tiene ciertas propiedades (Nombre, IndiceIcono, Categoria a la que pertenece, etc)

Y la clase que controla todo se llama TEstructuraCategorias y tiene un ADOConnection y un arreglo de Categorias.

Tiene un ADOConnection por que con este hace una consulta a una BD y saca toda la estructura de las categorias.

Mi problema es el siguiente. Tengo definidas las 3 clases:

Código:

type
    TSubcategoria = class
    private
          cIDSubCategoria: Integer;
          cIDCategoria: Integer;
          cNombreSubCategoria: String;
          cIndiceIcono: Integer;
    public
        property IDSubCategoria: Integer        read cIDSubCategoria        write cIDSubCategoria;
        property IDCategoria: Integer                read cIDCategoria                write cIDCategoria;
          property NombreSubCategoria: String  read cNombreSubCategoria  write cNombreSubCategoria;
        property IndiceIcono: Integer                read cIndiceIcono                write cIndiceIcono;
        constructor Crear(aIDSubCategoria: Integer; aIDCategoria: Integer; aNombreSubCategoria: String; aIndiceIcono: Integer);
    end;
 
  type
    TStrings = Array of String;
    TSubCategorias = Array of TSubCategoria;
    TCategoria = class
    private
          cIDCategoria: Integer;
          cNombreCategoria: String;
          cIndiceIcono: Integer;
          cPrefijo: String;
          cNombreCampos: TStrings;
          cCantidadCampos: Integer;
          cSubCategorias: TSubCategorias;
    public
        property IDCategoria: Integer                                read cIDCategoria        write cIDCategoria;
        property NombreCategoria: String                                read cNombreCategoria write cNombreCategoria;
        property IndiceIcono: Integer                                read cIndiceIcono        write cIndiceIcono;
        property Prefijo: String                                                read cPrefijo                write cPrefijo;
        property NombreCampos: TStrings                                read cNombreCampos        write cNombreCampos;
        property CantidadCampos: Integer                                read cCantidadCampos write cCantidadCampos;
        property SubCategorias: TSubCategorias                read cSubCategorias        write cSubCategorias;
        constructor Crear(aIDCategoria: Integer; aNombreCategoria: String; aIndiceIcono: Integer; aPrefijo: String; aCampo1: String; aCampo2: String; aCampo3: String; aCampo4: String; aCampo5: String; aCampo6: String; aCampo7: String; aCampo8: String; aCampo9: String; aCampo10: String);
        procedure AgregarSubCategoria(aIDSubCategoria: Integer; aNombreSubCategoria: String; aIndiceIcono: Integer);
    end;
 
  type
    TCategorias = Array of TCategoria;
    TEstructuraCategorias = class
    private
          cConnection: TADOConnection;
          cCategorias: TCategorias;
    public
          property Categorias: TCategorias  read cCategorias write cCategorias;
          constructor Crear(aConnection: TADOConnection);
          procedure Actualizar;
    end;

Y luego en la implementacion del TEstructurasCategorias tengo:

Código:

constructor TEstructuraCategorias.Crear(aConnection: TADOConnection);
  begin
    cConnection:=aConnection;
    Actualizar;
  end;
  procedure TEstructuraCategorias.Actualizar;
  var
    i, j: integer;
    Categoria: TCategoria;
    Query, Query1: TADOQuery;
  begin
    Query:=TADOQuery.Create(nil);
    Query.Connection:=cConnection;
    Query1:=TADOQuery.Create(nil);
    Query1.Connection:=cConnection;
    Query.Close;
    Query.SQL.Text:='SELECT * FROM Categorias ORDER BY Nombre';
    Query.Open;
    For i:=0 to Query.RecordCount-1 do
    begin
 Categoria:=TCategoria.Crear(Query.Fields[0].AsInteger, Query.Fields[1].AsString, Query.Fields[2].AsInteger, Query.Fields[3].AsString,
          Query.Fields[4].AsString, Query.Fields[5].AsString, Query.Fields[6].AsString, Query.Fields[7].AsString, Query.Fields[8].AsString,
          Query.Fields[9].AsString, Query.Fields[10].AsString, Query.Fields[11].AsString, Query.Fields[12].AsString, Query.Fields[13].AsString);
          Query1.Close;
        Query1.SQL.Text:='SELECT * FROM SubCategorias ORDER BY Nombre WHERE IDCategoria='+Query.Fields[1].AsString;
          Query1.Open;
          For j:=0 to Query1.RecordCount do
          begin
          Categoria.AgregarSubCategoria(Query1.Fields[0].AsInteger, Query1.Fields[2].AsString, Query1.Fields[3].AsInteger);
            Query1.Next;
          end;
          SetLength(cCategorias, High(cCategorias)+2);
          cCategorias[High(cCategorias)]:=Categoria;
          Query.Next;
    end;
    Query.Close;
    Query.Free;
    Query1.Close;
    Query1.Free;
  end;

O sea, creo un TEstructurasCategorias y este hace la consulta, empieza a crear Categorias y las va agregando al arreglo de TCategorias.
Pero cuando lo ejecuto me dice EAccessViolation al crear una Categoria.

O sea, cuando pongo Break, me marca esta linea:
Código:

Categoria:=TCategoria.Crear(Query.Fields[0].AsInteger, Query.Fields[1].AsString, Query.Fields[2].AsInteger, Query.Fields[3].AsString,
          Query.Fields[4].AsString, Query.Fields[5].AsString, Query.Fields[6].AsString, Query.Fields[7].AsString, Query.Fields[8].AsString,
          Query.Fields[9].AsString, Query.Fields[10].AsString, Query.Fields[11].AsString, Query.Fields[12].AsString, Query.Fields[13].AsString);

y dice:
Cita:

Project prjBVI.exe raised an exception class EAccessException with message 'Access vioation at address 004042C0 in module PrjBVI.exe. Write of address 0000000
Bueno, espero me ayuden.
Gracias por su tiempo.
Saludos.

maeyanes 03-02-2005 22:28:09

A simple vista no veo nada raro. Tal vez el error se encuentra en el código Create de TCategoria. Pon ese código para checarlo.

Por otro lado, te recomendaría mejor que uses un TList para guardar las Categorias que vas leyendo.

Código Delphi [-]
// Declaras la lista
cCategorias: TList;

// La creas en el Create de la clase
cCategorias := TList.Create;

// Agregas una categoria
cCategorias.Add(Categoria);

// Obtienes una categoria de la lista
Categoria := TCategoria(cCategorias[0]);

Con esto te evitas estar redimencionando el arreglo cada vez que quieras agregarle una categoria.


Saludos...


P.D.: Cuando pongas cualquier código entre las etiquetas [ code ], [ delphi ], etc, trata de cortarlas "manualmente" usando saltos de línea para que sea más legible... ;)

Holderhek 03-02-2005 23:05:19

Hola

Efectivamente el problema estava en el constructor de la clase TCategoria. Ocupaba un arreglo no inicializado

Gracias por resolverme el problema.

Y gracias por el consejo de las Listas, lo implementare con ellas.

Saludos.


La franja horaria es GMT +2. Ahora son las 02:44:03.

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