14

古いコードをリファクタリングし、pep8に従って関数の名前を変更したいと思います。しかし、システムの古い部分との下位互換性を維持したいと思います(関数名はAPIの一部であり、一部のユーザーは古いクライアントコードを使用するため、プロジェクトの完全なリファクタリングは不可能です)。

簡単な例、古いコード:

def helloFunc(name):
    print 'hello %s' % name

新しい:

def hello_func(name):
    print 'hello %s' % name

ただし、両方の機能が機能するはずです。

>>hello_func('Alex')
>>'hello Alex'
>>helloFunc('Alf')
>>'hello Alf'

私は考えています:

def helloFunc(name):
    hello_func(name)

、しかし私はそれが好きではありません(プロジェクトでは約50の関数であり、乱雑に見えると思います)。

それを行うための最良の方法は何ですか(コースの重複を除く)?ユニバーサルデコレータを作成することは可能ですか?

ありがとう。

4

4 に答える 4

11

今のところ、最も簡単なのは、古い関数オブジェクトへの新しい参照を作成することだと思います。

def helloFunc():
    pass

hello_func = helloFunc

もちろん、実際の関数の名前をに変更してから、エイリアスを次のように作成すると、おそらくもう少しきれいになります。hello_func

helloFunc = hello_func

モジュールの名前空間が不必要に乱雑になるため、これはまだ少し厄介です。これを回避するために、これらの「エイリアス」を提供するサブモジュールを作成することもできます。次に、ユーザーにとっては、に変更import moduleするimport module.submodule as moduleのと同じくらい簡単ですが、モジュールの名前空間を乱雑にすることはありません。

あなたはおそらくinspectこのようなことを自動的に(テストされていない)行うために使用することさえできます:

import inspect
import re
def underscore_to_camel(modinput,modadd):
    """
       Find all functions in modinput and add them to modadd.  
       In modadd, all the functions will be converted from name_with_underscore
       to camelCase
    """
    functions = inspect.getmembers(modinput,inspect.isfunction)
    for f in functions:
        camel_name = re.sub(r'_.',lambda x: x.group()[1].upper(),f.__name__)
        setattr(modadd,camel_name,f)
于 2012-08-16T12:26:51.330 に答える
7

他の答えは間違いなく真実ですが、関数の名前を新しい名前に変更し、警告を発する古い名前を作成すると便利な場合があります。

def func_new(a):
    do_stuff()

def funcOld(a):
    import warnings
    warnings.warn("funcOld should not be called any longer.")
    return func_new(a)
于 2012-08-16T12:48:11.470 に答える
4

関数オブジェクトをモジュールの名前空間内の別の名前にバインドできます。例:

def funcOld(a):
    return a

func_new = funcOld
于 2012-08-16T12:27:22.723 に答える
2

あなたの質問は非推奨などのように聞こえるので、よりクリーンなコードのためにデコレータを使用することを強くお勧めします。実際、別のスレッドの誰かがすでにこれを作成しています

于 2016-08-17T11:01:13.557 に答える