7

この種の幅広い質問。

ますます長いスクリプトを書かなければならなくなると、私の本能はすべてを一口サイズの関数に分割することであることがわかります。しかし、これは最終的に、関数を呼び出す関数が関数を呼び出す関数になります....そして、私はこれについて完全に間違った方法で考えているのではないかと思っています.

要約されたスクリプトは次のようになります。すみません、それは一種のわざとです。

def simple_task_1():
    return

def simple_task_2():
    return

def simple_task_3():
    return

def simple_task_4():
    return

def complex_task_1():
    simple_task_2()
    simple_task_3()
    simple_task_4()
    return

def startup():
    simple_task_1()
    complex_task_1()
    simple_task_4()

def finish():
    # other function calls
    return

def main():
    startup()
    finish()

では、これは関数を使用する正しい方法ですか? 相互に関数呼び出しが多すぎると言える客観的なポイントはありますか? 最終的に一度しか実行されないタスクの関数を作成する必要がありますか?

4

5 に答える 5

7

Python には「再帰」制限があります。それをヒットした場合は、おそらく関数を使いすぎている可能性があります。それ以外の場合は、おそらく大したことではありません-通常、関数を再帰的に呼び出している場合にのみ、再帰制限に達することができます(通常、何か間違ったことをしたためです必要なときに壊れませんでした)。

機能のポイントは、生活を楽にすることです。機能が多すぎて、実際に生活を楽にしていないことがわかった場合、それはおそらく問題です. 例えば:

def add(x,y):
    return x+y

はかなり無意味な関数であり、おそらく避けるのが最善ですが、必要に応じてsinc:

def sinc(x):
    return math.sin(x)/x

新しい関数名はその中で実行されるコードよりもわかりやすいので、これは実際に役立つかもしれません。また、後で x=0 の特異点を削除する必要があることがわかった場合は、それをsinc簡単に追加できます。

最終的に重要なのは読みやすさです。関数を使用するとコードが読みやすくなる場合は、おそらく価値があります (1 か所から呼び出すだけで、簡単にインライン展開できる場合でも)。パフォーマンスを本当に気にしている場合は、いくつかの灰色の領域があります (関数の実行にはインライン コードよりも少し時間がかかります)。それがパフォーマンスのボトルネックであること。

于 2012-12-11T21:00:12.727 に答える
3

モジュール、クラス、関数など、大きなものを小さなものに分割することは、まさにソフトウェアの複雑さを処理する方法です。分割統治。

于 2012-12-11T21:18:44.073 に答える
2

関数の主なポイントは、コードの再利用とよりクリーンなコードを可能にすることです。一度だけ実行するという本当に単純なことであれば、この関数はおそらく不要です。

そうは言っても、コードを関数の外観に分割することに明確な問題はありません。それがあなたの生活を楽にしたり、あなたのコードをより読みやすくしたりするなら、先に進んでそれらを使ってください。

于 2012-12-11T21:03:38.007 に答える
1

少なくとも抽象的には、問題ないように見えます。

プログラムの関数への正確な分解は、関数の機能によって異なりますが、最終結果が、関数の名前で完全に記述された1つのタスクを実行する関数で構成されている場合は、正しい方向に進んでいます。

論理的なグループ化が行われている関数が非常に多い場合は、それらをモジュールに分割することを検討してください。同じデータを使用する関数が多数ある場合は、データと対応する関数を保持するクラスを作成することを検討してください。

于 2012-12-11T21:04:06.163 に答える
1

あなたはトレードオフを行っています。通常、コードをモジュール化するのは良いことです。ほとんどの人はそれを十分に行っていません。これにより、コードの再利用性と (通常は) 読みやすさが向上します。しかし、行き過ぎてしまう可能性もあります。どの関数がどの関数を呼び出しているのか混乱し、可読性が低下し始めた場合は、設計を再検討することをお勧めします。

もう 1 つ注意すべき点は、関数の呼び出しにはかなりの量のオーバーヘッドがかかることです。これはかなりの量になる可能性があります。関数を呼び出すたびに、アクティベーション レコードを作成してコール スタックに配置する必要があります。途方もなく単純な関数の場合、このオーバーヘッドは価値がありません。たとえば、2 つの数値の平均を必要とする並べ替え関数を実装している場合 (クイックソートのピボットを選択するためでしょうか?)、(a+b)/2関数を定義するよりも、単に記述するだけの方がはるかに優れています。

def avg(a, b):
    return (a+b)/2

あなたは常に考えるべき非常に良い質問をしましたが、具体的な答えを出すのは明らかに非常に困難です. より多くのコードを記述すればするほど、その感覚が良くなります。

于 2012-12-11T21:06:01.100 に答える