Handhabung sehr großer Datenmengen
-
Warum new? Nimm doch einen Container der mit zerstückeltem Speicher zurecht kommt, wenn dies die Problemstelle ist.
-
Ach halt vergiss es, passt doch, du hast ja BYTES geschrieben und ich hab Bits gelesen

Mir würden für A und B aber auch 16 BIT ausreichen, nur für C und D brüchte ich später wohl float. Auch gut, dann halbiert sich eventuell auch die Speichergröße.
EDIT:
P.S. Schau dir mal die Klasse vector der Standardbibiothek an. Mit einem vector kannst du dann neuen Speicher anfordern, wenn er auch wirklich gebraucht wird.
Ich sehe gerade, du verwendest Windows (32 Bit ?). Ein int ist auf diesem System immer 4 Byte groß.
Außerdem, wenn du bis zu 600 MB einlesen mußt, heißt das ja nicht automatisch, dass du den selben Speicher zur Aufbereitung der Daten haben mußt. Du kannst diese Datenmenge in kleine Stückchen aufteilen, aufbereiten unn in kleinen Häppchen weiterschicken.hab ich mal reingeschaut, kann ich aber nicht wirklich viel mit anfangen. Ich initialisier die Arrays ja gleich beim Start des Programms.
Nein nutze win7 64 bit, hab aber erstmal mit ner 32 bit Anwendung angefangen, da ich für 64 keine Notwendigkeit sah.
Ich brauch mindestens nochmal so viel Speicher für die Berechnungen an sich, da ich die Differenz für jedes Pixel zweier aufeinander folgender Bilder ziehen muss, und dann für jedes Differenzbild die Summe als auch den Durchschnitt über das Bild, feststellen muss welche Pixel über nem gewissen Grenzwert liegen um dann aus ner gewissen Umgebung der hellsten Punkte jeweils noch mehrere Parameter für den Bildpunkt auszurechnen.
Im Optimalfall sollten alle Daten die bei den Berechnungen entstehen vorgehalten werden. Die Orginaldaten müssen aber auf jedenfall im RAM bleiben, da wiederholt auf sie zugegriffen werden muss, und eventuell auch nen Abgleich erfolgen muss zum Ram der GPU.
Was die Sache mit irgendwelchen Containern etc nageht, so bin ich da etwas skeptisch, da ich jederzeit wissen muss, wie ich jeden einzelnen Pixel ansprechen kann. Ich hab auf der GPU halt nur 1D arrays. Und dort kann ich halt nicht auf ne wirre Verteilung der Daten zugreifen. Da muss auf jedenfall mindestens 6 Bilder gleichzeitig in den Ram geladen werden pro Kernel, da sonst der overhead sich ziemlich aufsummiert.
-
Skysnake schrieb:
Hier der Code-Ausschnitt der relevant ist:
#include <iostream> #include <vector> #include <utility> #define alloca _alloca #define __NO_STD_VECTOR //Use cl::vektor instead of STL version #include <functional> //#include <cstdlib> für rand() eventuell nötig #include <CL\cl.hpp> #include <stdio.h> using namespace std; . . . const unsigned int xblockSize=64; const unsigned int xblocks =5; const unsigned int yblockSize=64; const unsigned int yblocks =5; const unsigned int xdimension=xblockSize*xblocks; const unsigned int ydimension=yblockSize*yblocks; const unsigned int dimension=ydimension*xdimension; const unsigned int anzahlBilder=1000; . . // nein lieber nicht so machen int * A=new int [ydimension*xdimension*anzahlBilder]; int * B=new int [ydimension*xdimension*anzahlBilder]; int * C=new int [ydimension*xdimension*anzahlBilder]; int * D=new int [ydimension*xdimension*anzahlBilder]; // std::vector<int> A(ydimension*xdimension*anzahlBilder); std::vector<int> B(ydimension*xdimension*anzahlBilder); std::vector<int> C(ydimension*xdimension*anzahlBilder); std::vector<int> D(ydimension*xdimension*anzahlBilder); . . .Fürs erste langen 500MB an Daten aus, also das was oben initialisiert werden soll. Wenn ihr ne Lösung für Arrays mit Daten >1GB habt, bin ich auch sehr aufgeschlossen. Wichtig ist halt nur, das wirklich alles im RAM hab und die Datenpackete nicht kleiner als 100k Einträge haben sollen.
Du solltest statt der einfachen C Felder lieber std::vector nehmen, da so auch sauber der Speicher verwaltet wird. Es gibt keine Nachteile und man kann einen std::vector immer als Ersatz für ein C Feld verwenden.
Zur Problematik der Feldgröße: als 64Bit Applikationen übersetzen und passenden Rechner nutzen.
-
Du mußt mal schreiben, ob du ein 32 Bit oder 64 Bit system nutzt. Auf 64 Bit Systemen wäre es, wie ~John gerade bemerkte, kein Problem mit passendem Rechner, da dir insgesamt auf aktueller Hardware/aktuellem OS 8192 GB virtueller Speicher zur Verfügung stehen. Auf 32 Bit Systemen kannst du im PE-Header ein Flag setzen, so dass dir zumindest 3 GB virtueller Speicher gewährt wird. Das OS nimmt dann nur noch 1GB für sich in Anspruch.
-
is 64 bit, mit 4GB realem Ram. Ich schreibs hier nochmal rein, der edit geht sicher utner.
ich schau mir das mit dem <vector> nochmal an.
EDIT: habs mir nochmal unter http://www.cplusplus.com/reference/stl/vector/ angeschaut. Jetzt ist mir auch wieder klar, warum ichs nicht vorher eingesetzt hab. Ich steig da nicht so 100% durch

-
Ernst gemeinter Ratschlag: Geh morgen mal in die Uni-Bibiothek und leih' dir ein richtig gutes Buch über C++ aus.
Das kann bspw. "Die C++ Programmiersprache" (original "The C++ Programming Language"
) von Bjarne Stroustrup sein. Dieses Buch kann ich wirklich empfehlen.
Alternativ soll auch der C++ Primer sehr gut sein (nicht gelesen).
In die STL solltest du dich wirklich einarbeiten, sie hilft dir bei sehr vielen Dingen ungemein!
-
Nur so interessehalber ... wie groß ist denn dein GPU Speicher?
-
machts aber nicht unbedingt einfacher wie ich bisher die Erfahrung gemacht hab.
mit <vector> kann ich jetzt z.B. toll den Speicher initialisieren und füllen, aber meine Übergabe an die OpenCL Funktion geht nicht mehr, und wird wie ich befürchte auch nicht so einfach werden, da ich nicht den entsprechenden Pointer so einfach übergeben kann
Ist folgender Funktionsaufruf:
cl_mem clCreateBuffer ( cl_context context, cl_mem_flags flags, size_t size, void *host_ptr, cl_int *errcode_ret)Ich schau mal ob ich den entsprechenden Pointer find.
Was das Buch angeht, so hab ich hier son Welzer liegen, hilft mir aber für die Sachen die ich such im Allgemeinen auch nicht weiter. Mit Speziallösungen etc. kann ich nicht soo viel anfangen, denn ich nutz C++ nur als Zwischenmedium für OpenCL. Daher würd ich gern die Gleichen Funktionen sowohl im C++ Teil als auch im OpenCL kernel verwenden. Falls es aber wirklich nicht anders geht, muss ich halt alles in RAM laden und dann kleinere Anteile halt an meinen OpenCL Kernel übergeben, was ja auch ohne Probleme für (5*64)*(5*65)*5 Bilder geklappt hat.
EDIT: 1Gb ist der Ram groß von dem atm nur 512 ohne Tricks genutzt werden können. Mit tricks 800MB rum. Was mir grad aufzeigt, das ich atm zu groß bin -.- Hatte noch die 16 bit die ich erstmal nur brauch noch im Kopf

Damit wirds etwas zu groß. Willte eigentlich den Stack von 2k Bildern auf A und B aufteilen, so das es zu keinen Speicherüberschneidungen kommt, aber muss ich dann wohl jetzt nochmal schauen, ob ichs nicht vielleicht in Blöcke a 250 Bilder aufteile oder so.
-
Jetzt habe ich aber selber mal eine Frage. Warum crasht das Porgramm unter win64?
Der Memory-Manager von Windows kann doch die angeforderten ~1.6 GB bei dem System direkt in den physischen Speicher mappen (4 GB sind ja vorhanden), ohne überhaupt dran denken zu müssen, irgend etwas zurück auf Disk zu pagen ?
-
Ok, hab mal noch nen bischen rumprobiert.
(5*64)*(5*64)*250 geht, das von der größe dann auch absolut ok, dann kann ich genug Bilder laden um damit lang genug arbeiten zu können vorm nächsten Speicherzugriff und hab eventuell auch noch genug Zeit um zwischen drin mit den Daten auch was auf der CPU arbeiten zu lassen, bevor die anderen Teile fertig sind.
Und insgesamt kann ich alle Daten wenn ich will dann ja mit dem <vector> speichern.
Sauber Leute, mein Problem scheint erstmal gelöst zu sein

Zumindest so lange, Bilder von zwei Kameras gleichzeitig ankommen und das dann wohl auch noch in höherer Auflösung

EDIT: Ich schau dann aber wohl wenns zeitlich langt, das ich gleich auf ne 64 bit Anwendung umsattel, damits für die Zukunft nicht doch noch zu Engpässen kommt.
-
Hi,
Ich weiss jetzt nicht, ob das Problem noch fuer dich von Relevanz ist, aber eigentlich garantiert vector, dass die Daten im Speicher linear abgelegt werden:
[quote="C++ Referenz von dieser Seite hier"]Just as regular arrays, vector containers have their elements stored in contiguous storage locations, which means that their elements can be accessed not only using iterators but also using offsets on regular pointers to elements.[/cpp]
Also sollte &A.front() als Zeiger doch eigentlich funktionieren fuer deine Grafikbibliotheksfunktion und damit kannst Du alles in vectoren speichern, sowohl temporaer als auch auf laengere Sicht. Aber ohne Gewaehr, ob ich irgendwas uebersehe.
-
Skysnake schrieb:
machts aber nicht unbedingt einfacher wie ich bisher die Erfahrung gemacht hab.
mit <vector> kann ich jetzt z.B. toll den Speicher initialisieren und füllen, aber meine Übergabe an die OpenCL Funktion geht nicht mehr, und wird wie ich befürchte auch nicht so einfach werden, da ich nicht den entsprechenden Pointer so einfach übergeben kann
Ein std::vector erlaubt es, daß man die Adresse des ersten Elements übergibt.
std::vector<int> A(5000); int* p = &A[0]
-
@Eisflamme:
Ja, da hast du vollkommen recht. Diese Klausel im Standard sorgt dafür, dass vector und dynamisches Array vollkommen äquivalent ist und die Adresse des ersten Vectorelementes so benutzt werden kann wie die Adresse eines dynamischen Arrays. Außer bei dem berüchtigten vector<bool> bei dem sich das Standardkomitee bis heute ärgert diesen überhaupt eingeführt zu haben.(Rein theoretisch erlaubt es der Standard auch, dass die Vectorelemente rückwärts im Speicher angeordnet sind. Dies macht aber keine einzige Implementierung so und wird sicherlich auch niemals eine machen. Darauf sollte man keine Rücksicht nehmen. Im neuen Standard wird (soweit ich weiß) auch dies ausgeschlossen)
-
~john schrieb:
Ein std::vector erlaubt es, daß man die Adresse des ersten Elements übergibt.
std::vector<int> A(5000); int* p = &A[0]Hey vielen Dank, das sieht ziemlich genau nach der Lösung für mein Problem mit der Übergabe an die OpenCL-Funktion aus
