让PyCharm将Python函数中的代码提取到嵌套函数

时间:2017-12-04 12:49:46

标签: python function pycharm automated-refactoring

我已经让PyCharm 2017.3将顶层函数中的一些代码提取到另一个顶级函数中,并且它做得很好。

但是,有时我想不将提取的函数放在顶层,而是应该成为嵌套在现有函数中的函数。基本原理是重用仅在函数内部使用的代码,但在那里多次使用。我认为理想情况下,这个“子功能”应该不能在原始功能之外访问。

我该怎么做?我没有在重构对话框中看到任何选项。

实施例

a)原始代码:

def foo():
    a = ''
    if a == '':
        b = 'empty'
    else:
        b = 'not empty'
    return b

b)提取的内容:

def foo():
    a = ''
    b = bar(a)
    return b


def bar(a):
    if a == '':
        b = 'empty'
    else:
        b = 'not empty'
    return b

c)我想拥有什么:

def foo():
    def bar():
        if a == '':
            b = 'empty'
        else:
            b = 'not empty'
        return b

    a = ''
    b = bar(a)
    return b

我知道bar的{​​{1}}会影响b的{​​{1}},除非在此过程中重命名。我还考虑过完全接受阴影,不返回或请求foo,只是在b内修改它。

如果出于任何原因,我还想暗示我的想法是不是一件好事。

1 个答案:

答案 0 :(得分:3)

将功能边界隔离是一种良好的做法:将数据作为参数获取,并将数据作为返回值吐出,尽可能减少副作用。也就是说,有一些特殊情况会打破这个规则;其中许多人在使用closures时。闭包在Python中并不像在Javascript中那样惯用 - 我个人认为它很好但很多人不同意。

有一个地方的封闭在Python中绝对是惯用的:装饰器。对于其他使用闭包以避免使用全局变量并提供某种形式的数据隐藏的情况,Python中还有其他替代方法。虽然有些人提倡在只有一种方法时使用闭包而不是类,但结合functools.partial的普通函数可能会更好。

这是我猜测为什么Pycharm中没有这样的功能:我们几乎从不在Python中使用它,相反,我们倾向于将函数签名保持为foo(x),即使我们可以从x获取self封闭范围。地狱,在Python中,我们的方法明确地接收this,其中大多数语言具有隐式git rm --cached config/initializers/smtp.rb git commit -m "Removed config file from repo" git push 。如果你以这种方式编写代码,那么Pycharm已经完成了重构时所需的一切:它可以在你剪切时修复缩进。糊。

如果你发现自己经常进行这种重构,我猜你会发现一种语言,其中闭包更像是Javascript或Lisp。

所以我的意思是:这个"嵌套到全球"或者"全局到嵌套" Pycharm中不存在函数重构功能,因为依赖于封闭范围的嵌套函数在Python中不是惯用的,除非对于闭包 - 甚至闭包不是装饰器之外的惯用语。

如果您有足够的关注,可以在their issue tracker填写功能请求,或者提供一些相关的门票,例如#PY-12802#PY-2701 - 您可以看到这些门票没有引起太多关注可能是由于上述原因。