{
"cells": [
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "slide"
}
},
"source": [
"# [X-Village] Lesson03 - Class\n",
"---\n",
"speaker: amber(吳思嬋)"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 有系統內建函式(ex. print),我們可以使用 keyword def 來建立自定義的函式。\n",
"\n",
"## 同理,有系統內建的type(ex. number, string, ...),我們也可以使用某一個keyword 來建立我們自定義的type。"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 使用 keyword class 就能建立自己的 type object,將這個type object 指派給我們我們自由定義的名字(Name)\n",
"---\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 在 class 的內部 assign name, name 為變數(variable) 或 函式(def statement)\n",
"---\n",
"* class 的變數(variable) 我們稱為屬性(attribute)\n",
"* class 的變數 函式(function),我們稱為方法(method)\n",
"* 當 class object 建立時,class object 擁有自己的scope, 存放 attribute 和 method\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## Instance Objects (實例物件)\n",
"* 當我們使用 class object 的時候,就會產生 instance object\n",
"* 產生 instance object 時,instance object 會擁有自己的 local scope。\n",
"* 產生 instance object 時,它會繼承 class object 的 attribute(屬性) 與 method(方法),位於 instance object 的 local scope"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"### 建立 instance object (實例物件) 時,instance object 就擁有自己獨立的scope 和 繼承 class的 attribute 與 method,attribute 與 method 屬於 instance object 的 local scope。\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"### 在instance object 中,assign attribute 或 reassgin attribute 都不會影響原本的 class object\n",
""
]
},
{
"cell_type": "code",
"execution_count": 22,
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"This is my own attribute\n"
]
}
],
"source": [
"class Animal:\n",
" name = 'default_name'\n",
" age = 'default_age'\n",
" \n",
"my_pet = Animal() # Make instances object\n",
"my_pet.name = 'dog'\n",
"my_pet.age = '7'\n",
"\n",
"my_pet.new = 'This is my own attribute'\n",
"print(my_pet.new)"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 在 class 中可以使用 keyword def 來產生 function,我們稱為method。\n",
"## Method 宣告時的第一個 argument 非常重要!!!一定要寫。 代表 instance object 可以取用 attribute。\n",
"---\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 使用 instance.method 的表達時,可以呼叫 method"
]
},
{
"cell_type": "code",
"execution_count": 49,
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"球體體積 523.3333333333334\n",
"球體表面積 314.0\n"
]
}
],
"source": [
"class Ball: \n",
" def set_radius(self, radius_arg):\n",
" self.radius = radius_arg\n",
" \n",
" def calculate_volume(self): # 計算球體體積\n",
" volume = 4/3 * 3.14 * (self.radius*self.radius*self.radius)\n",
" return volume\n",
"\n",
" def calculate_surface_area(self): # 計算球體表面積\n",
" self.surface_area = 4 * 3.14 * (self.radius*self.radius)\n",
" \n",
"x = Ball() # 建立 instance object\n",
"x.set_radius(5)\n",
"\n",
"volume = x.calculate_volume() # 呼叫計算體積method\n",
"print('球體體積', volume) # \n",
"\n",
"x.calculate_surface_area() # 呼叫計算表面積method\n",
"print('球體表面積', x.surface_area) "
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## Recap Scope - 當我們 assign name 的時候,name所在的位置就決定了它的scope\n",
"---\n",
"* 在 function 中 assign name,name 屬於 function 的 local scope\n",
"* 在 function 外 assign name,name 屬於 global scope"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "fragment"
}
},
"source": [
"## class object 和 instance object 的 Scope\n",
"---\n",
"* class object 建立的時候,擁有自己的 scope,存放attribute 和 method\n",
"* instance object 建立的時候,也擁有自己的scope,存放attribute 和 method"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 課堂練習 - 判斷 name 所屬的 scope (不列入課堂成績)\n",
"---\n",
"1. 請根據我們教的 scope 概念,圈出 global scope 和 local scope \n",
"2. 請判斷下列的name 所屬的 scope,若為 local scope, 則需列出是誰的local scope 。\n",
" * Ball, set_radius, calculate_volume, calculate_surface_area, radius_arg, volume1, volume2, x ,\n",
" * 屬性 color, radius, surface_area"
]
},
{
"cell_type": "code",
"execution_count": 53,
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"球體體積 523.3333333333334\n",
"球體表面積 314.0\n"
]
}
],
"source": [
"class Ball: \n",
" color = 'BLACK'\n",
" def set_radius(self, radius_arg):\n",
" self.radius = radius_arg\n",
" \n",
" def calculate_volume(self): # 計算球體體積\n",
" volume1 = 4/3 * 3.14 * (self.radius*self.radius*self.radius)\n",
" return volume1\n",
"\n",
" def calculate_surface_area(self): # 計算球體表面積\n",
" self.surface_area = 4 * 3.14 * (self.radius*self.radius)\n",
" \n",
"x = Ball() # 建立 instance object\n",
"x.set_radius(5)\n",
"\n",
"volume2 = x.calculate_volume() # 呼叫計算體積method\n",
"print('球體體積', volume) # \n",
"\n",
"x.calculate_surface_area() # 呼叫計算表面積method\n",
"print('球體表面積', x.surface_area) "
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 課堂練習1 - 判斷 name 所屬的 scope (列入課堂成績)\n",
"---\n",
"1. 請根據我們教的 scope 概念,圈出 global scope 和 local scope,判斷 name 的 scope。 \n",
"2. 請找助教講解下列程式的流程,以及每一個name所屬的scope及其緣由(為什麼會print出這樣的結果)。"
]
},
{
"cell_type": "code",
"execution_count": 62,
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Name: Keven result: 過輕\n"
]
}
],
"source": [
"class BMI: \n",
" name = 'default_name' \n",
" def set_name(self, name_arg):\n",
" self.name = name_arg\n",
" name = 'John'\n",
" \n",
" def judge(self, height, weight):\n",
" calculate = weight / (height*height)\n",
" if calculate < 18.5:\n",
" self.result = '過輕'\n",
" elif 18.5 < calculate and calculate < 24:\n",
" self.result = '正常'\n",
" else:\n",
" self.result ='過重'\n",
" def display(self): # 展示結果\n",
" print('Name:', self.name, 'result:',self.result)\n",
" \n",
"man = BMI()\n",
"man.set_name('Keven')\n",
"man.judge(1.82, 50)\n",
"man.display()"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 課堂練習2 - 建立 class Life(列入課堂成績)\n",
"* 程式要求:\n",
" * 需使用 list 儲存nxn地圖 \n",
" * 2x2 map:\n",
" [[*, *],\n",
" [*, *]]\n",
" * 建立 set_map method,傳入參數 n, 建立 nxn 地圖\n",
" * 建立 set_pattern method, 傳入參數 p, 如果 p=1, 在 nxn 地圖中的中央設置 Glider圖案(如下列範例)\n",
" * 建立 display method,展示地圖\n",
" * 可以自由建立任何你需要的 attribute, method\n"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"* 範例\n",
" * my_map = Map() #建立 instance object\n",
" * my_map.set_map(5) # n=5, 代表地圖為 5x5 大小\n",
" * my_map.display() #印出 5x5 地圖\n",
"\n",
" * my_map.set_pattern(1) # p=1, 設置 Glider 圖案在地圖中央\n",
" * my_map.display() # 展示有 Glider 圖案的地圖\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"* 範例(接續)\n",
" * my_map.set_map(7) # n=7, 代表地圖為 7x7 大小。\n",
" * my_map.display() #印出 7x7 地圖\n",
"\n",
"\n",
" * my_map.set_pattern(1) # p=1, 設置 Glider 圖案在地圖中央\n",
" * my_map.display() # 展示有 Glider 圖案的地圖\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## Constructors Method: _init_\n",
"----\n",
"* **語法: init前後都需要雙底線 **,init的名字不能更改,一定要叫做init。\n",
"* 如果我們有設置 _init_ method,當 instance object 被建立的時候,就會自動執行。\n",
"* 因此,我們常透過 _init_ method 來做初始化的動作。"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"![](https://i.imgur.com/jAbemHW.png)"
]
},
{
"cell_type": "code",
"execution_count": 63,
"metadata": {
"slideshow": {
"slide_type": "fragment"
}
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"John 35\n"
]
}
],
"source": [
"# __init__ is run when a new instance object is created\n",
"class People:\n",
" def __init__(self, name, age):\n",
" self.name = name\n",
" self.age = age\n",
" \n",
"x = People('John', '35')\n",
"print(x.name, x.age)"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## 課堂練習3 - 建立 class Life(列入課堂成績)\n",
"* 程式要求:\n",
" * 需使用 list 儲存nxn地圖 \n",
" * 2x2 map:\n",
" [[*, *],\n",
" [*, *]]\n",
" * 建立 _init_ method,傳入參數 n, p, 初始化 nxn 地圖。如果 p=1, 在 nxn 地圖中的中央設置 Glider圖案(如下列範例)\n",
" * 建立 display method,展示地圖\n",
" * 可以自由建立任何你需要的 attribute, method"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"* 範例\n",
" * my_map = Map(5, 1) #建立 instance object\n",
" * my_map.display() #印出有 Glider 圖案的 5x5 地圖\n",
""
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## [X-Village Python Programming - 作業1](https://github.com/x-village/X-Village-Homework1)(列入作業成績)"
]
},
{
"cell_type": "markdown",
"metadata": {
"slideshow": {
"slide_type": "subslide"
}
},
"source": [
"## [X-Village Python Programming - 自我挑戰題](https://hackmd.io/Oy66r5PkSNC7xoHbhZkwug)(不列入作業和課堂成績)"
]
}
],
"metadata": {
"celltoolbar": "Slideshow",
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.6.5"
}
},
"nbformat": 4,
"nbformat_minor": 2
}