F#注解

  不要问我为啥要学F#——因为气质摆在那里

  标注:以下内容均来自 anderslly F#系列

  1、类型推演

    let square x = x * x

    //接受一个某类型参数的quare函数返回一个这个参数的平方,因为支持参数*参数的类型有很多;比如int,byte,uint64,double等,而F#会默认为int类型

    //这就类似与js当中var 不同的是,在js当中,函数返回一个数值需要用return关键字 而F#不需要

  2、规定参数的类型(类似于C#的形参 也叫类型注解)

    let concat (x : string) y = x + y;;

    //一个函数接受一个x的参数,这个参数必须为string类型(这里的冒号":"的作用就是起到了约束作用)以及一个参数y

    //这里有同学以为y没有约束类型,那应该是什么类型都可以

    //实际上是由于因为x类型是string,返回的值又是x + y 用了"+"操作,所以类型必须相同,则y也是string(用vs的同学可以按 alt+enter检查)

  3、输出打印

    printfn "N^2 = %A" squares

    //打印信息 这里的%A是匹配任何类型的参数(也就是空格后面的squares) 注:参数的输入 必须要已空格隔开,否则会报错

    这里有几个输出的类型要注明:%d,%f,%s分别是int、float、string的占位符

  4、值,变量的不可变性

    跟C#不同,F#中的变量都是不可变性的,换句话说 就是固定不变的,自然同时就具备了类型安全这个优良的特点,如果你一定要改变这个值,也是可以的!

    用mutable改变这个值(注意:这个改动值,不是寻常我们C#,JS中的改变变量的值,而是重新创建了一个新的变量,这一点上是不是跟我们C#中的string有点类似呢 (^_^))

    然后用左箭头操作符 <- 修改变量的值

    let mutable x = "the original value.";;

    printfn "x‘s value is ‘%s‘" x;;    //x‘s value is ‘the original value‘.

    x <- "the new one.";;

    printfn "x‘s value is now ‘%s‘" x;;  //x‘s value is now ‘x‘s value is the original value‘

  5、引用值

    引用值是另一种表示可修改数据的方式。但它不是将变量存储在堆栈(stack),引用值其实是一个指向存储在堆(heap)上的变量的指针(pointer)。在F#中使用可修改的值时会有些限制(比如不可以在内部lambda表达式中使用)。而ref对象则可被安全地传递,因为它们是不可变的record值(只是它有一个可修改的字段)。原话引自——【F# 20分钟快速上手(二)

    使用引用值时,用“:=”赋一个新值,使用“!”进行解引用。

    let refCell = ref 42;;     //refCell = 42

    refCell := -1;;  //改变引用值

    !refCell;;  //解析引用值 显示-1

  6、模块(Modules)

    这个就跟C#的using引用程序集是一个道理了 直接看例子  

    module ProgramSettings =
      let version = "1.0.0.0"    
      let debugMode = ref false

    module MyProgram =
          do printfn "Version %s" ProgramSettings.version  
          open ProgramSettings
          debugMode := true

  7、元组(Tuple)

    表示值的有序集合 也是跟C#中的元组有近似相同;用来传递多个或一组值

    定义一个元组,只要将一组值用逗号分割

    let tuple = (1, false, "text");;

    let getNumberInfo (x : int) = (x, x.ToString(), x * x);;  //定义个接受int的变量x 函数返回三个变量(int,string,int)

    函数可以接受元素为参数,自然C#也是可以的

    let printBlogInfo (owner, title, url) = printfn "%s‘s blog [%s] is online at ‘%s‘" owner title url;;

    let myBlog = ("Chris", "Completely Unique View", "http://blogs.msdn.com/chrsmith");;

    printBlogInfo myBlog;;  //输出 Chris‘s blog [Completely Unique View] is online at ‘http://blogs.msdn.com/chrsmith‘

  8、函数科里化(Function Currying)

    F#中可以只接受某函数的参数 进而将参数传递给另一个新的函数

    let addThree x y z = x + y + z;;  //函数addThree接受三个参数  1

    let addTwo x y = addThree 10 x y;;  //函数addTwo接受两个参数  2

    addTwo 1 1;;  //调用addTwo传1,1两个参数—>由于函数2返回一个新的函数addThree 并接受一个参数10,和前一个函数的两个参数的值

  9、Union类型 

    没有自己的一些见解,直接点击原文

  10、模式匹配

    看起来想swicth case模式

    let listLength aList =
          match aList with
          | [] -> 0
          | a :: [] -> 1
          | a :: b :: [] -> 2
          | a :: b :: c :: [] -> 3
          | _ -> failwith "List is too big!"   //竖线 | 表示各种case ->是lambda表达 表示输出  a::[] 意思是说 a 在 [] 之前的元素(这是空的list集合)

    let isOdd x =
          match x with
          | _ when x % 2 = 0 -> false
          | _ when x % 2 = 1 -> true   //下划线 _ 是匹配任意值

    也可以动态匹配

    let getType (x : obj) =
          match x with
          | :? string -> "x is a string"
          | :? int -> "x is a int"
          | :? System.Exception -> "x is an exception"
          | :? _ -> "invalid type"     // 这里博主没有将:? 符号的意思说明 我就理解为表面意思 :匹配这个值 ?是可以是任何类型的 跟输入的类型是一样的 比如输入"a" 就是string;11 就是int

  11、Forward Pipe operator(|>)

    简单的理解就是一个函数A接受一个参数并返回一个值,然后把这个值又传递给另一个函数B,函数B得到这个参数并返回一个值(类型可能不同),进入接着往下传递

    用C#的写法就是

    Int32 result = Func3(Func2(Fun1(A)))......

    我们来看看F#的写法

    let square x         = x * x
    let toStr (x : int)  = x.ToString()
    let rev   (x : string) = new String(Array.rev (x.ToCharArray()))

    let result = rev (toStr (square 32))  //调用

    上面看起来就跟C#的一样直白,好理解,那我们接着用操作符 |> 写一遍

    let result = 32 |> square |> toStr |> rev

    可以看出这样极大的简化了我们代码,并且更说明了Forward Pipe Operator的含义

  12、集合(Collection:Seq,List,Array)

    F#表示集合的有三种,Seq;List; Array

    这里每个集合类型都有很多方法,大家可以用VS的智能提示了解(吐槽一下:不知道我的vs是怎么滴,一定得手动按ctrl+j才行 不能想C#中实时出现提示的)这里我记录几个常用的

    iter。“iter”函数遍历集合的每一项。 跟foreach遍历一样

    List.iter (fun i -> printfn "Has element %d" i) [1 .. 10]  从集合[1..10](这个是集合的元素从1到10)循环遍历输出Has element 1 2 3...

    map map函数基于一个指定的函数对集合的值进行转换

    Array.map (fun (i : int) -> i.ToString()) [| 1 .. 10 |]  //([|1..10 |] 前后加竖线是说明此几何为整数数组)    次数是由原来的整数集合变为一个字符串集合

    fold。“fold”函数接受一个集合,并将集合的值折叠为单个的值。像iter和map一样,它接受一个函数,将其应用于集合的每个元素,但它还接受另一个“accumulator”参数。fold函数基于上一次运算不断地累积  accumulator参数的值  注:是不是跟C#的ForEach(Func)很想呢

    Seq.fold (fun acc i -> i + acc) 10 { 1 .. 10 }

  13、可选值(Option Values)

    F#中的“可选类型(option type)”有两种状态:“Some”和“None”。在下面的记录类型Person中,中间的字段可能有值,也可能没有值

    type Person = { First : string; MI : string option; Last : string }
    let billg    = {First = "Bill";  MI = Some("H"); Last = "Gates" }
    let chrsmith = {First = "Chris"; MI = None;      Last = "Smith" }

  14、延迟求值 (LazyValue)

    延迟初始化表示一些值,它们在需要时才进行计算。F#拥有延迟求值特性。看下面的例子,“x”是一个整数,当对其进行求值时会打印“Computed”。

    let x = lazy (printfn "Computed."; 42);;  //初始化值42 但是被延迟了

    let listOfX = [x; x; x];;    

    x.Force();;  //直到使用Force 才会初始化x的值

时间: 2024-08-24 11:47:07

F#注解的相关文章

过分过分进货价获国家

http://f.dangdang.com/group/24554/3491082/http://f.dangdang.com/group/24554/3491087/http://f.dangdang.com/group/24554/3491094/http://f.dangdang.com/group/24554/3491099/http://f.dangdang.com/group/24554/3491105/http://f.dangdang.com/group/24554/349111

我们找个地方看好戏

http://v.qq.com/page/f/y/4/m041433ssun.html http://v.qq.com/page/f/y/4/m041433ssun.html http://v.qq.com/page/f/y/4/m04143o3lhg.html http://v.qq.com/page/f/y/4/m04144675h3.html http://v.qq.com/page/f/y/4/m04144k1k1j.html http://v.qq.com/page/f/y/4/m04

spring mvc 方法注解拦截器

应用场景,在方法级别对本次调用进行鉴权,如api接口中有个用户唯一标示accessToken,对于有accessToken的每次请求可以在方法加一个拦截器,获得本次请求的用户,存放到request或者session域. python中,之前在python flask中可以使用装饰器来对方法进行预处理,进行权限处理 先看一个实例,使用@access_required拦截: @api.route('/post_apply') @access_required def apply():     "&q

Java高级之注解、反射

Java的注解.反射等机制的产生,让动态代理成为可能,一般通过全限定名+类名,找到类,可以invoke它的构造方法以及其他方法,可以获取它的参数(Field)名称和值. 注解一般用在代码的注释上.代码审查上(有没有按标准写,比如inspect).代码注入(hook,asbectj),需要考虑的是,在何时注入(编译期还运行期) 反射一般用在动态将json和Object互相转化,执行相关底层代码,比如设置某个类的Accessible为false,防止别人hook修改 例:阿里的FastJson解析:

Java 注解

Annotation(注解)就是Java提供了一种元程序中的元素关联任何信息和着任何元数据(metadata)的途径和方法.Annotion(注解)是一个接口,程序可以通过反射来获取指定程序元素的Annotion对象,然后通过Annotion对象来获取注解里面的元数据. Annotation能被用来为某个程序元素(类.方法.成员变量等)关联任何的信息.需要注意的是,这里存在着一个基本的规则:Annotation不能影响程序代码的执行,无论增加.删除 Annotation,代码都始终如一的执行.另

Java注解项目实战即模拟Hibenernate生成sql语句

整理了近期学习java注解的部分代码 ,借助java注解模拟Hibenernate ORM模型建立对象与sql语句的映射 Table 注解的创建 package com.imooc.test; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.

Java的注解

1.什么是注解    语法: @注解名称    注解的作用:代替配置文件,如xml    servlet3.0中,就可以用写web.xml,可以使用注解来配置    注解是由框架来读取的,是给程序看的,而注释是给人看的 2.注解的使用    *定义注解:框架的工作    *使用注解:程序员的工作    *读取注解:框架的工作 3.定义注解类    class A{}//定义类    interface B{}//定义接口    enum C//定义枚举    @interface MyAnno1

01 start.s汇编代码注解(RTEMS)

start.s 文件中汇编代码的注解(RTEMS) 作者:zhousm    2016年01月01日 处理器:S3C2440  ARM9 操作系统:RTEMS-4.10.2 源文件路径:rtems-4.10.2/c/src/lib/libbsp/arm/gp32/start/start.S 当处理器跳转到指定的地址开始执行时,即从该文件开始执行: 1 /* Some standard definitions...*/ 2 .equ PSR_MODE_USR, 0x10 3 .equ PSR_MO

(6) 如何用Apache POI操作Excel文件-----POI-3.10的一个和注解(comment)相关的另外一个bug

如果POI-3.10往一个工作表(sheet)里面插入数据的话,需要注意了,其有一个不太被容易发现的bug. 被插入的工作表(sheet)里面的单元格没有包含任何的注解(comment)的时候,插入一行数据,不会有任何问题.但是如果被插入的工作表(sheet)里面的单元格只要包含任何的注解(comment)的时候,这个时候插入一行数据的时候,就会破坏这个文件.当程序执行完后,如果打开被插入数据的Excel文件,我们将会发现,其会弹出下面的对话框. 程序代码如下, package com.tibc