AxiZ沖縄ブログ

エンジニア育成学校【AxiZ沖縄】のブログです。

抽象化

問題解決力を高めたり、ものごとの本質を理解するには、 抽象化の考え方がとても重要だと感じています。 ですので今回は「抽象化」というキーワードでお話します。

抽象化という言葉の意味は、2つに分類できます。

1つ目が

  • 具体的なものを一般的なものとしてとらえること

2つ目が

  • 異なるものから共通している部分を見抜いて本質をとらえること

まずは1つ目から見ていきましょう。

具体的なものを一般的なものとしてとらえる

分かりやすいのは算数や数学の公式でしょうか。
具体的な数字の計算から、どの数字でも成り立つように一般的にしたものが公式です。
具体的なものを一般的なものとしてとらえる能力がないと、 何事も本質を理解することができません。

数学でいえば、公式を理解していないと、 教科書に載っている数字の計算はできても、数字が変わっただけで計算ができなくなる、
といったことになってしまいます。
また、一般的なものとしてとらえる発想がないと、その公式がなぜ成り立つのかを 理解することができず、本質を理解できないままとなってしまいます。

プログラミングでは、オブジェクト指向という考え方があります。
オブジェクト(モノ)に着目してプログラミングしていく考え方です。
オブジェクト指向をうまく活用するには、具体的なモノを一般的なものに分類することが求められます。
例えば、今この記事を書いている「私」は、
一般的なものに分類すると「生き物」「人間」「日本人」「男」などに分類できます。
「今私が触っているパソコン」は、
「ノートパソコン」「パソコン」「コンピュータ」などに分類できます。
このように、具体的に認識できる個別の「モノ」をより一般的(抽象的)なものに分類することが、 オブジェクト指向においては重要です。
この考え方ができないとオブジェクト指向の本質を理解することができません。

また、具体的なものを一般的なものとしてとらえる力がないと、
応用力が身に付きません。
応用力があるとはどういうことかというと、
自分が持っている知識を組み合わせて使いこなすことができるということです。

簡単な例を出します。
まず、足し算と引き算が知らない小学生がいたとします。
まず最初に足し算を教えます。そして、そのあとに引き算を教えます。
その状態で「10 + 5 - 7」のような、足し算と引き算を組み合わせた問題を出します。
応用力がある人は、足し算と引き算を行って、答えを出すことができますが、
応用力がない人は、「足し算と引き算を一緒に使っていいの?」という疑問が出てきて、 計算を進めることができません。
これは簡単な例で説明しましたが、これと似たようなことは結構あるのです。
今まで習ったことを組み合わせて使えば、簡単に解決できるのに、組み合わせる発想が出ない。
または、組み合わせてもいいなんて知らなかった、となる人が多いです。

これができるかどうかの違いは、具体的なものを一般的なものとしてとらえられているか、 これがカギになっていると思っています。
どういうことかというと、
足し算は「数 + 数」という書き方をします。
引き算は「数 - 数」です。
この情報だけでは、「数 + 数 - 数」は計算できないように感じても不思議ではありません。
しかし、ここで足し算の結果は必ず数になる、つまり「数 + 数 = 数」
となることを知っていれば、「数 + 数 - 数」 ⇒ 「(数 + 数) - 数」 ⇒ 「数 - 数」
と変換できます。だから計算が可能となるわけです。

次はExcelを例に説明します。
Excelでは様々な関数が用意されています。
例えば、合計を算出する「SUM」という関数があります。
また、数字を四捨五入する「ROUND」という関数があります。
それぞれの関数を理解するのは難しくありません。
「SUM(10.5, 5.2, 1.1) ⇒ 16.8」のように、複数の数値を入れると、合計を出してくれます。 「ROUND(10.5) ⇒ 11」のように数値を入れると、四捨五入した結果を出してくれます。
一つ一つだと、ほとんどの人が理解できます。
しかし、「ROUND(SUM(10.5, 5.2, 1.1))」のように、一気に2つ以上の関数を組み合わせると、 途端に分からなくなる、または、「そんなことしていいの?」という疑問が浮かんで、思考停止してしまいます。
ROUND関数には数値を入れることができる。SUM関数の結果は数値になる。
という知識をつなげることができれば、 ROUND関数の中にSUM関数を入れることに違和感はなくなります。
関数を使った結果を、「数値」や「文字」の一般的なものとしてとらえられると、 組み合わせて使う発想が出やすくなります。

プログラミングでも同じことが言えます。
プログラミングではif文(条件分岐)を教え、そのあとにfor文(繰り返し)を教えます。
一つ一つは理解しているのに、それらを組み合わせて使用しなければ解けない問題を出すと、 途端にできなくなったりします。
それぞれを別々で習うと、「一緒に使ってはいけないもの」と勝手に思い込んでしまうようです。
しかし、一緒に使ってはいけない、というルールはありません。
if文の中には「処理」を書くことができます。
for文の中にも「処理」を書くことができます。
そして、if文やfor文自体も「処理」です。
そのことを理解していれば、「一緒に使ってはいけない」という発想時代が出てこないはずです。

プログラミングでオブジェクト指向を使う場合も同様です。
オブジェクト指向では
インスタンス.フィールド」
インスタンス.メソッド()」
のようにすることで、オブジェクト(インスタンス)を扱うことができる、と教えます。
その状態で
インスタンス.フィールド.メソッド()」
インスタンス.メソッド().メソッド()」
「new クラス().メソッド()」
のような記述を見ると、「そんなことができるの?」と疑問に思う人が多いです。
インスタンス.フィールド、インスタンス.メソッド()の結果が何かしらのインスタンスだった場合 「インスタンス.フィールド」や「インスタンス.メソッド()」を「インスタンス」に置き換えることができます。
そうすると、全て
インスタンス.フィールド.メソッド()」 ⇒ 「インスタンス.メソッド()」
インスタンス.メソッド().メソッド()」 ⇒ 「インスタンス.メソッド()」
「new クラス().メソッド()」 ⇒ 「インスタンス.メソッド()」
という風に置き換えられます。

後半はプログラミングの専門的な話になってしましましたが、 伝えたかったことは 具体的なものを、より一般的なもの(抽象的なもの)としてとらえる習慣がないと、 何事も本質を理解することができないし、 知識を応用して活用することもできないと言うことです。

異なるものから共通している部分を見抜いて本質をとらえる

世の中には、一見異なるものだけど実は共通している部分がある、 というものがたくさんあります。 それを見つけることに何のメリットがあるかというと、異なるものであっても、
同じ構造であれば同じ法則が成り立つので、分析・解析がしやすくなります。 例えば、お金2.0の中では、経済を脳の構造と同じになっているとして、お金の流れを分析しています。
また、経済や自然とも同じ構造となっていると述べています。
このように抽象化すると、脳の仕組みや、自然の法則と照らし合わせて経済を分析することができます。

他にも、数学でも抽象化の能力は重要です。
一見違うものに見えるものを、同じ構造としてみることで、
別の分野で使われている定理が使えるようになったります。

プログラミングでは、「インターフェース」という概念があり、 別のものでも同じものとして扱えるようにする仕組みがあります。
また、機能が異なっても、設計の手法が似ているものを「パターン」としてまとめたカタログがあったり、 どのシステムでも共通して必要となる部分を「フレームワーク」としてまとめたりなど 共通しているものを見つける能力が、プログラミングにおいて重要な能力となります。

新しいことを勉強する際にも、 既に持っている知識と共通している部分を見つけることができる人は、 自分の知識と関連付けて学習することができるため、
理解するスピードが速いです。

先に紹介したお金2.0の著者もそうですが、起業して結果を出している人ほど、
物事を抽象化する能力が高いように感じます。
問題解決や、新しいビジネスを生み出すには抽象化のスキルが重要ではないかと思っています。

ここまで書いてきたように、物事を抽象化して考えることは、
問題解決や何かを学ぶときにすごく役に立ちます。
「〇〇と△△って実は似ているのでは」という風に考える練習ができると良いです。
抽象化する能力の鍛え方は、メモの魔力 という本が参考になります。

全体のまとめ

  • 抽象化は2つに分類できる
    • 具体的なものを一般的なものとしてとらえる
    • 異なるものの中から共通している部分を見つける
  • 抽象化の思考ができると
    • ものごとの本質を理解することができる
    • 応用力が高まる
    • 問題解決に役立つ