2015-11-08 16 views
6

Tôi cần thực hiện một số xử lý chỉ đọc trên tất cả các tệp trong thư mục một cách đệ quy. Tôi đang sử dụng Files.walk để nhận luồng luồng của các tệp nhưng tôi nhận thấy rằng api chỉ định rằng walk chỉ trả lại luồng thông thường chứ không phải luồng song song.Làm cách nào để nhận luồng song song của Files.walk?

Làm cách nào để xử lý tất cả các tệp trong một thư mục song song?

+4

Có thể giống như 'Files.walk (...). Parallel()'? – Flown

+0

@Fown Hah ... ngớ ngẩn tôi. Không nhận ra bạn có thể chuyển đổi các luồng bình thường thành song song. –

Trả lời

15

Bạn có thể chuyển đổi bất kỳ Stream thành song song Stream bằng cách gọi Stream::parallel.

Stream<Path> stream = Files.walk(startPath).parallel().forEach(...); 
+9

Lưu ý rằng 'Files.walk' song song không tốt, đặc biệt nếu cây con của bạn có ít hơn 1024 tệp. Nếu bạn có quá trình xử lý nhiều tập tin và không quá nhiều tệp, nó sẽ có thể hiệu quả hơn với 'Files.walk (đường dẫn) .collect (toList()). ParallelStream()'. –

+1

@TagirValeev Thú vị. Bạn có một liên kết giải thích lý do tại sao điều này là như vậy? –

+7

@DavidGrinberg, mã nguồn JDK và điểm chuẩn. Nó sử dụng 'Spliterators.spliteratorUnknownSize' nội bộ mà tách chiến lược là nạp khối thành các mảng bắt đầu với 1024 phần tử. Do kích thước không xác định, công cụ Stream pipeline giả định rằng việc chia tách tạo ra ngay cả các phần, nhưng chúng thực sự không (lần đầu tiên được chia cho <= 1024 đầu vào tất cả các phần tử thành tiền tố không để lại phần tử nào cho hậu tố). Điều này dẫn đến hiệu suất song song rất xấu. –

Các vấn đề liên quan