[英]OCaml error filter list using higher order functions
所以我有這個練習:
filter (fun x -> x = 0) [(1,0);(2,1);(3,0);(4,1)];;
result int list [1;3]
因此,基本上,您必須將x與列表中的第二個數字匹配,如果相同,則使用第一個數字創建新列表。
我的解決方案,但錯了
let rec filter f = function
| []->[]
| x::l -> if f=snd x then fst x :: filter f l else [];;
我想嘗試代碼時收到以下錯誤:
錯誤:此表達式的類型為
int
但應為int -> bool
類型的表達式int -> bool
我無法重現您報告的問題。 這是我嘗試輸入代碼時看到的內容:
$ ocaml
OCaml version 4.02.1
# let rec filter f = function
| []->[]
| x::l -> if f=snd x then fst x :: filter f l else [] ;;
val filter : 'a -> ('b * 'a) list -> 'b list = <fun>
# filter 0 [(1,0); (2,1); (3,0)];;
- : int list = [1]
沒有錯誤,但是得到了錯誤的答案。 這就是我期望查看您的代碼的原因。
您得到的錯誤是說編譯器在某個地方期望一個int -> bool
函數,但是您給它一個int
。 出現此錯誤的原因是因為您有一個等式( f = snd x
),其中f
的類型為snd x
int -> bool
而snd x
的類型為int
。 賦予相等性的兩個參數必須具有相同的類型。 相反,您想要做的只是將f
應用於x
的第二個元素的結果,例如:
let rec filter f = function
| []->[]
| x::l -> if f (snd x) then fst x :: filter f l else [];;
也就是說,我建議您使用模式匹配而不是fst
和snd
,例如:
let rec filter f l =
match l with
| [] -> []
| (x,y)::l -> if f y then x :: filter f l else filter f l
請注意, fy
將返回bool類型的內容,然后它將確定采用哪個分支。
Matts的答案完全正確。 最好重用現有功能,而不是從頭開始編寫特殊代碼:
[(1,0);(2,1);(3,0);(4,1)]
|> List.filter (fun (_, x) -> x = 0)
|> List.map fst
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.