![]() |
Zugriffsverletzung
Liste der Anhänge anzeigen (Anzahl: 1)
Hallo,
wenn ihr die exe im Anhang startet und dann auf das Symbol für Neue Datei klickt, dann erscheint ein neuer Tab. Nun klickt man auf den letzten Knopf mit dem X und dieser verschwindet. Anschließend klickt man wieder auf den letzen Knopf und es tritt eine Zugriffsverletzung auf. Die Procedure DeleteSubject in der maf.pas wird beim Klicken aufgerufen. Kann jemand den Fehler finden??? :f |
Re: Zugriffsverletzung
Zitat:
Wenn eine Zugriffsverletzung auftritt, nachdem etwas verschwindet, ist es nicht weiter schwer einen möglichen Fehler zu finden. Mit hoher Wahrscheinlichkeit findet wohl ein Zugriff auf ein gelöschtes Objekt statt. Also musst du nur dafür sorgen, dass du nicht auf etwas freigebenes zugreifst. Hab jetzt nicht in deinen Code geschaut, aber prüfen ob eine Variable noch zugewiesen ist macht man mit assigned(Variable) und beim Freigeben kannst du mit FreeAndNil(Variable) sicherstellen, dass der gespeicherte Zeiger nach dem Freigeben der Nullpointer ist. Gruß Der Unwissende |
Re: Zugriffsverletzung
Ich habe mal den Debugger benutzt. Mit F7 gehe ich Zeile für Zeile durch. Der Debugger springt in die markierte Zeile und danach wird der Fehler ausgelöst.
Delphi-Quellcode:
procedure TMarkFile.DeleteSubject(Sender : TObject);
var row,i,i2:integer; begin row:=(Sender as TButton).Tag; if row=High(FEingabeArray) then begin for i2 := 1 to 5 do begin FreeAndNil(FEingabeArray[row].array_edit[i2]); end; FreeAndNil(FEingabeArray[row].button_loeschen); FreeAndNil(FEingabeArray[row].Combobox_fach); end else begin for i := row to High(FEingabeArray)-1 do begin for i2 := 1 to 5 do begin FEingabeArray[i].array_edit[i2].text:=FEingabeArray[i+1].array_edit[i2].Text; end; FEingabeArray[i].button_loeschen.Tag:=FEingabeArray[i+1].button_loeschen.Tag; FEingabeArray[i].Combobox_fach.Text:=FEingabeArray[i+1].Combobox_fach.Text; end; FreeAndNil(FEingabeArray[High(FEingabeArray)].button_loeschen); FreeAndNil(FEingabeArray[High(FEingabeArray)].Combobox_fach); for i2 := 1 to 5 do begin FreeAndNil(FEingabeArray[High(FEingabeArray)].array_edit[i2]); end; end; SetLength(FEingabeArray,Length(FEingabeArray)-1); UpdateSubjects; end;//hier nach end; wird der Fehler ausgelöst. Danach kommt nichts mehr. |
Re: Zugriffsverletzung
Hallo,
kann es sein, dass Du den button löschst, der gerade gedrückt wurde? In diesem Fall passiert nämlich Folgendes: - Button.DoClick wird ausgelöst - Eigenes Ereignis OnClick wird ausgeführt - Button wird zerstört - Rücksprung zu Button.DoClick, aber Button ist nicht mehr vorhanden -> AV Gruß xaromz |
Re: Zugriffsverletzung
Ja so wird es sein :autsch: Und was kann man dagegen tun?
|
Re: Zugriffsverletzung
Hallo,
Zitat:
Da PostMessage die Message in die Warteschlage steckt, kommt diese nach dem Buttonclick an. In der Behandlungsroutine kannst Du dann den Button zerstören. ![]() Gruß xaromz |
Re: Zugriffsverletzung
Hab ich gemacht, aber der Button verschwindet nicht :roll:
|
Re: Zugriffsverletzung
Delphi-Quellcode:
Das wird gar nicht aufgerufen.
procedure TMarkFile.LoeschMich(var Msg: TMessage);
begin TObject(Msg.WParam).Free; // WParam nach TObject casten und freigeben showmessage('blubb'); end; |
Re: Zugriffsverletzung
dann sendest du wohl die message nicht
|
Re: Zugriffsverletzung
Ich hab das nicht abgespeichert, darum kann ich den modifizierten Source nicht mehr herzeigen. Meine Bitte: Kann das mal bitte jemand anpassen? :oops:
|
Re: Zugriffsverletzung
Das komische ist ja, dass die alte Version funktioniert:
Delphi-Quellcode:
Und die neue:
procedure TForm1.DeleteSubject(Sender : TObject);
var row,i,i2:integer; begin row:=(Sender as TButton).Tag; if row=High(EditsArray) then begin for i2 := 1 to 6 do begin EditsArray[row][i2].Free; end; BtnLoeschenArray[row].Free; end else begin for i := row to High(EditsArray)-1 do begin for i2 := 1 to 6 do begin EditsArray[i][i2].text:=EditsArray[i+1][i2].text; end; BtnLoeschenArray[i].Tag:=BtnLoeschenArray[i+1].Tag; end; for i2 := 1 to 6 do begin EditsArray[High(EditsArray)][i2].Free; end; BtnLoeschenArray[High(EditsArray)].Free; end; SetLength(EditsArray,Length(EditsArray)-1); SetLength(BtnLoeschenArray,Length(BtnLoeschenArray)-1); UpdateSubjects; end;
Delphi-Quellcode:
funktioniert nicht, obwohl ich vom Prinzip her nichts geändert habe. Ich habe nur die verschiedenen Komponenten in ein array of record gepackt.procedure TMarkFile.DeleteSubject(Sender : TObject); var row,i,i2:integer; begin row:=(Sender as TButton).Tag; if row=High(FEingabeArray) then begin for i2 := 1 to 5 do begin FreeAndNil(FEingabeArray[row].array_edit[i2]); end; FreeAndNil(FEingabeArray[row].button_loeschen); FreeAndNil(FEingabeArray[row].Combobox_fach); end else begin for i := row to High(FEingabeArray)-1 do begin for i2 := 1 to 5 do begin FEingabeArray[i].array_edit[i2].text:=FEingabeArray[i+1].array_edit[i2].Text; end; FEingabeArray[i].button_loeschen.Tag:=FEingabeArray[i+1].button_loeschen.Tag; FEingabeArray[i].Combobox_fach.Text:=FEingabeArray[i+1].Combobox_fach.Text; end; FreeAndNil(FEingabeArray[High(FEingabeArray)].Combobox_fach); FreeAndNil(FEingabeArray[High(FEingabeArray)].button_loeschen); for i2 := 1 to 5 do begin FreeAndNil(FEingabeArray[High(FEingabeArray)].array_edit[i2]); end; end; SetLength(FEingabeArray,Length(FEingabeArray)-1); UpdateSubjects; end; |
Re: Zugriffsverletzung
Liste der Anhänge anzeigen (Anzahl: 1)
Hallo Koller,
ich habe mir dein Projekt herunter geladen und den Code angepasst, damit das Löschen funktioniert. Ich finde du solltest bestimmte Teilaspekte deines Projektes zuerst isoliert ausprobieren und testen. Dein Code zeigt deutlich, dass du auf dem besten Weg bist die Übersicht zu verlieren. Wenn du schon soetwas wie ein Multi-Document-Interface realisieren möchtest, dann musst du auch dafür sorgen dass es in deiner Form1 eine Eigenschaft ActiveFile gibt, über die man die richtige Komponente TMarkFile selektieren kann. Viel Spaß noch mit deinem Projekt. marabu |
Re: Zugriffsverletzung
Erst mal vielen Dank!
Hast du nur diese Prozedur geändert?
Delphi-Quellcode:
procedure TMarkFile.DeleteSubject(rowIndex: Integer);
var iRow, iEdit: Integer; begin for iRow := rowIndex to Pred(High(FEingabeArray)) do begin for iEdit := 1 to 5 do FEingabeArray[iRow].array_edit[iEdit].text := FEingabeArray[Succ(iRow)].array_edit[iEdit].Text; FEingabeArray[iRow].button_loeschen.Tag := FEingabeArray[Succ(iRow)].button_loeschen.Tag; FEingabeArray[iRow].Combobox_fach.Text := FEingabeArray[Succ(iRow)].Combobox_fach.Text; end; with FEingabeArray[High(FEingabeArray)] do begin for iEdit := 1 to 5 do array_edit[iEdit].Free; Combobox_fach.Free; button_loeschen.Free; end; SetLength(FEingabeArray, High(FEingabeArray)); UpdateSubjects; end; Zitat:
|
Re: Zugriffsverletzung
Es sind schon noch ein paar Änderungen mehr. Besorge dir
![]() Zitat:
Freundliche Grüße marabu |
Re: Zugriffsverletzung
Zitat:
|
Re: Zugriffsverletzung
Eine property hast du schnell deklariert:
Delphi-Quellcode:
Das Feld ActiveFileIndex musst du ständig in Übereinstimmung mit den Aktionen des Benutzers aktualisieren. Zuvor solltest du dir ein paar Gedanken zur Benutzerschnittstelle und zu deiner Programmstruktur machen. Ich vermisse ein Konzept. So läufst du Gefahr eine Menge überflüssigen Code zu schreiben, der später mühevoll raus operiert werden muss.
type
TForm1 = class(TForm) private ActiveFileIndex: Integer; function GetActiveFile: TMarkFile; public property ActiveFile: TMarkFile read GetActiveFile; end; function TForm1.GetActiveFile: TMarkFile; begin Result := Files[ActiveFileIndex]; end; marabu |
Re: Zugriffsverletzung
Zitat:
Zitat:
Kannst du mir nen Ansatz geben, weil ich von alleine weiterkommen möchte |
Re: Zugriffsverletzung
Als erstes rate ich dir auf verschachtelte PageControls zu verzichten. Auf der zweiten Ebene deines Programms ist das auch garnicht hilfreich. Durch deinen Button "Daten auswerten" ist ein Sekundärfenster die bessere Lösung. Nimm die Seite Datenauswertung ganz weg und mache die Seite Dateneingabe direkt zu einer Seite der ersten Ebene.
Auf der ersten Ebene hast du einen Reiter "HomePage". Wenn alle folgenden Seiten gleichartig sind, dann solltest du auf eine andersartige erste Seite unbedingt verzichten. Die von dir dann überarbeitete Komponente TMarkFile sollte dann nicht der Verwalter des zugehörigen TabSheets sein, sondern das TabSheet sollte über seine Tag property auf das zugehörige TMarkFile verweisen. Vielleicht ist es dir nicht bekannt, aber ScreenEx birgt in diesen Zeiten die Gefahr einer Abmahnung. Informiere dich mal. marabu |
Re: Zugriffsverletzung
Zitat:
Zitat:
![]() |
Re: Zugriffsverletzung
*push*
|
Re: Zugriffsverletzung
Entschuldige, aber welche Antwort erwartest du von mir? Ich bin kein Jurist.
Freundliche Grüße vom marabu |
Re: Zugriffsverletzung
Zitat:
Zitat:
|
Re: Zugriffsverletzung
Verstehe. Das war nur ein gut gemeinter Hinweis von mir - mehr nicht. S... ist ein Produkt und andernorts eine Firma. Ich würde mir einen unverfänglicheren Namen suchen.
Freundliche Grüße marabu |
Re: Zugriffsverletzung
Zitat:
|
Re: Zugriffsverletzung
Zitat:
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 13:48 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz