2011-03-18 17 views
6

Tôi đang tìm một người nào đó để xác nhận một cách chính đáng hoặc sửa những gì tôi nghĩ rằng tôi biết về tùy chọn -CSDA trên dòng shebang của một tập lệnh Perl.Điều gì là tốt -CSDA chỉ được chỉ định trên dòng shebang?

Xem perldoc perlrun cho tài liệu của -CSDA. Tóm lại

  • S: STDIN, STDOUTSTDERR được giả định là UTF-8
  • D: UTF-8 là lớp PerlIO mặc định cho cả đầu vào và đầu ra suối
  • A: @ARGV yếu tố này được dự kiến ​​sẽ được chuỗi UTF-8
  • Đối với -CSDA để có hiệu lực, nó phải được xác định trên dòng lệnh như trong perl -CSDA script.pl.

  • Trước 5.10, -CSDA trên dòng công việc âm thầm sẽ thất bại vì các dòng tiêu chuẩn sẽ đã được mở ra và @ARGV sẵn có ở đó vào thời điểm nó đã gặp phải trừ -CSDA đã được chỉ định trên dòng lệnh là tốt.

  • Sau 5,10, -CSDA chỉ xuất hiện trên dòng shebang gây ra perl để bẻ cong do sự cố đó.

  • Một kịch bản với -CSDA được sử dụng để làm việc với perl s trước 5.10 nên có -CSDA lấy ra từ dòng công việc bởi vì nó không bao giờ được gọi với những tùy chọn trên dòng lệnh (và các tùy chọn, nếu được chỉ định chỉ duy nhất trên shebang line, không làm gì cả).

Tôi rất muốn nhận được một số phản hồi chắc chắn về các giả định của tôi ở trên là sai.

Trả lời

3

Không chắc chắn tôi có thẩm quyền như thế nào, nhưng tôi biết cách hoạt động của tính năng này.

  • Giả định đầu tiên của bạn gần như chính xác. Để các tùy chọn SDA có hiệu lực, chúng phải có mặt khi bắt đầu thông dịch viên. Đó có thể là do -CSDA trên dòng lệnh hoặc có thể do biến môi trường PERL_UNICODE hoặc có thể là một số phương pháp khác mà tôi không biết.
  • Giả thiết thứ hai của bạn là chính xác, ít nhất là đối với 5.8.8. Lưu ý rằng cờ D sẽ vẫn có hiệu ứng bình thường đối với các luồng được mở bởi tập lệnh.
  • Giả định thứ ba của bạn là chính xác. Tuy nhiên, bắt đầu với 5.10.1 nó sẽ không bị cắt nếu cờ thích hợp được kích hoạt thông qua biến môi trường PERL_UNICODE hoặc một số cơ chế khác.
  • Giả định thứ tư của bạn là không phải thường chính xác. Tôi đoán bạn đang đề cập đến tình huống khi kịch bản được gọi trực tiếp, thay vì gọi trình thông dịch perl với kịch bản như một đối số. Có hai trường hợp chung.
    • Trên hệ thống nơi hệ điều hành xác định rằng bất kỳ tệp nào có đuôi ".pl" sẽ được chuyển đến trình thông dịch perl để thực thi, như Windows, bạn có thể chính xác.Nhưng có thể lập luận rằng việc cắt xén kịch bản khi được gọi không có -CSDA là hành vi mong muốn, chứ không phải là những thứ thất bại một cách bí ẩn vì đầu vào tiêu chuẩn và @ARGV không phải là UTF-8 như kịch bản mong đợi. Trên hệ thống đọc dòng shebang khi một tập lệnh được thực hiện trực tiếp, giống như hầu hết các shell * nix, các tùy chọn dòng lệnh được chỉ định trong dòng shebang sẽ được sử dụng khi gọi trình thông dịch và do đó -CSDA trên dòng shebang sẽ được vinh danh.
+1

+1. Đối với mục cuối cùng, trên các hệ thống mà '/ usr/bin/perl' không phải là trình thông dịch nhưng là một chương trình quyết định phiên bản' perl' cần gọi (như trên hệ điều hành OS X, nơi '5.8' và' 5.10' cùng tồn tại), '-CSDA' trên dòng shebang làm cho' perl' bị xáo trộn khi nó được gọi. –

+0

Đó là sự thật, nó sẽ là một lỗi trong kịch bản trình bao bọc. Nhưng khi tôi kiểm tra nó trên máy Mac, tôi thấy rằng vấn đề thực sự là 5.10.0 (đi kèm với OS X 10.6.6) không cho phép -C luôn luôn, trong khi 5.10.1 (đó là những gì tôi có trên máy Linux của tôi) cho phép nó nếu các cờ được chỉ định đã hoạt động. Chỉ định perl5.8.9 trên shebang không tôn trọng -CSDA chính xác. – Anomie

+0

Cảm ơn bạn đã làm rõ. Nhiều đánh giá cao. –

3

Nếu kịch bản của bạn là

#!/usr/bin/perl -CSDA 

và bạn bắt đầu kịch bản của bạn sử dụng

./script foo 

Hệ điều hành sẽ khởi động Perl như sau:

/usr/bin/perl -CSDA ./script foo 

Sự thay đổi trong hành vi chỉ phát huy tác dụng nếu khởi chạy tập lệnh không chính xác, chẳng hạn như bằng cách sử dụng

/usr/bin/perl ./script foo 

Khắc phục không được xóa -CSDA, khắc phục là gọi tập lệnh chính xác.

+0

Tùy thuộc. Tôi đang cố gắng tìm hiểu xem liệu '-CSDA' có ảnh hưởng gì đến chức năng của chương trình này mà tôi đang cố gắng hiểu hay không. –

+0

@Sinan Ünür, Bạn có in tới STDOUT hoặc STDERR không? Bạn đã đọc từ STDIN chưa? Sau đó, nếu bạn mong đợi để đối phó với bất cứ điều gì ngoài phạm vi ASCII, thì bạn nên sử dụng nó hoặc một cái gì đó tương đương. – ikegami

+0

Vâng, tôi không biết và đó là một phần của vấn đề. –

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