2014-10-17 15 views
5

Tôi chắc chắn có lý do chính đáng cho việc này, nhưng tôi không thấy nó.Option.fold - tại sao đối số thứ hai của nó không phải là toán tử nhị phân?

Fold trên (nói) List lợi nhuận

kết quả của việc áp dụng lần hành op giữa tất cả các yếu tố và z

Nó có một mối quan hệ rõ ràng với foldLeftfoldRight rằng làm điều tương tự nhưng với thứ tự được xác định (và do đó không cần các toán tử liên kết)

Fold trên Option lợi nhuận

Trả về kết quả của việc áp dụng f-scala.Option này giá trị 's nếu scala.Option là không rỗng. Nếu không, hãy đánh giá biểu thức ifEmpty.

ifEmpty là (ở vị trí) z cho danh sách. f là (ở vị trí của) các op

Đối None (trong đó, sử dụng mô hình tinh thần của tôi về Option như là một "container" có thể có hoặc không có thể chứa một giá trị, là một "trống rỗng" thùng chứa), mọi thứ là OK , Option.fold trả về số không (giá trị của ifEmpty).

Đối Some(x), tuy nhiên, không f nên mất hai params, zx vì vậy nó phù hợp với fold trên chuỗi (bao gồm cả việc có một mối quan hệ tương tự như foldLeftfoldRight).

Chắc chắn có một đối số tiện ích chống lại điều này - có f chỉ cần x làm tham số trong thực tế có thể thuận tiện hơn. Trong hầu hết các trường hợp, nếu nó cũng mất z sẽ bị bỏ qua. Nhưng vấn đề nhất quán quá ...

Vì vậy, ai đó có thể giải thích cho tôi tại sao fold trên Tùy chọn vẫn là "thích hợp" fold?

+0

Nhưng 'Một số lần gấp # có 2 đối số. https://github.com/scala/scala/blob/v2.11.3/src/library/scala/Option.scala#L1 Tôi xin lỗi tôi không hiểu câu hỏi – Jatin

+0

Nó thực sự có hai đối số; nhưng các đối số chỉ nằm trong các danh sách đối số riêng biệt. – Jesper

+0

Tôi hỏi tại sao đối số thứ hai không phải là toán tử nhị phân. Không phải lý do tại sao nếp gấp lại có hai đối số - như bạn nói, nó có! –

Trả lời

2

Tại sao phải như vậy?

Lý do gấp "bình thường" cần một toán tử nhị phân là vì "thông thường" được sử dụng trong danh sách có thể được xử lý từng cái một với toán tử nhị phân (và giá trị hạt z).

Gấp trên một tùy chọn là, trên thực tế, một chức năng bản đồ với một trường hợp mặc định. Nếu bạn nhìn vào định nghĩa của nó, nghĩa đen là:

if (isEmpty) ifEmpty else f(this.get) 

Vì bạn chỉ có một đối số có thể, f phải là một toán tử đơn nhất. Người ta có thể tranh luận rằng có một lựa chọn gấp cần một toán tử nhị phân và sử dụng giá trị ifEmpty làm hạt giống trong trường hợp tùy chọn được xác định, nhưng giá trị hạt giống hợp lý của bạn và giá trị hợp lý của bạn khi tùy chọn trống có thể khác nhau rất nhiều.

Như một người nào đó đã chỉ ra, đối với các cấu trúc khác nhau, bạn cần các vị trí khác nhau (chẳng hạn như đối với cây), vì ứng dụng "hợp lý" của giảm có cấu trúc khác nhau.

0

scala.Option.fold là lỗi; thiết kế API kém.

Option { 
    // This is equivalent to: map f getOrElse ifEmpty. 
    def fold[B](ifEmpty: => B)(f: A => B): B = if (isEmpty) ifEmpty else f(this.get) 
} 

Phương pháp Option.fold có thể có ích, nhưng nó không fold (tương tự như vậy cho Either.fold).

TraversableOnce { 
    // List, et alia 
    def fold[A1 >: A](z: A1)(op: (A1, A1) => A1): A1 = foldLeft(z)(op) 
} 

Các lợi ích của một phương pháp tiêu chuẩn là các khái niệm và gõ chữ ký phù hợp (không cần phải xem xét các tài liệu một lần nữa).

Ngoài ra, Option.foldLeft nhất quán và thực hiện toán tử nhị phân.

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