ここでは、ダックタイピングについて説明していきます。
まずはこの文章を読んでみましょう。
"If it walks like a duck and quacks like a duck, it must be a duck"
(もしもそれがアヒルのように歩き、アヒルのように鳴くのなら、それはアヒルである)
それがどうした、という感じだと思いますが、これがダックタイピングの基本的な考え方です。
型は関係なく、機能で判断する考え方
つまり、ダックタイピングというのは型ではなく、機能で分類する考え方のことです。
型ではなく、機能で判断することについて、具体例で考えていきましょう。
個人的な例で恐縮ですが、私を例にダックタイピングについて考えてみます。
まず、私を型として分類するのであれば、男性と分類されます。
つまり、男性と女性という2つのカテゴリーの中で、私は男性に属するのです。
ところで、私は子供を持つ父です。ただ、世の中のすべての男性が父であるわけではありません。
また、私は働いているビジネスマンです。しかし、世の中のすべての男性がビジネスマンではありません。
ダックタイピングも同じようなイメージです。
大元として何らかの分類があり、その分類自体は変わらないものの、その分類に新たな機能が追加されていくことによって、呼び名が増えていくのです。
プログラミングで考える
先程の男性の例を踏まえた上で、今度はプログラミングについて考えてみましょう。
プログラム(Python)において、大元としての分類はデータの型です。(あくまでも私の考えですが。)
このデータ型とは、具体的には文字列、リスト、タプルといったデータのことです。
この大元の分類を踏まえた上で、追加の機能を持つことによって違う呼び名になる、というのがダックタイピングの考え方です。
イテレーター型について考えてみます。
イテレーター型というのは、__iter__()関数と、__next__()関数を持っているオブジェクトのことです。
ここで、a = [1, 2, 3]というリスト型のオブジェクトがあったとしましょう。
このオブジェクトはリスト型ですが、このオブジェクトが__iter__()関数と、__next__()関数を実装したとします。
この時、aというオブジェクトはリスト型でもあり、イテレーター型でもあるのです。
つまり、__iter__()関数と__next__()関数を実装したからといって、リスト型で無くなる訳ではないのです。
Pythonでは、list_iterableという型になります。
厳密な型分けではなく、機能をベースに整理することも重要
ダックタイピングを具体例でご紹介しました。
型という概念が強く焼き付いていると、ダックタイピングという機能に基づいて分類という概念が消えてしまいがちですが、Pythonを深く理解する上でダックタイピングという考え型は非常に重要です。
Pythonは機能による分類もあるということを頭に入れておきましょう。