Leinwand ist cool! - Seite 90

 
Nikolai Semko #:

Ein Canvas ist ein Objekt, an das ein Array von Pixeln gebunden ist. Die Ressource ist für die Bindung dieses Arrays von Pixeln verantwortlich (siehe bool CCanvas::Create())
Es ist eine schlechte Praxis, eine Leinwand ständig zu löschen und neu zu erstellen.
Es ist eine gute Praxis, eine Leinwand zu erstellen, wenn sie benötigt wird, und sie zu löschen, wenn sie nicht mehr benötigt wird, z. B. am Ende des Programms.

Sobald Sie ein Canvas-Objekt erstellt haben, können Sie es aufräumen, das Pixel-Array bei jedem Bild überschreiben, die Größe der Leinwand ändern und sie an einen beliebigen Ort verschieben.

Danke, es ist ein wenig klarer geworden, aber nicht alles. Verstehe ich das richtig, dass, wenn ich nach dem Erstellen eines Canvas-Objekts das Objekt einfach mit ObjectDelete() aus dem Diagramm lösche , dann bleibt das an dieses Objekt gebundene Pixel-Array unberührt und... Wenn ich wieder ein neues Canvas-Objekt mit einem anderen Namen erstelle, wird ein neues Pixel-Array im Speicher angelegt, und somit ist es theoretisch möglich, den gesamten Speicher zu füllen?

Oder wird das alte Pixel-Array einfach jedes Mal wieder an das zuletzt erstellte Canvas-Objekt gebunden (denn nur mit ihm funktionieren alle Funktionen der verwendeten Instanz der Canvas-Klasse)?

 
leon_17 #:

Danke, es wurde ein wenig klarer, aber nicht alles. Verstehe ich das richtig, dass wenn ich nach dem Erstellen eines Canvas-Objekts das Objekt einfach mit ObjectDelete() aus dem Diagramm lösche , dann bleibt das an dieses Objekt gebundene Pixel-Array unberührt und.... Wenn ich wieder ein neues Canvas-Objekt mit einem anderen Namen erstelle, wird ein neues Pixel-Array im Speicher angelegt, und somit ist es theoretisch möglich, den gesamten Speicher zu füllen?

Natürlich werden sich die besitzerlosen Ressourcen vervielfachen.

leon_17 #:

Oder aber das alte Pixelarray wird einfach jedes Mal wieder an das zuletzt erstellte kanvas-Objekt gebunden (denn nur damit funktionieren alle Funktionen der verwendeten Instanz der kanvas-Klasse)

Deine Phantasie ist großartig. Ich beneide dich. Auf so etwas wäre ich nicht gekommen. :))

Wenn Sie jedoch den Namen einer eigentümerlosen Ressource speichern, können Sie sie wieder an ein neues Bitmap-Objekt binden. Aber das ist aus dem Bereich der Schizophrenie.

 
Nikolai Semko #:

Wenn Sie jedoch den Namen einer eigentümerlosen Ressource speichern, können Sie sie erneut an ein neues Bitmap-Objekt binden. Aber das ist aus dem Bereich der Schizophrenie.

Ich nehme meine Worte zurück. Ich glaube, ich habe einen Fall gefunden, in dem so etwas nützlich sein könnte.
 
Nikolai Semko #:
Ich nehme das zurück. Ich glaube, ich habe einen Fall gefunden, in dem dies nützlich sein könnte.

Danke, ich wollte nur verstehen, was im Speicher passiert, wenn man ObjectDelete () anstelle von Destroy () verwendet. Und ich habe festgestellt, dass in einem solchen Fall die Grafikressourcen (eigentümerlose Pixelarrays und was auch immer) vervielfacht werden, wenn jedes Mal ein neuer Name für ein neues Canvas-Objekt generiert wird.

Und wenn ichObjectDelete() verwende , aber dann ein Canvas-Objekt mit demselben Namen erstelle, wird das Pixel-Array dann alt oder noch neu sein?

p.s. die Fragen sind wahrscheinlich dumm, aber ich brauche sie, um den Mechanismus von Canvas


zu verstehen .

 
leon_17 #:

Danke, ich wollte nur verstehen, was im Speicher passiert, wenn man ObjectDelete () anstelle von Destroy () verwendet. Und ich habe festgestellt, dass sich die grafischen Ressourcen (eigentümerlose Pixel-Arrays und anderes) vervielfachen, wenn jedes Mal ein neuer Name für ein neues Canvas-Objekt erzeugt wird.

Es ist einfach, dies zu überprüfen, indem man ein einfaches Skript schreibt
 
Nikolai Semko #:
Das lässt sich mit einem einfachen Skript leicht überprüfen.

Können Sie mir sagen, wie?

 
leon_17 #:

Können Sie mir sagen, wie?

etwa so:

#define protected public
#include <Canvas\Canvas.mqh>
#undef protected

void OnStart() {
   while(!IsStopped()) {
      int Width =(ushort)ChartGetInteger(0,CHART_WIDTH_IN_PIXELS);  // получаем Ширину окна
      int Height=(ushort)ChartGetInteger(0,CHART_HEIGHT_IN_PIXELS); // получаем Высоту окна
      CCanvas canvas;
      if(!canvas.CreateBitmapLabel("MyCanva"+string(rand()),0,0,Width,Height,COLOR_FORMAT_ARGB_NORMALIZE)) {
         Print("Error creating canvas: ",GetLastError());
      }
      canvas.FillRectangle(rand()%Width/2,rand()%Height/2,Width/2+rand()%Width/2,Height/2+rand()%Height/2,ARGB(128,rand()%255,rand()%255,rand()%255));
      canvas.Update();
      Comment("Задействовано памяти: - " + string(TerminalInfoInteger(TERMINAL_MEMORY_USED))+ " Mb");
      Sleep(500);
      ObjectDelete(canvas.m_chart_id,canvas.m_objname);
   }
}

und sehen Sie sich den Kommentar an:

!!! nach der Ausführung dieses Skripts, vergessen Sie nicht, das Terminal neu zu laden, um Speicher für verwaiste Ressourcen freizugeben.


 
Nikolai Semko #:

wie diese:

und sehen Sie sich den Kommentar an:

!!! nach der Ausführung dieses Skripts, vergessen Sie nicht, das Terminal neu zu laden, um Speicher für verwaiste Ressourcen freizugeben.


Herzlichen Dank für Ihre Hilfe! Ich habe bisher noch nicht auf diese Weise mit Speicher gearbeitet, ich werde es testen.
Danke für den Hinweis, dass verwaiste Ressourcen beim Neuladen des Terminals gelöscht werden! Viele solcher Dinge sind mir noch nicht klar.

p.s. Alles in diesem Beispiel ist perfekt! Es gibt etwas zum Anschauen, etwas zum Nachdenken und eine Gelegenheit zum Experimentieren... Der Code ist kurz.

 
Können Sie mir sagen, ob es bei der Verwendung von Kanvas in einem Expert Advisor notwendig ist, Destroy() auszuführen , wenn der Expert Advisor aus dem Chart entfernt und das Terminal geschlossen wird? Ich weiß auch nicht, wie ich das überprüfen kann. Ich meine ein Working Canvas mit einem festen Objekt. Dort liegt der Unterschied im Speicher innerhalb des Fehlers (wenn man Destroy() ausführt und nicht ausführt.
 
leon_17 der Expert Advisor aus dem Chart entfernt und das Terminal geschlossen wird? Ich weiß auch nicht, wie ich das überprüfen kann. Ich meine ein Working Canvas mit einem festen Objekt. Dort liegt der Unterschied im Speicher innerhalb des Fehlers (wenn Sie Destroy() ausführen und nicht ausführen.

Das brauchen Sie nicht. Im Canvas-Destruktor wird es automatisch ausgeführt:

                    ~iCanvas() { Destroy(); ChartRedraw();};
Grund der Beschwerde: