F#match的强大和List.tail方法的真实含义
2012-04-11 09:36 java线程例子 阅读(416) 评论(0) 编辑 收藏 举报这几天在学习F#,感觉F#在很多方面确实比较简洁而强大,其match表达式就是其中之一,match with 跟C#的Switch类似,但功能上要强大很多,下面是例子:
let print_any x = printfn "%A" x let rec findSequence l = match l with | [a; b; c; d] -> //a,b,c,d其实只是占位符号,表示4个元素的数组,当然,如果匹配到,你可以通过abcd访问到这4个元素 printfn "Last 4 numbers in the list were %i %i %i %i" a b c d | 1 :: 2 :: 3 :: tail -> //形如1,2,3,任意元素 printfn "Found sequence 1, 2, 3 within the list" findSequence tail | head :: mid ::tail -> //匹配3个元素的元组,因为每个数组最后都隐含一个空,所以只要是数组元素大于2,都可匹配到. printfn "xxxx:%A %A %A" head mid tail findSequence tail | head :: tail -> //同上,匹配一个二元组。 printfn "xxxx:%A %A" head tail | [] -> () let testSequence = [1; 2; 3;4; 5; 6; 7; 8; 9; 8; 7; 6; 5; 4; 3; 2; 1] let b1 = findSequence testSequence print_any b1
match with确实很强大,特别是在集合做分支的时候.但这里面有个误导,就是上面的head,tail并不是我们所理解的链表中的头和位,在这里其实只是一个占位符号.当然这里还是标示符号命名造成的,而List的head和tail就有误导人的之嫌:
let listOfList = [[2; 3; 5]; [7; 11; 13]; [17; 19; 23; 29]] let rec concatList l = match l with | head :: tail -> head @ (concatList tail) | [] -> [] let rec concatListOrg l = if List.isEmpty l = false then let head = List.head l in let tail = List.tail l in head @ (concatListOrg tail) else [] let print_any x = printfn "%A" x let primes = concatList listOfList print_any primes
head指向的是序列的头元素,而tail指向的是除了head元素之外的剩下序列.当然,这个也没有对何错,只是容易让人误解.我们在学链表的时候,head,tail一般都指首尾元素.如果用remain剩下来表达tail所指也有不好.当然大家弄明白了也就无所谓了.