第6回 Python プログラミング2
データサイエンス/2025|受講生一覧|[[汎用シート>]]
はじめに
前回の復習
前回、コードの書き方の事例として挙げた「1から100までの整数の総和を求めるプログラム」について、ChatGPTにも聞いてみました。解説つきで回答してくれました。
プログラミングスキルの向上に向けて
- はじめにサンプルを「真似」て、コードの意味を1行づつ確認
- プログラムの一部を改変して、予想通りの結果になるか確認
- 自分で新たな「問い(処理の仕様)」を考えて、それをコーディング
- 様々なバグに出会い、それを修正する
ChatGPT等の生成系AIの登場によって、Web上の参考事例を探す手間は大幅に削減されましたが、AI の登場でプログラマが不要になるわけではありません。何がしたいのかを正確に指示すること、また、生成されたコードが正しいかどうかを見極めるだけのスキルがなければ、結局そのコードは利用できません。AI によって生産性を上げられるのは、結局(マニュアルを見ながら)コードが書ける人だけです。プログラミングには大きな学習コストがかかりますが、少しづつでいいので、逃げずに取り組むことを推奨します。
Pythonプログラミングの具体例
モジュールの import について
Python には、様々な既存の機能が「ライブラリ」というかたちで用意されています。例えば、乱数を発生する機能もその一つで、みなさんがその機能を実現させるためのコードを一から書く必要はありません。
import math # 数学関数を利用する場合に読み込みます。 import random # 乱数を利用する場合に読み込みます。
演習6:MonteCarloMethod
モンテカルロ法とは
計算機を使った数値計算手法の一つで、乱数を用いた試行を繰り返すことによって確率論的に近似的に求める解を得る手法です。名称の由来はカジノで有名なモナコ公国のモンテカルロ地区・・と言われています。
円周率 π の値を求めるプログラム
大量の乱数データから、円周率 π の近似値を統計的に求める手法・・・
Wikimediacommons File:Montecarlo pi2.PNG
- 一辺の長さを r とする正方形の面積を S とし、その正方形の左下頂点を中心とする 半径rの4分円の面積を Q とすると
Q = π*r*r / 4 S = r*r よって、Q / S = ( π*r*r / 4 ) / ( r*r ) = π/4
- すなわち、以下の関係式が得られます。
π = Q / S * 4
- 正方形の「枠内」に一様な乱数を使って「雨を降らせる」と
正方形全体に降る雨粒の数:4分円の中に降る雨粒の数 ≒ S:Q
となり、雨粒の数が多くなれば、S:Q の比率に一致します。
- これを利用することで
π = 4分円の中に降る雨粒の数 / 正方形全体に降る雨粒の数 * 4
というかたちで、π の近似値を求めることができます。
開発準備
- Google Colaboratory で ファイル> ノートブックを新規作成
- Untitled0.ipynb というファイル名を変更 > MonteCarloMethod.ipynb
- テキストセルを追加して、ノートの冒頭にタイトルをつけましょう。
ソースコード
以下のコードをまるごとコードセルにコピー&ペーストして下さい。
# ライブラリの読み込み import math import random # 初期化 n = 1000 cnt_in = 0 cnt_out = 0 # シミュレーション for i in range(n): # 0.0 - 1.0 のランダムな「雨粒」 x = random.random() y = random.random() # 4分円の中に落ちた数をカウント r = math.sqrt(x**2 + y**2) if r <= 1.0: cnt_in += 1 else: cnt_out += 1 # 円周率の近似値 Pi = cnt_in / n * 4 # 結果の表示 print("Num:", n) print("IN:", cnt_in) print("OUT:", cnt_out) print("Pi:", Pi)
実行
- コードセルで実行ボタン「▶︎」をクリックすると実行されます。
- 結果は、コードセルの直下に表示されます。
このプログラムは乱数を使っていて、結果はその都度変わります。 - n の初期値を大きくしていくと、結果が 3.14 に近づくことを確認しましょう。計算資源に負担をかけることがないよう、n の値はほどほどに・・
学科サイトにリンク掲載
「モンテカルロ法で π の近似値を求める」プログラムのノートを、学科サイトの個人ページからリンクして下さい。以下、手順です。
- 1. 自分のノートを開いた状態で、右上の「共有」をクリック
- 2. 共有設定を変更して、以下のように表示される状態にします。
このリンクを知っているインターネット上の全員が閲覧できます。
- 3. 「リンクをコピー」をクリックして、そのアドレスを、以下の形式で、学科サイトの「Jupyter Notebooks」の部分に掲載して下さい。
-[[MonteCarloMethod>https://colab.research.go・・=sharing]]
- 4. 以下のようになればOKです。
https://design.kyusan-u.ac.jp/socialdesign/?JohnSmith/DataScience
関数について
プログラムの基本は 入力 > 処理 > 出力 です。プログラムのことを関数と呼ぶことがありますが、関数は英語で function つまり「何らかの機能を持ったもの」という意味で、世の中のあらゆるアプリケーションは、function の集合体と捉えることができます。
中学・高校の数学で登場する「関数」を思い出して下さい。例えば・・
y = 2x + 1 ・・・ y = f ( x ) と書いたりします
は、入力データ x を受け入れて、これに処理 f ( ) つまり「2倍して1加える」を施して、その結果を y として返す・・・つまり、入力>処理>出力の機能を数式で表現したものと言えます。
データサイエンスの演習では、その大半理を、各種ライブラリーに定義された関数を利用するだけで実現させていますが、自分自身でオリジナルの関数を作って利用することもできます。以下のように記述します。
# 自作関数の定義 def myFunc(x): # 入力:引数(ひきすう)として x を受け取る y = 2*x+1 # 処理 return y # 出力:戻り値として y を返す # 自作関数を利用したプログラム s = input("数を入力して下さい >>>") # 入力 x = float(s) # 処理(文字列を数値に変換) y = myFunc(x) # 処理(計算) print("計算結果:", y) # 出力 --- 実行結果 --- 数字を入力して下さい >>> 2.5 計算結果: 6
この事例は、演習の最初に作成した PythonBasics.ipnbに追記しておくことをおすすめします。
def は define(定義)という意味の英語の略です。
付記
プログラマーは、世界のあらゆる現象を関数(入力・処理・出力)として捉える思考を身につけることで、問題を効率的に解決しています。プログラミング教育の目的は、特定の言語によるコーディングの技術を身につけることではなく、プログラマー的思考を身につけることにあります。
オブジェクト指向プログラミングについて
データの集合体(プロパティ)と、それを操作する手続き(メソッド)を、ひとまとめにしたものをオブジェクトと言います。オブジェクト指向プログラミング(OOP)とは、このオブジェクトを要素単位として、それらの関係を記述するプログラミング手法です。
プロパティやメソッドを利用する際は、以下のように [ . ] 接続で記述します。
- オブジェクト名.変数名:プロパティ
- オブジェクト名.関数名( ):メソッド
APPENDIX|プログラミングとデザイン思考
オブジェクト指向と現代社会
人間と道具は「共進化」するものです。今日の社会は、オブジェクト指向でプログラミングされたアプリケーションがその基盤を支えていることから、私たち自身、日常の様々な手続きや情報交換を通して、無意識のうちに、その思考的枠組の影響を受けていると言えます。逆に言えば、それを意識化することができれば、我々をとりまく社会システムをクリアに捉えることができます。
コンピュータの設計と人間の活動は、共に進化しなければならない
Apple Computer, 1987, Human Interface Guidelines
道具の使い方を学ぶことが私たち自身を変える・・ という点に人間と道具の関係の本質がある。
アラン・ケイ, 1994, 人間のためのコンピュータ, Addison Wesley Publisher JP
従来型のプログラミングとオブジェクト指向の違い
従来の「手続き型プログラミング」では、「データ」と「処理」はバラバラに捉えられていて、プログラマーは、処理を担う「関数(引数>処理>戻り値)」を、いかに独立性の高いものに仕立てるか・・ということに関心を集中させていましたが、機能、手続きを中心に構成されたプログラムには、以下のような問題がありました。
- プログラムの規模が大きくなるにつれて全体像の把握が難しく、プログラミングにかかるコストが膨大になる
- 機能の追加・拡張・変更が難しい
- コードの再利用が難しい
オブジェクト指向プログラミングでは「データ(プロパティ)」と「処理(メソッド)」をセットにした「オブジェクト」を構成単位と見なすとともに「オブジェクトのデータは、オブジェクトが持つメソッドによって処理される」と考えることで、プログラマーは、それがいかに単品としてうまく動くかということに専念できるようになりました。これは、画期的な意識改革です。
オブジェクトを具体的な「モノ・コト」に例えみましょう。例えば「車」は以下のようなデータと処理機能を持ったオブジェクトであると言えます。
- プロパティ:車の名前、型式、重量、色、現在位置、スピード・・・
- メソッド:エンジン始動、エンジン停止、走る、止まる、点灯する・・
我々が使っている自然言語で例えると・・・
- プロパティ:名詞・形容詞(title, place, time, size, color・・)
- メソッド:自動詞・他動詞(Start(), Stop(), EditText(), PutImage(… ), ・・ )