"partial function" 在函数式编程中到底是什么意思?
What exactly is meant by "partial function" in functional programming?
根据我的理解,部分函数是我们通过将比预期更少的参数传递给函数而得到的函数。例如,如果这在 Python:
中直接有效
>>> def add(x,y):
... return x+y
...
>>> new_function = add(1)
>>> new_function(2)
3
在上面的代码片段中,new_function
是部分函数。但是,根据Haskell Wiki,偏函数的定义是
A partial function is a function that is not defined for all possible arguments of the specified type.
所以,我的问题是:"partial function" 到底是什么意思?
你在这里混淆了两个概念。 A partially applied function [haskell-wiki] with a partial function [haskell-wiki].
部分应用的函数是:
Partial application in Haskell involves passing less than the full number of arguments to a function that takes multiple arguments.
而偏函数确实是非全函数:
A partial function is a function that is not defined for all possible arguments of the specified type.
部分函数(在函数式编程和数学的上下文中)正是 wiki 所说的:未为其所有可能参数定义的函数。在编程的上下文中,我们通常将 "not defined" 解释为几件事之一,包括未定义的行为、异常或非终止。
部分函数的一个例子是整数除法,如果除数为 0 则它没有定义(在 Haskell 中它会抛出错误)。
in above snippet new_function is partial function.
该代码只会在 Python 中导致错误,但如果它按您的预期工作,它将是一个完整的(意味着不是部分的)函数。
正如评论员已经指出的那样,您很可能会想到它是一个部分应用的函数。
答案说明一切,我将在每种语言中添加一个示例:
def add(x,y):
return x+y
f = add(1)
print(f(3))
f = add(1)
TypeError: add() missing 1 required positional argument: 'y'
这既不是部分函数也不是柯里化函数,这只是一个您没有给出所有参数的函数 .
python 中的柯里化函数应该是这样的:
partialAdd= lambda x: lambda y: x + y
plusOne = partialAdd(1)
print(plusOne(3))
4
并在 haskell 中:
plus :: Int -> Int -> Int
plus x y = x + y
plusOne = plus 1
plusOne 4
5
python中的部分函数:
def first(ls):
return ls[0]
print(first([2,4,5]))
print(first([]))
output
2
print(first([]))
File "main.py", line 2, in first
return ls[0]
IndexError: list index out of range
并且在 Haskell 中,正如您的 link 出现的那样:
head [1,2,3]
3
head []
*** Exception: Prelude.head: empty list
So what is a total function?
嗯,基本上相反:这是一个适用于该类型的任何输入的函数。这是 python 中的示例:
def addElem(xs, x):
xs.append(x)
return xs
这甚至适用于无限列表,如果你使用一个小技巧:
def infiniList():
count = 0
ls = []
while True:
yield ls
count += 1
ls.append(count)
ls = infiniList()
for i in range(5):
rs = next(ls)
print(rs, addElem(rs,6))
[1, 2, 3, 4]
[1, 2, 3, 4, 5] [1, 2, 3, 4, 5]
Haskell中的等价物:
addElem :: a -> [a] -> [a]
addElem x xs = x : xs
addElem 3 (take 10 [1..])
=> [3,1,2,3,4,5,6,7,8,9,10]
这里的函数不会永远挂起。概念是相同的:对于每个列表,函数都将起作用。
根据我的理解,部分函数是我们通过将比预期更少的参数传递给函数而得到的函数。例如,如果这在 Python:
中直接有效>>> def add(x,y):
... return x+y
...
>>> new_function = add(1)
>>> new_function(2)
3
在上面的代码片段中,new_function
是部分函数。但是,根据Haskell Wiki,偏函数的定义是
A partial function is a function that is not defined for all possible arguments of the specified type.
所以,我的问题是:"partial function" 到底是什么意思?
你在这里混淆了两个概念。 A partially applied function [haskell-wiki] with a partial function [haskell-wiki].
部分应用的函数是:
Partial application in Haskell involves passing less than the full number of arguments to a function that takes multiple arguments.
而偏函数确实是非全函数:
A partial function is a function that is not defined for all possible arguments of the specified type.
部分函数(在函数式编程和数学的上下文中)正是 wiki 所说的:未为其所有可能参数定义的函数。在编程的上下文中,我们通常将 "not defined" 解释为几件事之一,包括未定义的行为、异常或非终止。
部分函数的一个例子是整数除法,如果除数为 0 则它没有定义(在 Haskell 中它会抛出错误)。
in above snippet new_function is partial function.
该代码只会在 Python 中导致错误,但如果它按您的预期工作,它将是一个完整的(意味着不是部分的)函数。
正如评论员已经指出的那样,您很可能会想到它是一个部分应用的函数。
答案说明一切,我将在每种语言中添加一个示例:
def add(x,y):
return x+y
f = add(1)
print(f(3))
f = add(1)
TypeError: add() missing 1 required positional argument: 'y'
这既不是部分函数也不是柯里化函数,这只是一个您没有给出所有参数的函数 .
python 中的柯里化函数应该是这样的:
partialAdd= lambda x: lambda y: x + y
plusOne = partialAdd(1)
print(plusOne(3))
4
并在 haskell 中:
plus :: Int -> Int -> Int
plus x y = x + y
plusOne = plus 1
plusOne 4
5
python中的部分函数:
def first(ls):
return ls[0]
print(first([2,4,5]))
print(first([]))
output
2
print(first([]))
File "main.py", line 2, in first
return ls[0]
IndexError: list index out of range
并且在 Haskell 中,正如您的 link 出现的那样:
head [1,2,3]
3
head []
*** Exception: Prelude.head: empty list
So what is a total function?
嗯,基本上相反:这是一个适用于该类型的任何输入的函数。这是 python 中的示例:
def addElem(xs, x):
xs.append(x)
return xs
这甚至适用于无限列表,如果你使用一个小技巧:
def infiniList():
count = 0
ls = []
while True:
yield ls
count += 1
ls.append(count)
ls = infiniList()
for i in range(5):
rs = next(ls)
print(rs, addElem(rs,6))
[1, 2, 3, 4]
[1, 2, 3, 4, 5] [1, 2, 3, 4, 5]
Haskell中的等价物:
addElem :: a -> [a] -> [a]
addElem x xs = x : xs
addElem 3 (take 10 [1..])
=> [3,1,2,3,4,5,6,7,8,9,10]
这里的函数不会永远挂起。概念是相同的:对于每个列表,函数都将起作用。