Friday, July 13, 2018

MIT 6.00 コンピュータサイエンスとプログラミング秋期講座第19回

MIT 6.00 コンピュータサイエンスとプログラミング秋期講座第19回
オープンコースウエア 大学名:MIT
講座名:6.00 Introduction to Computer Science and Programming
講義日:2008年11月13日(木曜日) ― 第11週・2回目  

担当教授:Prof. Guttag

全講義数:24コマ
各講義時間:60分

配信開始日:2009年8月19日
講義ビデオソース:Youtube
講義ビデオ収録時間:50分38秒
サブタイトル:有
ジャンル: オブジェクト指向プログラミング、クラス構造、ソフトウエアの再利用、ランダムウオーク、Pylab、Numpy、図表やヒストグラムをプロットする方法

ビデオ画像品質5段階評価:3.5
(今回は、どういうわけかソースコードがやや読みにくいように感じます。)
ビデオ音声品質5段階評価:4


講義コメント:
グターグ教授、どうやら風邪を引いた様子。咳をしながらの講義はちょっとつらそうです。

MITのこの講座も会を重ねること19回目となりました。あと5回の講義を残すのみとなり、
ゴールがはっきりと見えてきたような気がします。
今回19回目の講義は前回、前々回の講義でコーディングしたランダムウオークプログラムの拡張です。
でもただの拡張とは違います。
Pythonがサポートしているオブジェクト指向プログラミングの特性を利用して、
新しいクラスを既存のクラス構造の中にはめ込む事によって、プログラムの機能を拡張するテクニックの学習です。
グターグ教授は、どちらかというと、プログラミングのテクニックをいろいろ講義の中に盛り込みたい傾向があるようです。
対してグリムソン教授は、プログラミングのもつ数学的というかアルゴリズム的な部分に特に重きを置いているようです。
ここでは、前回のプログラムで作った 酔っぱらいクラスを以下のように拡張しています。

class Drunk(object): #Replaced
  def __init__(self, name):
    self.name = name
  def move(self, field, cp, dist = 1):
    if field.getDrunk().name != self.name:
      raise ValueError('Drunk.move called with drunk not in field')
    for i in range(dist):
      field.move(cp, 1)
   
class UsualDrunk(Drunk): #Added a new class
  def move(self, field, dist = 1):
    cp = random.choice(CompassPt.possibles)
    Drunk.move(self, field, CompassPt(cp), dist) #Note notation of call
  
class ColdDrunk(Drunk): #Added a new class
  def move(self, field, dist = 1):
    cp = random.choice(CompassPt.possibles)
    if cp == 'S':
      Drunk.move(self, field, CompassPt(cp), 2*dist)
    else:
      Drunk.move(self, field, CompassPt(cp), dist)
   
class EWDrunk(Drunk): #Added a new class
  def move(self, field, time = 1):
    cp = random.choice(CompassPt.possibles)
    while cp != 'E' and cp != 'W':
      cp = random.choice(CompassPt.possibles)
    Drunk.move(self, field, CompassPt(cp), time)




-------------------------------------------------

Lecture 19 Hand out 補助教材 ダウンロード

Lecture 19 ホームワーク ダウンロード
MIT 6.00 講座のプログラムも含んだ資料のダウンロード
-------------------------------------------------


-------------------------------------------------
講義で取り上げたPythonコードの例
注-1! あらかじめ PylabとNumpy という数学・計算用および図表表示モジュールをインストールしておく必要があります。
個別モジュールをダウンロードするには、ソースフォージ(SourceForge)のサイトから次の2つの小さいパッケージをダウンロードしてインストールします。
1. Numpy のパッケージ --> http://sourceforge.net/projects/numpy/files/NumPy/
   ダウンロードするパッケージは、numpy-1.5.1-win32-superpack-python2.6.exe
2. Pylab のパッケージ --> http://sourceforge.net/projects/matplotlib/files/matplotlib/matplotlib-1.0.1/
   ダウンロードするパッケージは、matplotlib-1.0.1.win32-py2.6.exe


例-1 ソースコード


import math, random, pylab, numpy

class Location(object):
  def __init__(self, x, y):
    self.x = float(x)
    self.y = float(y)
  def move(self, xc, yc):
    return Location(self.x+float(xc), self.y+float(yc))
  def getCoords(self):
    return self.x, self.y
  def getDist(self, other):
    ox, oy = other.getCoords()
    xDist = self.x - ox
    yDist = self.y - oy
    return math.sqrt(xDist**2 + yDist**2)
class CompassPt(object):
  possibles = ('N', 'S', 'E', 'W')
  def __init__(self, pt):
    if pt in self.possibles: self.pt = pt
    else: raise ValueError('in CompassPt.__init__')
  def move(self, dist):
    if self.pt == 'N': return (0, dist)
    elif self.pt == 'S': return (0, -dist)
    elif self.pt == 'E': return (dist, 0)
    elif self.pt == 'W': return (-dist, 0)
    else: raise ValueError('in CompassPt.move')
 
class Field(object):
  def __init__(self, drunk, loc):
    self.drunk = drunk
    self.loc = loc
  def move(self, cp, dist):
    oldLoc = self.loc
    xc, yc = cp.move(dist)
    self.loc = oldLoc.move(xc, yc)
  def getLoc(self):
    return self.loc
  def getDrunk(self):
    return self.drunk
class Drunk(object): #Replaced
  def __init__(self, name):
    self.name = name
  def move(self, field, cp, dist = 1):
    if field.getDrunk().name != self.name:
      raise ValueError('Drunk.move called with drunk not in field')
    for i in range(dist):
      field.move(cp, 1)
   
class UsualDrunk(Drunk): #Added a new class
  def move(self, field, dist = 1):
    cp = random.choice(CompassPt.possibles)
    Drunk.move(self, field, CompassPt(cp), dist) #Note notation of call
 
class ColdDrunk(Drunk): #Added a new class
  def move(self, field, dist = 1):
    cp = random.choice(CompassPt.possibles)
    if cp == 'S':
      Drunk.move(self, field, CompassPt(cp), 2*dist)
    else:
      Drunk.move(self, field, CompassPt(cp), dist)
   
class EWDrunk(Drunk): #Added a new class
  def move(self, field, time = 1):
    cp = random.choice(CompassPt.possibles)
    while cp != 'E' and cp != 'W':
      cp = random.choice(CompassPt.possibles)
    Drunk.move(self, field, CompassPt(cp), time)
def performTrial(time, f):
  start = f.getLoc()
  distances = [0.0]
  for t in range(1, time + 1):
    f.getDrunk().move(f)
    newLoc = f.getLoc()
    distance = newLoc.getDist(start)
    distances.append(distance)
  return distances
##drunk = Drunk('Homer Simpson')
##for i in range(3):
##  f = Field(drunk, Location(0, 0))
##  distances = performTrial(500, f)
##  pylab.plot(distances)
##pylab.title('Homer\'s Random Walk')
##pylab.xlabel('Time')
##pylab.ylabel('Distance from Origin')
def performSim(time, numTrials, drunkType): #Replaced
  distLists = []
  for trial in range(numTrials):
    d = drunkType('Drunk' + str(trial))
    f = Field(d, Location(0, 0))
    distances = performTrial(time, f)
    distLists.append(distances)
  return distLists
def ansQuest(maxTime, numTrials, drunkType, title): #Replaced
  means = []
  distLists = performSim(maxTime, numTrials, drunkType)
  for t in range(maxTime + 1):
    tot = 0.0
    for distL in distLists:
      tot += distL[t]
    means.append(tot/len(distLists))
  pylab.figure()
  pylab.plot(means)

##  pylab.ylabel('distance')
##  pylab.xlabel('time')
##  pylab.title('Average Distance vs. Time (' + str(len(distLists)) + ' trials)')
  pylab.ylabel('Ave. Distance')
  pylab.xlabel('Steps')
  pylab.title(title)
numSteps = 500
numTrials = 100
ansQuest(numSteps, numTrials, UsualDrunk, 'UsualDrunk ' + str(numTrials) + ' Trials')
ansQuest(numSteps, numTrials, ColdDrunk, 'ColdDrunk ' + str(numTrials) + ' Trials')
ansQuest(numSteps, numTrials, EWDrunk, 'EWDrunk ' + str(numTrials) + ' Trials')
pylab.show()




例-1の実行結果
エディタから実行してPython Shell に出力
Mit_600_19_1

出力した画像の元ファイルをダウンロードしてみる。

「Usual_Drunk_100Trials.svg」をダウンロード
「Cold_Drunk_100Trials.svg」をダウンロード
「EastWest_Drunk_100Trials.svg」をダウンロード
SVG(Scalable Vector Graphics)ファイル
--------------------------------------------------


Python コードのHTML表示には、Dan CederholmのSimpleCodeを使用しています。
Python コードの入出力は、Python IDLE から行っています。
Python_idle_1_small


-------------------------------------------------

講座第19回のリーディングアサイメント

1. Random walks applet

2. Chapter 13 of Matplotlib/pylab reference
-------------------------------------------------

-------------------------------------------------

No comments:

Post a Comment

MIT 6.00 コンピュータサイエンスとプログラミング秋期講座第2回

  MIT 6.00 コンピュータサイエンスとプログラミング秋期講座第2回 オープンコースウエア 大学名:MIT 講座名:6.00 Introduction to Computer Science and Programming Download course material ...