6

Próbowałem zasymulować wykres w czasie rzeczywistym z danymi dynamicznymi za pomocą d3.js. Używam tego przy użyciu przeglądarki IE-10.Pamięć stopniowo zwiększała się przy użyciu d3 dla wykresu w czasie rzeczywistym?

My Source Code

mogę natknąć się na problem, gdzie pamięć o mojej przeglądarce IE będzie stopniowo zwiększa się, jeśli opuścił aplikacji internetowych działa na pewien okres czasu.

I Wyszukiwałem możliwe przyczyny tego problemu.

Dwie rzeczy przychodzą do mojego umysłu do dyskusji:

  1. Timer uniemożliwia zbieranie śmieci IE

  2. wykres d3 nie zwalnia pamięć po data.shift()

Moje pytanie:

  1. Jak mogę zdiagnozować, czy mój problem rzeczywiście powstał z dyskusji 1 lub 2, czy też nie?

  2. Jak mogę rozwiązać problem z pamięcią?

Być może trzeba pobrać kod i uruchomić go od jakiegoś czasu i monitorować iexplorer.exe użyciu monitora zasobów w celu zidentyfikowania problemu.

Dziękuję.

Kod źródłowy:

<html> 
<head> 
<title>Animated Sparkline using SVG Path and d3.js</title> 
<script src="http://mbostock.github.com/d3/d3.v2.js"></script> 
<style> 
/* tell the SVG path to be a thin blue line without any area fill */ 
path { 
stroke: steelblue; 
stroke-width: 1; 
fill: none; 
} 
</style> 
</head> 
<body> 

<span> 
<b>Size:</b> 300x30 &nbsp;&nbsp;<b>Interpolation:</b> basis &nbsp;&nbsp;<b>Animation:</b> true &nbsp;&nbsp;<b>Transition:</b> 1000ms &nbsp;&nbsp;<b>Update Frequency:</b> 1000ms 
<div id="graph1" class="aGraph" style="width:300px; height:30px;"></div> 
</span> 



<script> 
var myTimer; 
function FeedDataToChart(id, width, height, interpolation, animate, updateDelay, transitionDelay, data, startIndex) { 
// create an SVG element inside the #graph div that fills 100% of the div 
var graph = d3.select(id).append("svg:svg").attr("width", "80%").attr("height", "80%"); 

// X scale will fit values from 0-10 within pixels 0-100 
var x = d3.scale.linear().domain([0, 48]).range([10, width-10]); // starting point is -5 so the first value doesn't show and slides off the edge as part of the transition 
// Y scale will fit values from 0-10 within pixels 0-100 
var y = d3.scale.linear().domain([0, 20]).range([height-10, 10]); 

// create a line object that represents the SVN line we're creating 
var line = d3.svg.line() 
// assign the X function to plot our line as we wish 
.x(function(d,i) { 
// verbose logging to show what's actually being done 
//console.log('Plotting X value for data point: ' + d + ' using index: ' + i + ' to be at: ' + x(i) + ' using our xScale.'); 
// return the X coordinate where we want to plot this datapoint 
return x(i); 
}) 
.y(function(d) { 
// verbose logging to show what's actually being done 
//console.log('Plotting Y value for data point: ' + d + ' to be at: ' + y(d) + " using our yScale."); 
// return the Y coordinate where we want to plot this datapoint 
return y(d); 
}) 
.interpolate(interpolation) 

var counter = startIndex; 

//var myData = data.slice(); 

// display the line by appending an svg:path element with the data line we created above 
graph.append("svg:path").attr("d", line(data)); 
// or it can be done like this 


function redrawWithAnimation() { 
// update with animation 
graph.selectAll("path") 
.data([data]) // set the new data 
.attr("transform", "translate(" + x(1) + ")") // set the transform to the right by x(1) pixels (6 for the scale we've set) to hide the new value 
.attr("d", line) // apply the new data values ... but the new value is hidden at this point off the right of the canvas 
.transition() // start a transition to bring the new value into view 
.ease("linear") 
.duration(transitionDelay) // for this demo we want a continual slide so set this to the same as the setInterval amount below 
.attr("transform", "translate(" + x(0) + ")"); // animate a slide to the left back to x(0) pixels to reveal the new value 
} 

function redrawWithoutAnimation() { 
// static update without animation 
graph.selectAll("path") 
.data([data]) // set the new data 
.attr("d", line); // apply the new data values 
} 

function stopTimer() 
{ 
clearInterval(myTimer); 
myTimer = null; 
graph.selectAll("path").data([data]).remove().append("svg:path").attr("d", line); 
buffer = null; 

signalGenerator(); 
} 

function startTimer() 
{ 
if (myTimer == null) 
{ 
myTimer = setInterval(function() { 
if (counter < data.length - 1) 
{ 
var v = data.shift(); // remove the first element of the array 
data.push(v); // add a new element to the array (we're just taking the number we just shifted off the front and appending to the end) 
if(animate) 
{ 
redrawWithAnimation(); 
} 
else 
{ 
redrawWithoutAnimation(); 
} 
counter++; 
} 
else 
{ 
//alert("no more data in buffer"); 
stopTimer(); 
counter = startIndex; 
} 
}, updateDelay); 
} 
} 

startTimer(); 

} 


var buffer; 
function signalGenerator() 
{ 
if (buffer == null) 
{ 
buffer = new Array(100); 

var i; 
for (i = 0; i < buffer.length; i++) 
{ 
buffer[i] = Math.random() * 10; 
} 

FeedDataToChart("#graph1", 300, 300, "basis", true, 100, 100, buffer, 0); 

} 
} 

function startGenerator() 
{ 
    signalGenerator(); 

} 

startGenerator(); 

</script> 

</body> 
</html> 
+0

Nie wiem szczerze, czy może to być ilość danych, ale można spróbować usunąć nieużywane/stare dane z zestawu danych i zobaczyć, jak to działa. (Nie mogłem też spróbować uruchomić go na moim komputerze, ponieważ jestem na OSX) – tomtomtom

+0

Myślę, że moje źródło może działać na chrome, a także – jhyap

+0

zostawiłem to działa przez 5 minut lub tak (pasek obejmował całą oś X i niektóre dane wyszły z ekranu), nie zauważyłem zwiększenia zużycia pamięci w moim monitorze aktywności przy użyciu Safari – tomtomtom

Odpowiedz

3

Próbowałem jak powiedział przez 2 godziny i było początkowo 56 MB pamięci i wykorzystanie w końcu około 56,8 MB. Oznacza to tylko 0,8 MB różnicy w niektórych wyjątkowych przypadkach. Ale mogę pomóc ci znaleźć dokładny punkt, w którym występuje ładowanie pamięci. Wystarczy postępować zgodnie z instrukcjami jeden po drugim.

  1. Otwartych "Narzędzia dla deweloperów" IE naciskając klawisz F12

  2. idź do pamięci (symbolem aparatu lub Ctrl + 7)

  3. kliknij Rozpocznij Profilowanie Session (Zielony przycisk Play na szczycie)

  4. Zrób zdjęcie z ujęcia sterty, aby utworzyć linię podstawową.

  5. Teraz co 10 lub 15 minut podjąć sterty snap shot

  6. Czy to za ile godzin wymaga (w przypadku 2 godziny)

  7. Po profilowania odbywa się na żądanym czasie, należy przerwać to i analizuj od początku, porównując Strzały z Przyciągania Strzały.

  8. Jeśli różnica w pamięci na początku i na końcu jest tak duża, sprawdź, gdzie zaczyna się wzrost pamięci, analizując różnicę w pamięci w migawce.

  9. Tutaj można sprawdzić różnicę w pamięci używanej przez proces pod względem bajtów lub KB.

  10. Sprawdź, która funkcja, zmienna lub operacja powodują problem z pamięcią. Najprawdopodobniej niektóre obliczenia, które są wielokrotnie przeprowadzane, aby zmienne użyte w tych obliczeniach nie zostały zwolnione z określonego punktu czasowego. Podczas analizowania przepływu pamięci widziałem "Ba, p", "n, p", "Wa, n, p" itd. Wierzę, że funkcje, które używają tych zmiennych, stwarzają problem dla ciebie.

Uwaga

W przypadku korzystania z interfejsu reagowania (CTRL + 5), można łatwo zauważyć, że Garbage Collection jest przeprowadzane przez IE automatycznie.

+0

Zweryfikowałem, że zrzut sterty nie pokazuje wycieku pamięci w systemie lokalnym. Strzała stosu przedstawia niski rozmiar sterty, podczas gdy pamięć ciągle rośnie. – jhyap

Powiązane problemy