2012-01-03 22 views
14

Tôi có một chương trình haskell liệt kê tất cả các số nguyên từ [1..n] dựa trên đầu vào n. Tôi muốn lọc các số nhất định dựa trên điều kiện từ số đó và hiển thị dưới dạng danh sách. ở đâu và làm thế nào tôi có thể sử dụng chức năng lọc/điều kiện?Làm cách nào để sử dụng chức năng lọc trong Haskell?

Theo tài liệu Haskell:

filter :: (a -> Bool) -> [a] -> [a] 

lọc, áp dụng cho một vị và một danh sách, trả về danh sách những nhân tố này đáp ứng các vị ngữ; tức là,

filter p xs = [ x | x <- xs, p x] 

Trả lời

21

Bạn đã nhận nó, khá nhiều. Vì vậy, phần còn lại của thỏa thuận này là thiết kế chức năng vị ngữ cho danh sách của bạn. Giả sử bạn đã có danh sách được gọi là xs và hàm vị trí p, tất cả những gì bạn phải làm là

bộ lọc p xs.

Thông thường, bạn sẽ thấy p định nghĩa là một ẩn danh, hoặc lambda, biểu hiện, như vậy:

lọc (\ n -> n 'mod` 2 == 0) xs.

Không cần thiết và có thể hữu ích khi người mới bắt đầu xác định các hàm được đặt tên.

ISEVEN n = n 'mod` 2 == 0

evenListNumbers xs = lọc ISEVEN xs

evenListNumbers [1,2,3,4]

Đó là này [2,4].

Vì vậy, một chức năng vị ngữ cho một bộ lọc danh sách nhất định có một phần tử danh sách và trả về một giá trị boolean. Nếu đó là sự thật, phần tử được giữ lại (hoặc được thêm vào danh sách kết quả), và nếu nó là false, nó được chuyển qua.

+0

cảm ơn! giải thích nó rất rõ ràng. tôi hiểu làm thế nào để lọc số chẵn và lẻ nhưng những gì về lọc những con số có thể chia n đầu vào? một cái gì đó như isDivisible n = lọc [1..n] div n? cú pháp cho điều đó là gì?: S – Amjad

+0

Bạn sẽ phải thực hiện một chức năng dọc theo các dòng: 'isDivisible n p = n \' mod \ 'p == 0' và sử dụng làm vị từ của bạn. Lưu ý rằng hàm này trả về true nếu phần còn lại của phân chia n với p là 0 và sai khác. Hãy lưu ý rằng các đối số hiện đang theo thứ tự hơi khác so với thứ bạn muốn, vì vậy bạn có thể chỉ cần lật chúng trong định nghĩa ngay bây giờ hoặc sử dụng 'lật'. – Sarah

+0

Nhận lỗi, không chắc chắn vị trí xác định vị từ này. tôi nghĩ rằng tôi không thể sử dụng nó trong cùng một dòng như bộ lọc phải không? Tôi muốn chương trình có được một đầu vào và liệt kê tất cả các ước của nó. tôi muốn biết làm thế nào vị ngữ được định nghĩa cho điều này. cảm ơn. – Amjad

2

Vâng, bạn chuyển điều kiện đó thành vị ngữ (hàm trả về Bool) và sử dụng nó để lọc số.

Ví dụ, nếu bạn phải chọn chỉ các số lẻ, bạn có thể sử dụng filter odd [1..n]

+0

Bạn có nghĩa là tôi phải xác định vị từ được sử dụng với bộ lọc và là hàm Int -> Bool được chuyển làm đối số đầu tiên để lọc. làm thế nào chính xác tôi có thể làm điều này? đó là câu hỏi của tôi. ví dụ: làm thế nào để tôi liệt kê tất cả các ước của một số nguyên mà tôi nhập vào. – Amjad

+0

Có, bạn cần một hàm kiểu 'Int -> Bool'. Ví dụ thứ hai của bạn với số chia danh sách số đầu vào không thể hoạt động theo cách này. Bởi vì từ một số duy nhất bạn có được một danh sách các ước số, do đó hàm của bạn sẽ có kiểu 'Int -> [Int]' không giống với 'Int -> Bool'. Trong trường hợp này, có thể 'map' hoặc' concatMap' là những gì bạn muốn. –

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