Như đã đề cập trong câu trả lời của Kevin Guerra, chiến lược "root.clear()" trong tài liệu ElementTree chỉ xóa các phần tử được phân tích cú pháp hoàn toàn của thư mục gốc. Nếu những đứa trẻ đó đang neo đậu những cành cây lớn, nó không phải là rất hữu ích.
Ông đề cập đến giải pháp lý tưởng, nhưng không gửi bất kỳ mã, vì vậy đây là một ví dụ:
element_stack = []
context = ET.iterparse(stream, events=('start', 'end'))
for event, elem in context:
if event == 'start':
element_stack.append(elem)
elif event == 'end':
element_stack.pop()
# see if elem is one of interest and do something with it here
if element_stack:
element_stack[-1].remove(elem)
del context
Yếu tố hấp dẫn sẽ không có phần tử con; chúng sẽ bị xóa ngay khi thẻ kết thúc của chúng được xem. Điều này có thể được chấp nhận nếu tất cả những gì bạn cần là văn bản hoặc thuộc tính của phần tử.
Nếu bạn muốn truy vấn vào con cháu của phần tử, bạn cần tạo một nhánh đầy đủ cho nó. Đối với điều này, duy trì một lá cờ, thực hiện như một truy cập chiều sâu cho những yếu tố đó. Chỉ gọi .remove() khi độ sâu là 0:
element_stack = []
interesting_element_depth = 0
context = ET.iterparse(stream, events=('start', 'end'))
for event, elem in context:
if event == 'start':
element_stack.append(elem)
if elem.tag == 'foo':
interesting_element_depth += 1
elif event == 'end':
element_stack.pop()
if elem.tag == 'foo':
interesting_element_depth -= 1
# do something with elem and its descendants here
if element_stack and not interesting_element_depth:
element_stack[-1].remove(elem)
del context
Nguồn
2017-06-12 22:26:27
Hãy làm rõ "luôn tăng". Nếu bạn thực hiện thao tác trên trong một vòng lặp, việc sử dụng bộ nhớ có phát nổ không? Hay bạn chỉ thấy việc sử dụng tăng lên sau khi làm điều này một lần, ngay cả sau khi tất cả các đối tượng được giải phóng? – wberry
Tôi có nghĩa là tôi mong đợi việc sử dụng bộ nhớ cho chương trình ở trên không thay đổi. Thay vào đó, nó cho thấy một sự gia tăng độc đáo. –
chạy trên trong một vòng lặp không có hiệu lực, vì nó sẽ chỉ tiêu thụ stdin. –