AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

Dynamisches Array von DLL übergeben

Ein Thema von TheMiller · begonnen am 4. Dez 2006 · letzter Beitrag vom 8. Dez 2006
Antwort Antwort
Seite 2 von 4     12 34      
Eichhoernchen

Registriert seit: 22. Apr 2004
Ort: Hagen
322 Beiträge
 
Turbo Delphi für Win32
 
#11

Re: Dynamisches Array von DLL übergeben

  Alt 5. Dez 2006, 21:48
Zitat von DJ-SPM:
hm...

oder ich muss den schritt halt aufteilen: Die Funktion gibt mir lange Strings zurück, die ich in der Hauptanwendung in diese dann dort in Array packe. Finde ich zwar nicht so schön, aber so solls halt erstmal sein.

Danke euch.

Aber wenn's noch Vorschläge gibt, nehm ich sie gerne an!

Würde das nicht irgendwie dem Sinn der DLL widersprechen?

Ich meine du zerteilst erst etwas mit deiner Explode Funktion und dann bastelst du wieder einen String, den man um ihn in ein Array zu packen wieder mit einer Explode-artigen Funktion bearbeiten muss um das Ergebnis in ein Array zu speichern. Hört sich für mich Sinnlos an.

Kannst du nicht vielleicht einen Pointer übergeben, der auf eine Speicheradresse mit dem Array zeigt? Aber das würde wahrscheinlich nur bei konstanter Größe gehen richtig?
Jan
  Mit Zitat antworten Zitat
Benutzerbild von TheMiller
TheMiller

Registriert seit: 19. Mai 2003
Ort: Gründau
2.480 Beiträge
 
Delphi XE7 Architect
 
#12

Re: Dynamisches Array von DLL übergeben

  Alt 5. Dez 2006, 21:56
Pointer sind schon der richtige Weg - denke ich.

Mein Problem ist folgendes. Ich möchte einen Datensatz aus einer DB per PHP laden. Da habe ich dann verschiedene Felder (klar -> ist ja eine DB) diese Felder bzw. deren Werte sind durch einen Separator getrennt. Das Ende des Datensatzes hat einen anderen Separator. Jetzt möchte ich alle Datensätze in ein Record speichern.

Dazu muss ich doch erst die Werte zurückgeben lassen (die "Sep1" getrennt) und das Ende eines Datensatzes finden ("Sep2"). Jetzt muss ich erst nach Sep2 exploden und diese in ein Array speichern, sodass ich auf die einzelnen Datensätze zugreifen kann. Dann kann ich mich an die Werte machen ("Sep1") und kann diese Daten dann schön in mein Array speichern.

Soweit mein Vorhaben *g*
  Mit Zitat antworten Zitat
gmc616

Registriert seit: 25. Jun 2004
Ort: Jena
627 Beiträge
 
Delphi 10.3 Rio
 
#13

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 00:55
Mit Pointer funktioniert das so nicht!

Das Arbeiten mit dynamischen Arrays zwischen DLL und Applikation ist, wie ich schmerzlich lernen mußte, nicht ohne weiteres möglich. Besonders dann nicht, wenn du ohne Speichermanager arbeiten willst.

Ich habe mir für diesen Fall eine "Krücke" gebastelt, in dem ich das Array in der DLL verwalten lasse und mir Export-Funktionen gebaut habe, die mir u.a. die Länge des DLL-Arrays zurück geben. Die einzelnen Array-Elemente lasse ich mir mit einer weiteren Export-Funktion(Index)Char zurück geben. Hierbei muss ich nur dafür sorgen, das ausreichend Speicher reserviert wird, sonst bekommt man nur ein Teil des String wieder zurück.

Quasi überträgt man nicht das Array komplett, sondern nur die einzelnen Elemente des Arrays.

Wenn du auf Applikationsseite die einzelen Elemente wieder in ein Array speicherst, dagegen spricht nix. Es ist halt nur nicht möglich das Array komplett per Parameter wieder zurück zubekommen. Zumindest nicht ohne Speichermanager.

Sorry, mit Beispielcode kann ich dir augenblicklich nicht dienen.
  Mit Zitat antworten Zitat
Muetze1
(Gast)

n/a Beiträge
 
#14

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 07:21
Frage an gmc616: Warum gibt die DLL nicht einfach zurück, wieviele Einträge es in dem Array gibt und eine weitere Funktion gibt die Adresse des ersten Eintrags an. Dies würde der Applikation doch schon reichen, schliesslich sind alle Arrays im Speicher fortlaufend und somit kann sie sich mit einem grossen CopyMemory() oder Move() Befehl den kompletten Array Inhalt kopieren ohne über jedes einzelne Element zu laufen.
  Mit Zitat antworten Zitat
6. Dez 2006, 11:13
Dieses Thema wurde von "Daniel" von "Programmieren allgemein" nach "Sonstige Fragen zu Delphi" verschoben.
gmc616

Registriert seit: 25. Jun 2004
Ort: Jena
627 Beiträge
 
Delphi 10.3 Rio
 
#16

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 12:07
Hallo Muetze1,

Das habe ich schon probiert.

Ich lade meine DLL dynamisch. Das Kopieren per CopyMemory funktioniert auch ohne Probleme.
Wenn Ich allerdings die DLL mit FreeLibrary wieder entlade, bekomme ich eine Schutzverletzung bei Schreiben(!) an Adresse xy.

Vlt. liegt es daran, dass ich mit Array of Records arbeite. Vlt. muß ich auch irdendwo wieder Speicher freigeben, wüsste aber nicht welchen.
Oder es liegt daran, das es ohne Speichermanager einfach nicht funktioniert.

Ich weiß es nicht. Daher die Krücke.

Es wäre allerdings ne feine Sache, wenn das so einfach mit CopyMemory funktioniert täte / tun würde.

gmc
  Mit Zitat antworten Zitat
Benutzerbild von Wormid
Wormid

Registriert seit: 26. Aug 2003
Ort: Steinfurt
292 Beiträge
 
Delphi XE2 Professional
 
#17

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 13:02
Bekomme ich hier was nicht mit?

Man kann doch dynamische Arrays aus einer DLL zurückgeben...

Delphi-Quellcode:
library xyz;

uses
  ...

type
  TTestArray = array of ShortString;

function GetTestArray: TTestArray; stdcall;
begin
  SetLength(Result, 3);
  Result[0] := 'Hallo';
  Result[1] := 'Welt';
  Result[2] := '!';
end;

exports
  GetTestArray;

end.
Delphi-Quellcode:
program test_xyz;

interface

type
  TTestArray = array of ShortString;

...
  var GetTestArray: function: TTestArray; stdcall;

implementation

procedure TestItOut;
var
  a: TTestArray;
  i: Integer;
  hDLL: THandle;
begin
  hDLL := LoadLibrary('xyz.dll');
  if hDLL <> 0 then
  begin
    GetTestArray := GetProcAddress(hDLL, 'GetTestArray');
    if GetTestArray <> nil then
    begin
      a := GetTestArray;
      ShowMessage(IntToStr(Length(a))); // Eine schicke "3" erscheint als Meldung
      for i := Low(a) to High(a) do
        ShowMessage(a[i]); // Hallo *click* Welt *click* ! *click*
      SetLength(a, 0);
      GetTestArray := nil;
    end;
    FreeLibrary(hDLL);
  end;
end;
*Edit: "Testprogramm" um dynamisches Einbinden der Funktion erweitert
Debuggers don't remove Bugs, they only show them in Slow-Motion.
  Mit Zitat antworten Zitat
Muetze1
(Gast)

n/a Beiträge
 
#18

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 14:25
Zitat von Wormid:
Bekomme ich hier was nicht mit?

Man kann doch dynamische Arrays aus einer DLL zurückgeben...
Nur wenn du ShareMem oder FastMM in beiden Projekten einbindest. (beides als erste Unit in beiden Projekten). Und genau diesen Fakt will er ja vermeiden.

Zitat von gmc616:
Wenn Ich allerdings die DLL mit FreeLibrary wieder entlade, bekomme ich eine Schutzverletzung bei Schreiben(!) an Adresse xy.

Vlt. liegt es daran, dass ich mit Array of Records arbeite. Vlt. muß ich auch irdendwo wieder Speicher freigeben, wüsste aber nicht welchen.
Da das Array kopiert wird, sollte es keine Probleme geben. Es kann aber Probleme geben, wenn die Funktion der DLL so deklariert ist, das gesamte Array zurück zu geben anstatt einen Zeiger auf den Record (welcher dann mit der Adresse des ersten Records befüllt wird beim Aufruf).

Ansonsten Speicher des Array freigeben? Naja, SetLength(Array, 0); - aber eigentlich nicht unbedingt von nöten.

Ich werde die Tage selber mal ein Beispielprojekt dazu aufbauen und das ganze nochmal im Detail versuchen nach zu vollziehen.
  Mit Zitat antworten Zitat
Benutzerbild von TheMiller
TheMiller

Registriert seit: 19. Mai 2003
Ort: Gründau
2.480 Beiträge
 
Delphi XE7 Architect
 
#19

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 15:10
Hm...

hab mir dazu nochmal gedanken gemacht und getestet (hab mit Pointern noch nie was gemacht - lerne aber gerne dazu) und einiges rumprobiert.

hab zum Testen die Funktion myArray, die mir den zeiger zurückgeben soll. Eine weitere Funktion empfängt einen Zeiger und weist dementsprechend den Wert aus. Mein Programm fragt also nach einem Zeiger, empfängt ihn, sendet ihn an Funktion 2 und empfängt den String. Vom Prinzip her garnicht mal so übel (hoffe ich).

Doch ich denke, mein erster Fehler liegt schon in der ersten Funktion, da ich nicht weiß, welchen Rückgabewert ich benutzen muss. Ich denke, da Integer und Pointer so ziemlich gleich sind, kann ich den Pointer in einen Integer packen, gibt aber bei der Rückgabe im Programm nur Schrott aus. Weis nicht, wie ich auf einen Pointer zugreifen kann, um dessen Wert zu bekommen.:

Delphi-Quellcode:
function myArray: integer;
var
  testarr: array of byte;
  zeiger: ^integer;
begin
  SetLength(testarr, 2);
  randomize;
  testarr[0]:=random(9999);
  testarr[1]:=32;
  zeiger:=@testarr[0];
  result:=Integer(zeiger);
end;
Danke nochmal!
  Mit Zitat antworten Zitat
Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
43.181 Beiträge
 
Delphi 12 Athens
 
#20

Re: Dynamisches Array von DLL übergeben

  Alt 6. Dez 2006, 15:20
Da die Array-Variable selber ein Pointer ist, kannst du auch direkt casten:
('s kommt aber darauf an, wie du es drüben verwenden willst)
Delphi-Quellcode:
function myArray: integer;
var
  testarr: array of byte;
begin
  SetLength(testarr, 2);
  randomize;
  testarr[0]:=random(9999);
  testarr[1]:=32;
  result:=Integer(testarr);
end;
oder etwas schöner ... du gibst ja einen Zeiger zurück
Delphi-Quellcode:
function myArray: pointer;
var
  testarr: array of byte;
begin
  SetLength(testarr, 2);
  randomize;
  testarr[0]:=random(9999);
  testarr[1]:=32;
  result:=pointer(testarr);
end;
und zurück dann z.B. so:
type Ttestarr = array of byte;

Ttestarr(myArray)

PS: randomize; nicht ständig aufrufen!

PSS:
SetLength(Arr, 0);
dat is schneller, da es direkt ClearArray aufruft ._.
Arr := nil;
Garbage Collector ... Delphianer erzeugen keinen Müll, also brauchen sie auch keinen Müllsucher.
my Delphi wish list : BugReports/FeatureRequests
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 2 von 4     12 34      


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 23:51 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz