web-dev-qa-db-ja.com

tkinter GUIをプログラミングするときにクラスを使用する理由

私は主にpythonでプログラミングし、TkinterでいくつかのGUIをプログラミングしました。これまでに見たすべてのチュートリアルでは、GUIのクラスを定義して使用することを推奨していますが、私のGUIはプロシージャのみを使用して問題なく実行されます。クラスなし。

クラスを使用する理由私の観点からは、単に複雑さと不必要なコードの追加レイヤーであるように思われます。

22
Devon Muraoka

クラスを使用する理由オブジェクト指向プログラミングの方法を知っていると想定し、重要なGUIを作成していると想定すると、作業が簡単になります。オブジェクトを使用すると、コードを自己完結型のモジュール単位に簡単に分割でき、コードのモジュール化は一般的にベストプラクティスと見なされています。

GUIプログラミングは、オブジェクト指向のスタイルに適しています。これは、GUIが完全にオブジェクト(ラベル、ボタン、スクロールバー、テキスト領域など)で構成されているためです。すでにオブジェクトを使用しているため、コードを大きなオブジェクトに編成することは理にかなっています。ツールバーはオブジェクト、ステータスバーはオブジェクト、ナビゲーションペインはオブジェクト、メイン領域はオブジェクト、各ノートブックタブはオブジェクトなどです。

コードがそれほど複雑ではない場合でも、より実用的な観点からは、呼び出している関数の定義よりもファイル内でバインディングとコールバックを定義することができます。

たとえば、単純な例を考えます(tkinterが_import tkinter as tk_(python3)または_import Tkinter as tk_(python2)のようにインポートされていると仮定します)。

_def quit(event=None):
    sys.exit()
root = tk.Tk()
label = tk.Label(root, text="Hello, world")
label.pack()
label.bind("<1>", quit)
root.mainloop()
_

私にとって、そのコードの流れはすべて間違っています。参照する前にquitメソッドを定義する必要があります。ルートウィンドウの作成とmainloopの呼び出しは、他のすべてのコードによって分離されています。

ただし、クラスを使用することで、より自然な順序でコードを記述できます。

_class MyWindow(tk.Frame):
    def __init__(self, parent):
        tk.Frame.__init__(self, parent)
        label = tk.Label(self, text="Hello, world")
        label.pack()
        label.bind("<1>", self.quit)
    def quit(self, event=None):
        sys.exit()

root = tk.Tk()
MyWindow(root).pack()
root.mainloop()
_

GUIの本体はファイルの上部にあり、サポートコードはその下にあります。もちろん、関数を使用して同じことの多くを実現できます。ただし、私の意見では、クラスを使用すると、すべてが少し簡単になります。

もう1つの利点は、「メイン」ウィンドウ(およびその逆)について何も変更せずに、収容ウィンドウを簡単に変更できることです。つまり、メインGUIにボーダーまたは完全に新しいセクションを追加できますが、MyWindow内の1行のコードに触れる必要はありません。 label.pack()ステートメント、およびUI内の他のすべてのウィジェットのパック(またはグリッド)ステートメントを変更する必要がある手続き型コードとは対照的です。

ただし、オブジェクト指向のアプローチを使用することは、優れた、クリーンで、保守可能なコードを記述するために必要なことではありません。 canである可能性もありますが、コードの質が低下する可能性もあります。結局のところ、オブジェクト指向のアプローチは単なるツールです。使用するかどうか、正しく使用するかどうかは、多くの要因に依存します。したがって、あなたにとって、そしてコードyoについては、関数型のスタイルが完全に受け入れられる可能性が高いでしょう。あなたのプログラムがより複雑になるにつれて、オブジェクト指向のアプローチがあなたのコードを整理し、維持することをより簡単にするだろうと私は思うでしょう。

22
Bryan Oakley