5

Tôi có một câu hỏi chung về dịch viên ngôn ngữ chức năng:Liệu runtime thường sử dụng một giải bắt buộc giống như mã ngôn ngữ chức năng

Có thực sự bất kỳ lợi thế để sử dụng một ngôn ngữ chức năng so với một ngôn ngữ bắt buộc trong thời gian chạy (hoặc làm theo cách của họ để thông dịch viên)?

Không có câu hỏi nào tôi thấy (chẳng hạn như this) thực sự nhận được câu hỏi này và tìm kiếm tràn ngập các đối số về định nghĩa của các ngôn ngữ khác nhau.

CHỈNH SỬA: Tách xuống câu hỏi duy nhất mà tôi đã kết thúc cần được trả lời.

+2

Bạn có ý nghĩa gì bởi những lợi thế mà họ thực hiện theo cách của họ tới thông dịch viên? – sepp2k

+1

@ sepp2k Cũng giống như các ví dụ cụ thể mà tôi liệt kê: dường như có nhiều tính năng phổ biến khác nhau của ngôn ngữ lập trình hàm. Tôi muốn biết nếu các tính năng này có vẻ khác biệt với lập trình chức năng từ phong cách bắt buộc sẽ thực sự tạo ra bất kỳ sự khác biệt nào trong thời gian chạy hay chỉ là một sự khác biệt bề ngoài trong phong cách mã hóa phân biệt hai. Có lý? –

+0

Tôi đã thay đổi tiêu đề và một chút câu hỏi, hy vọng nó rõ ràng hơn bây giờ. –

Trả lời

29

Câu trả lời ngắn gọn là: mọi thứ được biên dịch sang một số ngôn ngữ cấp thấp cuối cùng (ngôn ngữ lắp ráp hoặc ngôn ngữ máy ảo). Các ngôn ngữ chức năng và mệnh lệnh là bằng nhau: chúng phải biên dịch các cơ chế trừu tượng của chúng để phù hợp với những gì có sẵn trên máy.
Nơi ngôn ngữ tạo sự khác biệt là chúng khớp với mã cấp thấp cơ bản như thế nào (bằng cách cung cấp các tính năng cấp thấp để tối ưu hóa mã bằng tay khi được mong muốn) và tối ưu hóa chúng cho phép hoặc dễ dàng hơn bằng cách có ngữ nghĩa rõ ràng. . Ví dụ, khi biên dịch thành mã gốc, đệ quy không phải là (nói chung) được biên dịch thành các vòng lặp, mà là nhảy vào nhãn, giống như vòng lặp là: hầu hết các ngôn ngữ lắp ráp đều không có vòng lặp hay đệ quy. Tất nhiên, nếu bạn biên dịch thành một máy ảo có vòng lặp nhưng không có nhảy, bạn cần tạo ra các vòng lặp; đây là một vấn đề ví dụ trên máy ảo Java, bởi vì các cuộc gọi đuôi chung có tính biểu cảm cao hơn các vòng một mình và bạn cần phải làm việc xung quanh giới hạn đó, từ bỏ một số hiệu quả.

"Ưu điểm" của các chương trình chức năng có thể là do ngữ nghĩa hoạt động tốt hơn, bạn có thể dễ dàng hơn về chương trình và ví dụ như tối ưu hóa nhanh theo cách đơn giản hơn. Rất nhiều trình biên dịch ngày nay sử dụng hình thức trung gian Single Static Assignment (SSA), về cơ bản là một ngôn ngữ chức năng cấp thấp - mặc dù nó được phát hiện độc lập bởi những người trong cộng đồng trình biên dịch. Hầu hết các tối ưu hóa dễ dàng hơn khi bạn đã loại bỏ các biến đột biến, ví dụ, và một biến giữ cùng một giá trị trong tất cả phạm vi của nó. Có một số kỹ thuật để thực hiện phân bổ đăng ký trong more efficient ways trên các biểu mẫu trung gian chức năng như vậy.

¹: Xem bài viết ngắn của Andrew Appel năm 1998: SSA is Functional Programming; nếu bạn quan tâm đến chi tiết về biểu mẫu SSA, dưới đây là some reading notes về mối quan hệ giữa SSA và các hình thức trung gian chức năng khác, chẳng hạn như CPS.

Bạn cũng có thể nhận được lợi thế tối ưu từ độ tinh khiết (không có tác dụng phụ, hoặc ít nhất một điều khiển tốt mà tính toán sẽ không có tác dụng phụ) và gõ tĩnh. Từ độ tinh khiết, bạn có thể lấy được các tối ưu hóa mạnh mẽ như deforestation hoặc fusion (loại bỏ cấu trúc dữ liệu trung gian) và từ đánh máy bạn có thể nhận được sự đảm bảo mạnh mẽ về hình dạng của giá trị của bạn (đó là lý do tại sao một số ngôn ngữ động cố gắng cho phép một số chú thích loại bị hạn chế mục đích) cho phép tạo mã tốt hơn.

Về quyền truy cập vào các tính năng cấp thấp: Fortran, C và C++ có lẽ là ngôn ngữ tốt nhất và có sẵn nhất "có thể đi rất thấp".Một số ngôn ngữ cố gắng cung cấp một số khả năng đó: ví dụ: ATS (ban đầu là ngôn ngữ lập trình hàm, mặc dù nó rất khó nhìn thấy) cung cấp khả năng kiểm soát tốt trên phân bổ cấp phát stack, cả hai Haskellthe CLR (C#,etc.) các loại tổng hợp là trường hợp đặc biệt của lý do cấp thấp như vậy và tương tự Rust đang cố gắng cung cấp cho bạn các cách đưa ra quyết định cấp thấp về mức tiêu thụ bộ nhớ. Tuy nhiên, trong khi điều này chắc chắn hữu ích khi bạn đã phân lập một phần nhỏ mã quan trọng đối với buổi biểu diễn của mình và bạn muốn tối ưu hóa địa ngục (từ bỏ một số tính linh hoạt/đơn giản/khả năng bảo trì), điều này sẽ không thay đổi cuộc sống của bạn trong các tình huống hàng ngày, trừ khi bạn là một lập trình viên nhúng/hạt nhân. Bạn có thể sẽ nhận được hiệu suất tổng thể nhiều hơn từ một ngôn ngữ hiệu quả cho phép bạn sử dụng mức trừu tượng đúng, và dành nhiều thời gian hơn vào việc lựa chọn thiết kế và thuật toán chính xác cho vấn đề của bạn. Tất nhiên, người ta có thể muốn có cả hai, và có thể nhưng khó khăn.

+0

Điều này là hoàn hảo, cảm ơn bạn. –

0

Có thực sự bất kỳ lợi thế để sử dụng một ngôn ngữ chức năng so với một ngôn ngữ bắt buộc trong thời gian chạy (hoặc thực hiện theo cách của họ để người phiên dịch)?

Có. Nếu bạn sử dụng một ngôn ngữ chức năng, lợi thế là trình biên dịch thông dịch có thể được thực hiện nhanh hơn. Nếu bạn sử dụng một lệnh bắt buộc, bộ nhớ ít hơn và CPU có thể được sử dụng.

Vì vậy, bất kể bạn làm như thế nào, đều có lợi thế.

Nhưng, với hai thông dịch viên, một được viết bằng ngôn ngữ bắt buộc và một ngôn ngữ khác trong ngôn ngữ bắt buộc, và cho thêm cả hai đều đúng, bạn không thể biết được kết quả của một chương trình mà trình thông dịch được sử dụng.

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