2010-08-18 34 views

Trả lời

11

Nếu mã trong câu hỏi là không sử dụng STDOUT một cách rõ ràng (ví dụ, nó chỉ không print "..."), bạn có thể sử dụng select để thay đổi filehandle rằng print sử dụng:

my $output; 
open(my $outputFH, '>', \$output) or die; # This shouldn't fail 
my $oldFH = select $outputFH; 
call_code_that_prints(); 
select $oldFH; 
close $outputFH; 

print $output; # Here's what we collected 

Sử dụng select làm cho nó dễ dàng hơn để khôi phục lại STDOUT sau đó. Đóng và mở lại STDOUT khó hoàn tác hơn. Lưu ý rằng select không ảnh hưởng đến chính STDOUT, do đó, nó không ảnh hưởng đến các quá trình bên ngoài, nhưng bạn nói rằng bạn không có bất kỳ. Nó cũng không ảnh hưởng đến mã làm điều gì đó như print STDOUT "...".

Nếu phương pháp select không đủ cho nhu cầu của bạn, tôi khuyên bạn nên thử Capture::Tiny. Nó có thể nắm bắt đầu ra từ các chương trình bên ngoài và mã viết cho STDOUT một cách rõ ràng. Nhưng nó không thể (hiện tại) chỉ chụp STDOUT; nó luôn luôn chụp cả STDOUT và STDERR (một cách riêng biệt hoặc được hợp nhất thành một chuỗi).

16

Cách mới, thú vị để xử lý việc này là với Capture::Tiny. Bạn có thể sử dụng nó bằng phẫu thuật để chỉ ảnh hưởng đến một phần của chương trình mà bạn cần nó mà không làm phiền bất cứ điều gì khác. Nhưng, tôi có thể làm những gì cjm recommends vì điều đó không đòi hỏi một mô-đun.

+1

Một vấn đề với việc sử dụng Capture :: Tiny cho điều này là nó không có cách nào để chỉ chụp STDOUT và để STDERR một mình. Nó luôn luôn chụp cả hai, một cách riêng biệt hoặc sáp nhập. – cjm

+1

Vâng, không phải cho đến khi ai đó gửi một bản vá. [RT # 60515] (https://rt.cpan.org/Ticket/Display.html?id=60515) :) –

+0

Theo dõi ... Capture :: Tiny đã được cập nhật tại một số điểm sau khi các ý kiến ​​ở trên. Nó có thể lấy chỉ STDOUT và để STDERR một mình với 'capture_stdout'. Có những biến thể khác cũng tùy thuộc vào những gì bạn muốn làm. Mô-đun rất hữu ích. –

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