精华内容
下载资源
问答
  • 偏函数

    千次阅读 2019-02-28 17:38:52
    所谓偏函数,就是固定一个函数的一个或者多个参数,返回一个新的函数,这个函数用于接受剩余的参数。听起来可能有点迷糊,没事,咱们慢慢来~ 首先,我们来看一个简单的例子,下面只是一个普普通通的函数, ...
    所谓偏函数,就是固定一个函数的一个或者多个参数,返回一个新的函数,这个函数用于接受剩余的参数。听起来可能有点迷糊,没事,咱们慢慢来~ 
    首先,我们来看一个简单的例子,下面只是一个普普通通的函数,
    
    function add(a,b){
        return a + b;
    }
    console.log(add(1,2));//结果3
    console.log(add(1,3));//结果4
    console.log(add(1,4));//结果5
    console.log(add(1,5));//结果6
    console.log(add(1,6));//结果7
    console.log(add(1,7));//结果8
    1
    2
    3
    4
    5
    6
    7
    8
    9
    不知道大家有没有发现,往add()传入的第一个参数全都是相同的,也就是1,对于这样相同的参数,我们已经重复输入了6次。参数少的情况还好办,那参数多的时候就非常不方便了,请往下看:
    
    function add(a,b,c,d,e){
        return a + b + c + d + e;
    }
    console.log(add(1,2,3,4,5));
    console.log(add(1,2,3,1,2));
    console.log(add(1,2,3,3,5));
    console.log(add(1,2,3,2,11));
    console.log(add(1,2,3,3,8));
    console.log(add(1,2,3,7,5));
    1
    2
    3
    4
    5
    6
    7
    8
    9
    那么有没有什么办法可以让我们对于相同的参数,只输入一次(也就是把他们固定住),对于其他的参数在调用的时候输入就行了呢?答案是肯定的(不然接下来我还怎么扯淡~),它就是本文的主角–偏函数!
    
    揭开偏函数的神秘面纱 
    就像上面我所说的一样,偏函数是固定一个函数的一个或多个参数,然后返回一个新函数,所以我们可以定义一个函数,把它命名为partial,这个函数就相当于一个工厂,需要接受一个入参函数,这个工厂用来生产偏函数,按照这个思路,可以写出大概的构架如下:
    //入参函数
    function add(a,b){
        return a + b;
    }
    //生产偏函数的工厂,接受一个入参函数,返回一个新的函数,用于接受剩余的参数
    function partial(fn,a){
        return function(b){
            return fn(a,b);
        }
    }
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    既然生产偏函数的工厂返回了一个新的函数,所以就用一个变量去接受这个函数,然后在调用该函数的时候再把剩下的参数传入即可。具体代码如下:
    
    //入参函数
    function add(a,b){
        return a + b;
    }
    //生产偏函数的工厂
    function partial(fn,a){
        return function(b){
            return fn(a,b);
        }
    }
    var parAdd = partial(add,1);//变量parAdd接受返回的新函数
    console.log(parAdd(2));//在调用的时候传入剩余的参数
    console.log(parAdd(3));//在调用的时候传入剩余的参数
    console.log(parAdd(4));//在调用的时候传入剩余的参数
    console.log(parAdd(5));//在调用的时候传入剩余的参数
    这里运行的步骤是 首先当 2 传进去的时候 首先 add = 2传进去了 传给了 return function(b) 这个函数的形参 b 这个时候 b==2了 把 a=1 b =2 传进了函数 fn中 也就是 add中 第一次得出结果是3 以此类推
    原文:https://blog.csdn.net/qq_42129063/article/details/81874314 
    
    展开全文
  • scala的偏函数

    2021-01-07 04:40:50
    偏函数 偏函数可以提供了简洁的语法,可以简化函数的定义。配合集合的函数式编程,可以让代码更加优雅。 定义 偏函数被包在花括号内没有match的一组case语句是一个偏函数 偏函数是PartialFunction[A, B]的一个实例 A...
  • 所谓偏函数即是规定了固定参数的函数,在函数式编程中我们经常可以用到,这里我们就来看一下Python使用functools模块中的partial函数生成偏函数的方法
  • 偏函数与偏应用函数

    千次阅读 2017-05-07 07:37:54
    偏函数 偏应用函数偏函数val isEven: PartialFunction[Int, String] = { case x if x % 2 == 1 => " is even" }val isOdd: PartialFunction[Int, String] = { case x if x % 2 == 0 => " is odd" }(1 to 10) map ...

    偏函数

    val isEven: PartialFunction[Int, String] = {
      case x if x % 2 == 1 => " is even"
    }
    
    val isOdd: PartialFunction[Int, String] = {
      case x if x % 2 == 0 => " is odd"
    }
    
    (1 to 10) map (isEven orElse isOdd) foreach println
    
    try {
      (1 to 10) map isEven foreach println
    } catch {
    case _: MatchError => "Error!"
    }
    
    isEven.isDefineAt(2) //false
    isOdd.isDefineAt(2) //true
    
    val printResult: PartialFunction[String, Unit] = {
      case x: String => println("result is: " + x)
    }
    
    (isEven andThen printResult)(3) //result is: 3 is even

    偏函数是一个单参数函数,且并未对该类型的所有值都实现相应处理逻辑。偏函数的字面量语法由包围在花括号中的一个或多个case语句构成。这与普通函数字面量不同,普通函数字面量可以使用花括号,也可以使用圆括号。

    偏函数之所以“偏”,在就在于其只能处理那些能与至少一个case语句匹配的输入,而不能处理所有可能的输入。

    如果偏函数被调用,而函数的输入却与所有case语句都不匹配,系统就会抛出一个MatchError的运行时错误。可以使用isDefinedAt方法测试特定输入是否与偏函数匹配,这样偏函数就可以避免抛出MatchError错误了。

    将多个偏函数连接成一个偏函数的方法有两种:
    1. 使用orElse关键字,此时如果第一个偏函数不匹配就会尝试匹配下一个偏函数。
    2. 使用andThen关键字,此时会将第一个偏函数的执行结果传递给下一个偏函数作为参数并执行第二个偏函数。


    偏应用函数

    def cat(s1: String)(s2: String): String = s1 + s2
    
    val hello = cat("hello ") _ //定义一个偏应用函数

    偏应用函数是一个表达式,包含函数的部分而非全部参数列表。返回值是一个新函数,此函数携带剩下的参数列表。

    对于拥有多个参数列表的函数而言,如果你希望忽略其中一个或多个参数列表,可以通过定义一个新函数来实现。也就是说,你给出了部分所需要的参数。为了避免潜在的表达式歧义,Scala要求在后面加上下划线,用来告诉编译器你的真实目的。注意,这个特性只对函数的多个参数列表有效,对一个参数列表中的多个参数的情况并不适用。


    参考《Scala程序设计》第二版

    展开全文
  • Scala 偏函数和偏应用函数

    千次阅读 2015-07-16 16:54:25
    偏函数 偏函数是指仅定义了输入参数的子集的函数,如下图: 这个图显示的一个偏函数:f : X -> Y,该函数仅定义了输入参数X的子集1和3,没有包含2。 在Scala中的偏函数是通过特质PartialFunction[-A, +B]来定义的...

    偏函数

    偏函数是指仅定义了输入参数的子集的函数,如下图:



    这个图显示的一个偏函数:f : X -> Y,该函数仅定义了输入参数X的子集1和3,没有包含2。

    在Scala中的偏函数是通过特质PartialFunction[-A, +B]来定义的,查看PatialFunction特质的API,可看到PatialFunction定义如下:

    trait PartialFunction[-A, +B] extends (A) ⇒ B
    可以看出偏函数:

    1)是一个将类型A转为类型B的特质。

    2)接受A类型的输入参数,返回值为B类型。

    3)是一个一元函数,“-”符号作用于类型表示逆变,-A表明输入参数为A类型或A类型的父类,也就是说输入的参数应为A的子集,具有“部分”的含义。

    4)函数有可能“偏”离了A定义域(Type)类型,而成为值域B, +表明可以是B或B的子类,具有“全部”的含义。

    偏函数和其它函数一样,也定义了apply方法,apply方法会从匹配到的模式计算函数值。也添加了另外一个方法“def isDefinedAt(a: A):Boolean”,isDefinedAt方法决定了该方法的参数是否在给定的偏函数的定义域内,如果返回结果为true,表示在,否则不在,最好在。见下例,signal引用了一个偏函数:

    val signal: PartialFunction[Int, Int] = {
        case x if x > 1 => 1
        case x if x < -1 => -1
    }
    这个signal所引用的函数除了0值外,对所有整数都定义了相应的操作。 调用signal(0) 会抛出异常,因此使用前最好先signal.isDefinedAt(0)判断一下。
    偏函数主要用于这样一种场景:对某些值现在还无法给出具体的操作(即需求还不明朗),也有可能存在几种处理方式(视乎具体的需求),我们可以先对需求明确的部分进行定义,比如上述除了0外的所有整数域,然后根据具体情况补充对其他域的定义,比如 :

    val composed_signal: PartialFunction[Int,Int] = signal.orElse{
      case 0 => 0
    }
    
    composed_signal(0)  // 返回 0 
    
    或者对定义域进行一定的偏移(假如需求做了变更,  1 为无效的点)

    val new_signal: Function1[Int, Int] = signal.compose{
      case x => x  - 1
    }
    
    <pre name="code" class="html">new_signal(1)  // throw exception
    new_signal(0)   // 返回 -1 
    new_signal(2)  // 返回 1
     还可以用andThen将两个相关的偏函数串接起来 
    

    val another_signal: PartialFunction[Int, Int] = {
       case 0 =>  0
       case x if x > 0 => x - 1 
       case x if x < 0 => x + 1
    }
    
    <span style="color: rgb(51, 51, 51); font-family: 'Microsoft YaHei', Verdana, sans-serif, 宋体; font-size: 12.5px; line-height: 22.5px;">val then_signal =  another_signal andThen  signal</span>
    

    这里的then_signal 剔除了-1, 0, 1三个点的定义。


    偏应用函数

    偏应用函数是指在调用函数时,有意缺少部分参数的函数。

    以下为摘自网上的文章:

    Scala里,当你调用函数,传入任何需要的参数,你就是在把函数应用到参数上。如,给定下列函数: 

    1. scala> def sum(a: Int, b: Int, c: Int) = a + b + c  
    2. sum: (Int,Int,Int)Int  
    你就可以把函数sum应用到参数1,2和3上,如下:
    
    
    1. scala> sum(123)  
    2. res12: Int = 6 
    偏应用函数是一种表达式,你不需要提供函数需要的所有参数。代之以仅提供部分,或不提供所需参数。比如,要创建不提供任何三个所需参数的调用sum的偏应用表达式,只要在“sum”之后放一个下划线即可。然后可以把得到的函数存入变量。举例如下:
    
    
    1. scala> val a = sum _  
    2. a: (Int, Int, Int) => Int = < function>  
    有了这个代码,Scala编译器以偏应用函数表达式,sum _,实例化一个带三个缺失整数参数的函数值,并把这个新的函数值的索引赋给变量a。当你把这个新函数值应用于三个参数之上时,它就转回头调用sum,并传入这三个参数:
    
    
    1. scala> a(123)  
    2. res13: Int = 6 
    实际发生的事情是这样的:名为a的变量指向一个函数值对象。这个函数值是由Scala编译器依照偏应用函数表达式sum _,自动产生的类的一个实例。编译器产生的类有一个apply方法带三个参数。产生的类扩展了特质Function3,定义了三个参数的apply方法。之所以带三个参数是因为sum _表达式缺少的参数数量为三。Scala编译器把表达式a(1,2,3)翻译成对函数值的apply方法的调用,传入三个参数1,2,3。因此a(1,2,3)是下列代码的短格式:
     
    1. scala> a.apply(123)  
    2. res14: Int = 6 
    Scala编译器根据表达式sum _自动产生的类里的apply方法,简单地把这三个缺失的参数前转到sum,并返回结果。本例中apply调用了sum(1,2,3),并返回sum返回的,6。

     

    这种一个下划线代表全部参数列表的表达式的另一种用途,就是把它当作转换def为函数值的方式。例如,如果你有一个本地函数,如sum(a: Int, b: Int, c: Int): Int,你可以把它“包装”在apply方法具有同样的参数列表和结果类型的函数值中。当你把这个函数值应用到某些参数上时,它依次把sum应用到同样的参数,并返回结果。尽管不能把方法或嵌套函数赋值给变量,或当作参数传递给其它方法,但是如果你把方法或嵌套函数通过在名称后面加一个下划线的方式包装在函数值中,就可以做到了。

    现在,尽管sum _确实是一个偏应用函数,或许对你来说为什么这么称呼并不是很明显。这个名字源自于函数未被应用于它所有的参数。在sum _的例子里,它没有应用于任何参数。不过还可以通过提供某些但不是全部需要的参数表达一个偏应用函数。举例如下: 

    1. scala> val b = sum(1, _: Int, 3)  
    2. b: (Int) => Int = < function> 
    这个例子里,你提供了第一个和最后一个参数给sum,但中间参数缺失。因为仅有一个参数缺失,Scala编译器会产生一个新的函数类,其apply方法带一个参数。在使用一个参数调用的时候,这个产生的函数的apply方法调用sum,传入1,传递给函数的参数,还有3。如下:
     
    1. scala> b(2)  
    2. res15: Int = 6 
    这个例子里,b.apply调用了sum(1,2,3)。

     

    1. scala> b(5)  
    2. res16: Int = 9 
    这个例子里,b.apply调用了sum(1,5,3)。
    
    为什么要使用尾下划线?

     

    Scala的偏应用函数语法凸显了Scala与经典函数式语言如Haskell或ML之间,设计折中的差异。在经典函数式语言中,偏应用函数被当作普通的例子。更进一步,这些语言拥有非常严格的静态类型系统能够暴露出你在偏应用中可能犯的所有错误。Scala与指令式语言如Java关系近得多,在这些语言中没有应用所有参数的方法会被认为是错误的。进一步说,子类型推断的面向对象的传统和全局的根类型接受一些被经典函数式语言认为是错误的程序。

    举例来说,如果你误以为List的drop(n: Int)方法如tail(),那么你会忘记你需要传递给drop一个数字。你或许会写,“println(drop)”。如果Scala采用偏应用函数在哪儿都OK的经典函数式传统,这个代码就将通过类型检查。然而,你会惊奇地发现这个println语句打印的输出将总是< function>!可能发生的事情是表达式drop将被看作是函数对象。因为println可以带任何类型对象,这个代码可以编译通过,但产生出乎意料的结果。

    为了避免这样的情况,Scala需要你指定显示省略的函数参数,尽管标志简单到仅用一个‘_’。Scala允许你仅在需要函数类型的地方才能省略这个仅用的_。



    展开全文
  •  我感觉很多人都对函数加里化(Currying)和偏函数应用(Partial Application)之间的区别搞不清楚,尤其是在相似的上下文环境中它们同时出现的时候。  偏函数解决这样的问题:如果我们有函数是多个参数的,...
  • js代码-函数式编程-偏函数
  • 主要介绍了Python嵌套函数,作用域与偏函数用法,结合实例形式分析了Python嵌套函数,作用域与偏函数的功能、定义与相关使用方法,需要的朋友可以参考下
  • 主要介绍了Python中偏函数用法,结合实例形式分析了Python基于functools模块创建和使用偏函数的相关操作技巧与注意事项,需要的朋友可以参考下
  • python偏函数.pdf

    2021-09-14 13:30:25
    python偏函数.pdf
  • Python 偏函数.pdf

    2021-08-10 16:40:02
    Python 偏函数.pdf
  • 主要介绍了python中偏函数partial用法,实例分析了偏函数partial的功能、定义及使用方法,需要的朋友可以参考下
  • Python的functools模块提供了很多有用的功能,其中一个就是偏函数(Partial function)。要注意,这里的偏函数和数学意义上的偏函数不一样。 在介绍函数参数的时候,我们讲到,通过设定参数的默认值,可以降低函数...
  • Javascript函数式编程之偏函数

    千次阅读 2018-08-20 17:10:56
    在上一篇文章中我简单地提及了函数式编程中的纯函数,那么在这篇文章中就来说说偏函数,如果小伙伴们还不知道什么是纯函数或者感兴趣(有时间)的话,可以点击下方的链接~ Javascript函数式编程之纯函数 二、什么...

    一、前言

    在上一篇文章中我简单地提及了函数式编程中的纯函数,那么在这篇文章中就来说说偏函数,如果小伙伴们还不知道什么是纯函数或者感兴趣(有时间)的话,可以点击下方的链接~
    Javascript函数式编程之纯函数

    二、什么是偏函数?

    • 我个人的理解

    所谓偏函数,就是固定一个函数的一个或者多个参数,返回一个新的函数,这个函数用于接受剩余的参数。听起来可能有点迷糊,没事,咱们慢慢来~
    首先,我们来看一个简单的例子,下面只是一个普普通通的函数,

    function add(a,b){
        return a + b;
    }
    console.log(add(1,2));//结果3
    console.log(add(1,3));//结果4
    console.log(add(1,4));//结果5
    console.log(add(1,5));//结果6
    console.log(add(1,6));//结果7
    console.log(add(1,7));//结果8

    不知道大家有没有发现,往add()传入的第一个参数全都是相同的,也就是1,对于这样相同的参数,我们已经重复输入了6次。参数少的情况还好办,那参数多的时候就非常不方便了,请往下看:

    function add(a,b,c,d,e){
        return a + b + c + d + e;
    }
    console.log(add(1,2,3,4,5));
    console.log(add(1,2,3,1,2));
    console.log(add(1,2,3,3,5));
    console.log(add(1,2,3,2,11));
    console.log(add(1,2,3,3,8));
    console.log(add(1,2,3,7,5));

    那么有没有什么办法可以让我们对于相同的参数,只输入一次(也就是把他们固定住),对于其他的参数在调用的时候输入就行了呢?答案是肯定的(不然接下来我还怎么扯淡~),它就是本文的主角–偏函数!

    • 揭开偏函数的神秘面纱
      就像上面我所说的一样,偏函数是固定一个函数的一个或多个参数,然后返回一个新函数,所以我们可以定义一个函数,把它命名为partial,这个函数就相当于一个工厂,需要接受一个入参函数,这个工厂用来生产偏函数,按照这个思路,可以写出大概的构架如下:
    //入参函数
    function add(a,b){
        return a + b;
    }
    //生产偏函数的工厂,接受一个入参函数,返回一个新的函数,用于接受剩余的参数
    function partial(fn,a){
        return function(b){
            return fn(a,b);
        }
    }

    既然生产偏函数的工厂返回了一个新的函数,所以就用一个变量去接受这个函数,然后在调用该函数的时候再把剩下的参数传入即可。具体代码如下:

    //入参函数
    function add(a,b){
        return a + b;
    }
    //生产偏函数的工厂
    function partial(fn,a){
        return function(b){
            return fn(a,b);
        }
    }
    var parAdd = partial(add,1);//变量parAdd接受返回的新函数
    console.log(parAdd(2));//在调用的时候传入剩余的参数
    console.log(parAdd(3));//在调用的时候传入剩余的参数
    console.log(parAdd(4));//在调用的时候传入剩余的参数
    console.log(parAdd(5));//在调用的时候传入剩余的参数

    固定多个参数的情况:

    function add(a,b,c,d,e){
        return a + b + c + d + e;
    }
    function partial(fn,a,b,c){
        return function(d,e){
            return fn(a,b,c,d,e);
        }
    }
    var parAdd = partial(add,1,2,3);
    console.log(parAdd(2,1));
    console.log(parAdd(3,7));
    console.log(parAdd(4,8));
    • 偏函数的原理

    从上面的演示中我们可以看出,偏函数应用了闭包的原理。

    三、偏函数的简单应用

    • Function.prototype.bind()

    这是MDN对于bind()的描述:bind() 函数会创建一个新函数(称为绑定函数),新函数与被调函数(绑定函数的目标函数)具有相同的函数体(在 ECMAScript 5 规范中内置的call属性)。当新函数被调用时 this 值绑定到 bind() 的第一个参数,该参数不能被重写。绑定函数被调用时,bind() 也接受预设的参数提供给原函数。一个绑定函数也能使用new操作符创建对象:这种行为就像把原函数当成构造器。提供的 this 值被忽略,同时调用时的参数被提供给模拟函数。
    不知道大家有木有发现在上面的描述中,出现了几个很重要的表述,创建一个新函数具有相同的函数体调用时的参数被提供给模拟函数,哈哈,这不正和我刚刚说的生产偏函数工厂相似吗。所以对于上面的应用,我们还可以这样改写:

    function add(a,b){
        return a + b;
    }
    var obj = {};
    obj.parAdd = add.bind(obj,1);
    console.log(obj.parAdd(2));//结果3

    嘿嘿,是不是很神奇,小伙伴们也可以自己去尝试哦~

    四、结语

    好了,以上就是今天偏函数的全部内容了,有什么遗漏和错误的地方希望大家多多指正,感谢阅读!

    展开全文
  • 主要介绍了JavaScript偏函数与柯里化,结合实例形式详细分析了JavaScript偏函数与柯里化的概念、原理、定义、使用方法及相关操作注意事项,需要的朋友可以参考下
  • scala 偏函数

    千次阅读 2015-12-12 20:13:11
    Scala 偏函数介绍。
  • 摘要:python的设计核心原则就是简洁——在这种原则的指导下,诞生了lambda表达式和偏函数:二者都让函数调用变得简洁。本文主要为你介绍偏函数的应用。 1.为什么要使用偏函数 如果我们定义了一个函数,比如说将四...
  • Python——偏函数

    2018-08-17 18:29:00
    Python的functools模块提供了很多有用的功能,其中一个就是偏函数(Partial function)。 偏函数是将所要承载的函数作为 partial() 函数的第一个参数,原函数的各个参数依次作为 partial() 函数的后续参数,...
  • Scala偏函数与部分函数

    千次阅读 2015-08-02 13:39:05
    前几天用到了偏函数,然后自己参阅一些相关资料,最后把Scala的部分函数和偏函数整理了一下,和大家分享。
  • python的偏函数

    2017-10-29 21:18:53
    Python的functools模块提供了很多有用的功能,其中一个就是偏函数(Partial function)。要注意,这里的偏函数和数学意义上的偏函数不一样。 在介绍函数参数的时候,我们讲到,通过设定参数的默认值,可以降低...
  • Python中的偏函数.pdf

    2021-08-10 16:57:19
    Python中的偏函数.pdf
  • python 偏函数装饰器.pdf
  • js代码-柯里化 偏函数

    2021-07-14 21:49:42
    js代码-柯里化 偏函数
  • Python的functools模块中有一种函数叫“偏函数”,自从接触它以来,发现确实是一个很有用且简单的函数,相信你看完这篇文章,你也有相见恨晚的感觉。 我们都知道,函数入参可以设置默认值来简化函数调用,而偏函数的...
  • js代码-011 节流防抖,函数珂里化,偏函数
  • Python的functools模块提供了很多有用的功能,其中一个就是偏函数(Partial function)。 要注意,这里的偏函数和数学意义上的偏函数不一样。 在介绍函数参数的时候,我们讲到,通过设定参数的默认值,可以降低函数...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 139,616
精华内容 55,846
关键字:

偏函数