Frage

Ich fange Programmierung in MATLAB und ich habe einige Probleme eine Puffermatrix zu schaffen. Ich versuche, die folgende zu tun:

Ich bin ständig ein Bild von einer Webcam zu erhalten und nach der Segmentierung ich den Schwerpunkt eines sich bewegenden Ziels erhalten. Ich brauche die Schwerpunktdaten zur Verarbeitung zu speichern, aber ich will nicht zu viel Speicherplatz belegen. Zum Beispiel, wenn ich eine Zeit t=inf war, dachte ich an 10 Zeitpunkt von Daten in einer Matrix zu speichern, wie ein Ringpuffer, dann das Schreiben und die älteren Daten gelöscht werden, weil ich mit beiden muß arbeiten, die eigentlichen Daten in der Zeit ( t) und ein vorheriges Datum in der Zeit (t-1).

War es hilfreich?

Lösung

buffSize = 10;
circBuff = nan(1,buffSize);
for newest = 1:1000;
    circBuff = [newest circBuff(1:end-1)]
end

Ich habe dies getestet, dauert es keine nennenswerte Zeit in MATLAB zu laufen. Der Profiler brachte keine Engpässe mit dem Code finden.

Andere Tipps

UPDATE:

Da ich jetzt verstehen, dass Sie brauchen ein Kreis Pufferdaten zu speichern, hier ist eine Lösung, die Sie verwenden können. Da Sie sagen Sie Zentroid Daten von Objekten in einem Bild zu speichern wurden, werde ich Ihnen einen allgemeinen Fall geben, für eine beliebige Anzahl von Messungen, Speichern (entweder 1-Pixel-Indexwert für jeden Flächenschwerpunkt oder 2 Werte für x und y-Koordinaten, etc.) ...

Zuerst initialisieren den Puffer:

nBuffer = 10;  % You can set this to whatever number of time points
               %   you want to store data for
nSamples = 2;  % You can set this to the number of data values you
               %   need for each point in time
centroidBuffer = zeros(nSamples,nBuffer);  % Initialize the buffer to zeroes

Als nächstes werden Sie Ihre kontinuierliche Schleife haben. Sie können eine while-Schleife und ein Flag-Variable das hat zunächst den Wert TRUE (und die Sie kann so eingestellt href="http://www.mathworks.com/access/helpdesk/help/techdoc/ref/false.html" rel="nofollow noreferrer"> FALSE

keepLooping = true;
while keepLooping,
  % Capture your image
  % Compute the centroid data and place it in the vector "centroidData"
  centroidBuffer = [centroidBuffer(:,2:end) centroidData(:)];
  % Do whatever processing you want to do on centroidBuffer
  % Choose to set keepLooping to false, if you want
end

Dies funktioniert auf folgende Weise: zu jedem Zeitpunkt, die erste Spalte (dh der ältesten Daten) in centroidBuffer entfernt und eine neue Spalte (dh die neuen Daten) an das Ende angefügt wird . Auf diese Weise ist die Puffermatrix immer die gleiche Größe.

Wenn Sie nicht Ihre Verarbeitung bei jedem Zeitschritt wollen, durchführen, sondern nur nach jedem nBuffer Zeitpunkt, so dass sie an einem neuen Satz von Daten jedes Mal arbeiten, dann ersetzen die obiger Code mit dem folgenden:

keepLooping = true;
processTime = 0;
while keepLooping,
  % Capture your image
  % Compute the centroid data and place it in the vector "centroidData"
  centroidBuffer = [centroidBuffer(:,2:end) centroidData(:)];
  processTime = processTime+1;
  if (processTime == nBuffer),
    % Do whatever processing you want to do on centroidBuffer
    processTime = 0;
  end
  % Choose to set keepLooping to false, if you want
end

EDIT:

Es gibt eine Reihe von Variationen, die Sie mit dem obigen Code machen. Zum Beispiel, wenn Sie zwei Sätze von Daten mit 10 Zeitpunkt jeweils speichern mögen, können Sie ändern nBuffer bis 20 den alten Satz in den ersten 10 Spalten zu speichern und den neuen Satz in den letzten 10 Spalten . Ändern Sie dann die if-Anweisung:

  ...
  if (processTime == nBuffer/2),
  ...

Und jetzt können Sie führen Sie Ihre Verarbeitung sowohl den älteren Satz von 10 Datenpunkten (in centroidBuffer (:, 1:10) ) und den neueren Satz von 10 Datenpunkten (in centroidBuffer. (:, 11,20) )

Wenn Sie sprechen über große Datenmengen bei jeder Iteration kann die Daten Shuffle beginnen, einige Zeit in Anspruch nimmt. So wie ich es für große Datenmengen handhaben ist, etwas zu verwenden wie:

circBuff (:,:, mod (Zähler, numFrames)) = newData; Auf diese Weise können Daten nur einmal überschrieben, anstatt bei jedem Zyklus jeden Datenpunkt in Ihrem gesamten Puffer zu bewegen. Sie müssen nur ein bisschen mehr versierte darüber sein, wie Sie auf Ihre Daten zugreifen.

HTH, Dan

centroidBuffer = [centroidBuffer(:,2:end) centroidData(:)];

Dies ist eine schöne und einfache Lösung, aber es ist langsam. Jedes Mal, wenn Sie einen neuen Vektor hinzufügen, hat Matlab die ganzen alten Daten außer dem ersten Eintrag zu kopieren. Wenn Sie in Echtzeit denken, das ist keine gute Idee.

circBuff(:,:,mod(counter,numFrames)) = newData

Diese Idee hat nicht das Kopie-Problem, aber jetzt haben Sie keine schöne Subarray mehr, die die Daten in chronologischer Reihenfolge vom ersten Index bis zum letzten Index darstellt.

ich hochgeladen nur meine Lösung für einen schnellen Ringpuffer, der die beiden Probleme

vermeidet

http://www.mathworks.com/matlabcentral/fileexchange/47025 -circvbuf-m

Die Grundidee dieses Ringpuffers ist konstant und schnelle Performance und die Vermeidung von Kopiervorgängen, wenn der Puffer in einem Programm mit:

% create a circular vector buffer
    bufferSz = 1000;
    vectorLen= 7;
    cvbuf = circVBuf(int64(bufferSz),int64(vectorLen));

% fill buffer with 99 vectors
    vecs = zeros(99,vectorLen,'double');
    cvbuf.append(vecs);

% loop over lastly appended vectors of the circVBuf:
    new = cvbuf.new;
    lst = cvbuf.lst;
    for ix=new:lst
       vec(:) = cvbuf.raw(:,ix);
    end

% or direct array operation on lastly appended vectors in the buffer (no copy => fast)
    new = cvbuf.new;
    lst = cvbuf.lst;
    mean = mean(cvbuf.raw(3:7,new:lst));

überprüfen Sie den Screenshot zu sehen, dass dieser Ringpuffer Vorteile hat, wenn der Puffer groß ist, aber die Größe der Daten jedes Mal anzuhängen ist klein, wenn die Leistung von circVBuf auf der Puffergröße nicht davon ab, im Vergleich zu einer einfachen Kopie Puffer.

Die doppelte Pufferung garanties eine prädiktive Zeit für eine Append auf den Daten abhängig, in jeder Situation anzuhängen. In Zukunft soll diese Klasse gibt Ihnen eine Auswahl für die doppelte Pufferung ja oder nein - Dinge Speedup, wenn Sie die garantied Zeit nicht benötigen. eingeben Bild Beschreibung hier

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top