def edDistRecursive(a,b):
    #print(a, 'a')
    #print(b,'b')

    if len(a) == 0:
        return len(b)

    if len(b)==0:
        return len(a)



    delta = 1 if a[-1] != b[-1] else 0
    return min(edDistRecursive(a[:-1], b[:-1]) + delta,   edDistRecursive(a[:-1], b)+1,  edDistRecursive(a, b[:-1]) +1)


edDistRecursive('actor','racto')

2

但是,如果我在没有min的情况下运行它,

TypeError: can only concatenate tuple (not "int") to tuple


这是遗传学中的一种算法(近似匹配),用于确定需要多少次编辑才能匹配ab。我以为,如果我不加分钟就运行它,我将能够看到每个函数产生的编辑数量。

编辑:我想我知道输出是一个元组,但我也有些困惑。
如果我删除其他两个功能,则可以简化此功能

def edDistRecursive(a,b):
    #print(a, 'a')
    #print(b,'b')

    if len(a) == 0:
        return len(b)

    if len(b)==0:
        return len(a)



    delta = 1 if a[-1] != b[-1] else 0
    return edDistRecursive(a[:-1], b[:-1]) + delta


edDistRecursive('actor','racto')  returns a value of  5.


为什么可以在此处毫无问题地添加增量?

另一个例子是这样的

def sum(x,y):
    x =3
    y =2

    return x+y, y


(sum(2,3))


即使这样的输出(其输出是元组),对其元素之一的加法运算也没有问题。

在上面的函数中,值delta或+1被添加到一个元组中,这就是引发错误的原因,但是int值并未被添加到整个元组中。实际上,元组的每个元素都包含(函数+整数)。所以当元组本身的元素是(function + int)时,我看不到如何添加到元组。

x,y,z = edDistRecursive('actor','racto')似乎也导致相同的错误。

我认为通过在每个函数((edDistRecursive(a[:-1], b[:-1]) + delta), (edDistRecursive(a[:-1], b)+1), (edDistRecursive(a, b[:-1]) +1))中添加方括号,

Python可以将元组的每个元素都视为function + int,但是我遇到了相同的错误。

有没有办法获得每个函数的值,这是我最初的目标?

最佳答案

如果您考虑在递归的第二到最低级别(请参见下面的编辑)会发生什么,则对edDistRecursive(a[:-1], b[:-1])的递归调用将返回一个整数元组。当程序尝试将delta值(一个int)连接到该元组时,将引发错误。通过使用min,您可以确保返回类型始终相同并与您的实现兼容。

编辑:让我们通过一个示例,以便我们可以更直接地查看正在发生什么。对于此示例,让我们不要使用min,以便我们可以看到问题出在哪里。

为了简化示例,假设我们从

edDistRecursive(['x','k','z'], ['y','e','d'])


在进行递归调用的某个时刻(即在每个return语句中执行第一个递归调用之后),我们将达到

edDistRecursive(['x'], ['y'])


这就是我所说的“最低级别的递归”,但实际上是“倒数第二个级别”,因为我们即将达到基本情况。

所以a = ['x']和b = ['y']。现在,我们进入该函数并检查前两个if:
* len(a)== 0吗?没有。
* len(b)== 0吗?没有。
*计算增量= 1
* return edDistRecursive(a[:-1], b[:-1]) + delta,
  edDistRecursive(a[:-1], b) + 1,
  edDistRecursive(a, b[:-1]) + 1

现在,Python将评估第一个递归调用,因为它必须先这样做,然后才能实际返回内容。

第一个递归调用将是edDistRecursive([], [])。现在让我们看看会发生什么:
* len(a)== 0吗?是,已达到基本情况-返回len(b)= 0

所以现在我们回到上一级,回到之前的return语句:
return 0 + 1, edDistRecursive(a[:-1], b) + 1, edDistRecursive(a, b[:-1]) + 1

edDistRecursive(a[:-1], b)将评估为edDistRecursive([], ['y'])
让我们检查一下该呼叫:
* len(a)== 0吗?是,已达到基本情况-返回len(b)= 1

再次返回到return语句:
return 0 + 1, 1 + 1, edDistRecursive(a, b[:-1])

edDistRecursive(a, b[:-1])将评估为edDistRecursive(['x'], [])
这是在此级别进行评估的最后一个电话:
* len(a)== 0吗?没有。
* len(b)== 0吗?是-返回len(a)= 1

再来看一次return语句,现在可以实际返回它:
return 1, 2, 1 + 1

好的,所以我们进入的递归调用的结果是元组(1, 2, 2)
当它返回到调用它的edDistRecursive(例如edDistRecursive(['x','k'], ['y','e']))时,即引发了异常:

return (1, 2, 2) + delta, edDistRecursive(a[:-1], b) + 1, ...
       |---------------|
       this will raise the exception


我强烈建议您绘制一个与此示例相似的示例,并检查所有递归步骤。在不使用min的情况下进行尝试,然后在使用min的情况下进行尝试-您应该注意到在某些级别返回的内容有所不同。

关于python - 为什么此功能可以与min一起使用,但不能与之配合使用?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/43197706/

10-12 02:31