Làm thế nào để hủy một đối tượng JavaScript?


79

Gần đây, tôi đã xem một ứng dụng của mình ngốn quá nhiều bộ nhớ và tăng 10 MB / giây.

Vì vậy, tôi muốn biết cách tốt nhất để phá hủy đối tượng và biến JavaScript để mức tiêu thụ bộ nhớ giảm xuống và FF của tôi không thể bị phá hủy.

Tôi đang gọi hai JavaScript của mình trong khoảng thời gian 8 giây một lần mà không cần tải lại trang.

function refresh() {
    $('#table_info').remove();
    $('#table').hide();
    if (refreshTimer) {
        clearTimeout(refreshTimer);
        refreshTimer = null ;
    }
    document.getElementById('refresh_topology').disabled=true; 
    $('<div id="preload_xml"></div>').html('<img src="pic/dataload.gif" alt="loading data" /><h3>Loading Data...</h3>').prependTo($("#td_123"));
    $("#topo").hide();
    $('#root').remove();
    show_topology();
}

Làm cách nào để biết biến nào gây ra Chi phí bộ nhớ và phương pháp ngừng thực thi quá trình đó?


1
Bạn đã xem xét việc cô lập các phần mã của mình bằng cách sử dụng các lệnh đóng chưa?
YS.

1
Bạn đã thử gì chưa? Thích sử dụng obj = null?
Florian Margaine

A) Làm gì show_topology? --- B) Bạn có bao giờ xóa những thứ bạn thêm vào #td_123không? --- C) Có phiên bản trực tiếp của điều này ở đâu đó không?
Deestan

Câu trả lời:


92

Bạn có thể đặt tất cả mã của mình trong một không gian tên như thế này:

var namespace = {};

namespace.someClassObj = {};

delete namespace.someClassObj;

Việc sử dụng deletetừ khóa sẽ xóa tham chiếu đến thuộc tính, nhưng ở cấp độ thấp, bộ thu gom rác JavaScript (GC) sẽ lấy thêm thông tin về đối tượng nào cần được lấy lại.

Bạn cũng có thể sử dụng Công cụ dành cho nhà phát triển Chrome để tải hồ sơ bộ nhớ của ứng dụng của mình và những đối tượng nào trong ứng dụng của bạn cần được thu nhỏ.


12
Nhấn F12 để nhận các công cụ dành cho nhà phát triển. Chuyển đến tab Hồ sơ và Nhấp vào Bắt đầu để bắt đầu hồ sơ. Bạn có thể làm hồ sơ trên JS CPU, CSS Selector và bạn có thể chụp nhanh Heap.
Sarath

3
hoặc trong chrome mới nhất, nhập hiệu suất từ ​​trong bảng điều khiển js
David Morrow.

Có lẽ điều đó là hiển nhiên, nhưng bạn có thể đặt tên cho không gian tên của mình một cái gì đó như "g" và tiết kiệm rất nhiều lần nhập. Sử dụng g.curItem = ... thay vì var curItem = ... và lưu việc nhập cũng như cho phép g = undefined xóa tất cả phân bổ bộ nhớ chung.
David Spector

31

Bạn không thể xóa các đối tượng, chúng sẽ bị xóa khi không còn tham chiếu đến chúng. Bạn có thể xóa các tham chiếu với delete.

Tuy nhiên, nếu bạn đã tạo các tham chiếu vòng tròn trong các đối tượng của mình, bạn có thể phải loại bỏ một số thứ.


2
Bạn có thể thêm một ví dụ về tham chiếu vòng tròn mà bộ thu gom rác sẽ không bắt được không? Yêu cầu một người bạn! ;)
emilhem

@emilhem bạn có thể tham khảo trình thu gom rác và nó sẽ tự xóa chính nó và internet - vụ nổ có thể tạo ra một lỗ đen tại CERN. Bạn đã nghĩ về ví dụ đó chưa?
El Mac

28

Mặc dù các câu trả lời hiện có đã đưa ra các giải pháp để giải quyết vấn đề và nửa sau của câu hỏi, chúng không cung cấp câu trả lời cho khía cạnh tự khám phá của nửa đầu câu hỏi được in đậm:

"Làm cách nào để biết biến nào gây ra chi phí bộ nhớ ...?"

Có thể không còn mạnh mẽ như 3 năm trước, nhưng phần " Hồ sơ " của Công cụ dành cho nhà phát triển Chrome hiện khá mạnh mẽ và nhiều tính năng. Nhóm Chrome có một bài viết chi tiết về cách sử dụng nó và cũng như cách thức hoạt động của bộ thu gom rác (GC) trong javascript, đây là cốt lõi của câu hỏi này.

deletevề cơ bản là gốc của câu trả lời hiện được chấp nhận bởi Yochai Akoka, điều quan trọng là phải nhớ xóa tác dụng gì. Nó không liên quan nếu không được kết hợp với các khái niệm về cách GC hoạt động trong hai câu trả lời tiếp theo: nếu có một tham chiếu hiện tại đến một đối tượng thì nó chưa được làm sạch. Các câu trả lời đúng hơn, nhưng có lẽ không được đánh giá cao vì chúng đòi hỏi nhiều suy nghĩ hơn là chỉ viết 'xóa'. Có, một giải pháp khả thi có thể được sử dụng delete, nhưng sẽ không thành vấn đề nếu có một tham chiếu khác liên quan đến rò rỉ bộ nhớ.

Một câu trả lời khác đề cập thích hợp đến các tham chiếu vòng tròn và tài liệu của nhóm Chrome có thể cung cấp nhiều thông tin rõ ràng hơn cũng như các công cụ để xác minh nguyên nhân.

deleteđã được đề cập ở đây, nó cũng có thể hữu ích khi cung cấp tài nguyên Hiểu Xóa . Mặc dù nó không đi vào bất kỳ giải pháp thực tế nào thực sự liên quan đến trình thu gom rác của javascript.


8

Cấu trúc mã của bạn để tất cả các đối tượng tạm thời của bạn được đặt bên trong các bao đóng thay vì không gian tên toàn cục / thuộc tính đối tượng toàn cầu và vượt ra khỏi phạm vi khi bạn đã làm xong với chúng. GC sẽ lo phần còn lại.


1

Tôi đang đối mặt với một vấn đề như thế này và có ý tưởng chỉ đơn giản là thay đổi nộiHTML của các con của đối tượng có vấn đề.

adiv.innerHTML = "<div...> the original html that js uses </div>";

Có vẻ bẩn, nhưng nó đã cứu mạng tôi, vì nó hoạt động!

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.