# 2024-08-30 AIoT班上課紀錄V
## AIoT班上課紀錄 Part I網址
https://hackmd.io/@aaronlife/uch-aiot-2024
## AIoT班上課紀錄 Part II網址
https://hackmd.io/@aaronlife/uch-aiot-2024-2
## AIoT班上課紀錄 Part III網址
https://hackmd.io/@aaronlife/uch-aiot-2024-3
## AIoT班上課紀錄 Part IV網址
https://hackmd.io/@aaronlife/uch-aiot-2024-4
## AIoT班上課紀錄 Part V(測驗) 網址
https://hackmd.io/@aaronlife/uch-aiot-2024-5
## 2024-08-30
#### Embeddeding
參考1: https://platform.openai.com/docs/api-reference/embeddings/create
餐考2: https://platform.openai.com/docs/guides/embeddings
```python=
from openai import OpenAI
import pprint
# 安裝語法為: pip3 install scikit-learn
from sklearn.metrics.pairwise import cosine_similarity
client = OpenAI()
resp1 = client.embeddings.create(
model="text-embedding-ada-002",
input="啤酒",
encoding_format="float"
)
resp2 = client.embeddings.create(
model="text-embedding-ada-002",
input="尿布",
encoding_format="float"
)
resp3 = client.embeddings.create(
model="text-embedding-ada-002",
input="蔬菜",
encoding_format="float"
)
# 取得每個句子的Embedding
a1 = resp1.data[0].embedding
a2 = resp2.data[0].embedding
a3 = resp3.data[0].embedding
# 用餘弦相似度計算Embedding值
result = cosine_similarity([a1, a2, a3])
print(result)
```
> `pip install scikit-learn`
## 2024-08-09
#### 單體模式(SingleTon)
```python=
class SingleTon:
_instance = None
@staticmethod
def get_instance():
if SingleTon._instance is None:
SingleTon._instance = SingleTon()
return SingleTon._instance
def __init__(self) -> None:
if SingleTon._instance is not None:
raise Exception('抱歉,只能建立一次')
else:
SingleTon._instance = self
self.ref = id(self)
def show_me(self):
print(self.ref)
a1 = SingleTon()
a2 = SingleTon.get_instance()
a1.show_me()
a2.show_me()
```
#### 算命程式(責任鏈版本)
```python=
import random
# 算命
# val = random.randint(1, 10)
# if val == 1:
# print('今天會撿到錢')
# elif val == 2:
# print('今天會加薪')
# elif val == 3:
# print('今天會中發票')
# else:
# print('沒事')
class Handler:
def set_next(self, next_handler):
self.next_handler = next_handler
def do_next(self, data):
if hasattr(self, 'next_handler'):
return self.next_handler.handle(data)
else:
return data
class FortuneTellingResult1(Handler):
def handle(self, data):
if data == 1:
return '今天會撿到錢'
else:
return self.do_next(data)
class FortuneTellingResult2(Handler):
def handle(self, data):
if data == 2:
return '今天會加薪'
else:
return self.do_next(data)
class FortuneTellingResult3(Handler):
def handle(self, data):
if data == 3:
return '今天會中發票'
else:
return self.do_next(data)
class FortuneTellingResult4(Handler):
def handle(self, data):
if data == 4:
return '今天會有豔遇'
else:
return self.do_next(data)
class FortuneTellingResultDefault(Handler):
def handle(self, data):
return self.do_next('沒事')
def build_chain():
# 建立責任
h1 = FortuneTellingResult1()
h2 = FortuneTellingResult2()
h3 = FortuneTellingResult3()
h4 = FortuneTellingResultDefault()
# 新的
h5 = FortuneTellingResult4()
# 設定責任順序
h3.set_next(h1)
h1.set_next(h2)
# 新的
h2.set_next(h5)
h5.set_next(h4)
return h3
# 建立責任鏈
chain = build_chain()
# 開始執行責任鏈
result = chain.handle(random.randint(1, 10))
print(result)
```
#### 責任鍊模式
##### my-chain.py
```python=
from handlers.chat import Chat
from handlers.checklen import CheckLength
from handlers.checkmoderation import CheckModeration
# from handlers.GetMessageFromFile import GetMessageFromFile
from handlers.getmessage import GetMessage
# 建立責任練
def build_chain():
c0 = GetMessage()
# c0 = GetMessageFromFile()
c1 = CheckLength()
c2 = CheckModeration()
c3 = Chat()
# 設定責任鍊順序
c0.set_next(c1)
c1.set_next(c2)
c2.set_next(c3)
return c0
chains = build_chain()
result = chains.handle(None)
print(result)
```
##### handlers/handler.py
```python=
class Handler:
# 設定下一個要執行的責任方法
def set_next(self, next_hanlder):
self.next_handler = next_hanlder
def do_next(self, data):
# 判斷self物件內有沒有next_handler這個屬性
if hasattr(self, 'next_handler'):
return self.next_handler.handle(data)
else:
return data
```
##### handlers/getmessage.py
```python=
from handlers.handler import Handler
class GetMessage(Handler):
def handle(self, data):
user = input('=> ')
# 進行下一關
result = self.do_next(user)
return result
```
##### handlers/getmessagefromfile.py
```python=
from handlers.handler import Handler
class GetMessageFromFile(Handler):
def handle(self, data=None):
with open('input.txt', 'r', encoding='utf-8') as file:
user = file.read()
# 進行下一關
result = self.do_next(user)
return result
```
##### handlers/checklen.py
```python=
from handlers.handler import Handler
class CheckLength(Handler):
def handle(self, data):
result = None
if len(data) > 10:
result = '聊天內容超過10個字'
else:
# 進行下一關
result = self.do_next(data)
return result
```
##### handlers/checkmoderation.py
```python=
from openai import OpenAI
from handlers.handler import Handler
client = OpenAI()
class CheckModeration(Handler):
def handle(self, data):
result = None
# 檢查內容是否違反規範
moderation = client.moderations.create(input=data)
# pprint.pprint(moderation.results[0].to_dict())
if moderation.results[0].flagged:
result = '內容違反規範: '
if moderation.results[0].categories.sexual:
result += '有性相關內容/'
if moderation.results[0].categories.hate:
result += '有仇恨相關內容/'
if moderation.results[0].categories.harassment:
result += '騷擾相關內容/'
if moderation.results[0].categories.self_harm:
result += '自殘相關內容/'
if moderation.results[0].categories.sexual_minors:
result += '次要性相關內容/'
if moderation.results[0].categories.hate_threatening:
result += '恐嚇相關內容/'
if moderation.results[0].categories.violence_graphic:
result += '暴力圖片/'
if moderation.results[0].categories.self_harm_intent:
result += '有自殘意圖/'
if moderation.results[0].categories.self_harm_instructions:
result += '有指導自殘相關內容/'
if moderation.results[0].categories.violence:
result += '暴力相關內容/'
else:
# 進行下一關
result = self.do_next(data)
return result
```
##### handlers/chat.py
```python=
from openai import OpenAI
from handlers.handler import Handler
client = OpenAI()
class Chat(Handler):
def handle(self, data):
completion = client.chat.completions.create(
model="gpt-4o",
messages=[
{"role": "system", "content": "You are a helpful assistant."},
{"role": "system", "content": "請用繁體中文回答"},
{"role": "user", "content": data}
])
result = self.do_next(completion.choices[0].message.content)
return result
```
#### OpenAI內容檢查
```python=
from openai import OpenAI
import pprint
client = OpenAI()
user = input('=> ')
# 檢查內容是否違反規範
moderation = client.moderations.create(input=user)
pprint.pprint(moderation.results[0])
if moderation.results[0].flagged:
print('內容違反規範')
if moderation.results[0].categories.sexual:
print('有性相關內容')
if moderation.results[0].categories.hate:
print('有仇恨相關內容')
if moderation.results[0].categories.harassment:
print('騷擾相關內容')
if moderation.results[0].categories.self_harm:
print('自殘相關內容')
if moderation.results[0].categories.sexual_minors:
print('次要性相關內容')
if moderation.results[0].categories.hate_threatening:
print('恐嚇相關內容')
if moderation.results[0].categories.violence_graphic:
print('暴力圖片')
if moderation.results[0].categories.self_harm_intent:
print('有自殘意圖')
if moderation.results[0].categories.self_harm_instructions:
print('有指導自殘相關內容')
if moderation.results[0].categories.violence:
print('暴力相關內容')
else:
# 聊天
completion = client.chat.completions.create(
model="gpt-4o",
messages=[
{"role": "system", "content": "You are a helpful assistant."},
{"role": "system", "content": "請用繁體中文回答"},
{"role": "user", "content": user}
])
print(completion.choices[0].message.content)
```
##### 說明
flagged: 是否有出現不適當內容
sexual: 是否為性相關內容
hate: 是否為仇恨內容
harassment: 是否為騷擾內容
self-harm: 是否為自我傷害內容
sexual/minors: 是否為較低程度的性內容
hate/threatening: 是否為恐嚇內容
violence/graphic: 是否為暴力內容圖片
self-harm/intent: 是否為意圖自我傷害內容
self-harm/instructions: 是否為指導自我傷害內容
harassment/threatening: 是否為騷擾、暴力內容
violence: 是否為暴力內容
# Python測驗
###### tags: `python`
## 基本型態、運算子
1. Python數值型態有哪4種?
**答:**
```
int, float, bool, complex
```
2. 字串可以使用哪些算術運算子?
**答:**
```
+: 串接
*: 重複字串
```
3. 在字串裡可以使用什麼轉譯字來換行?
**答:**
```
\n
```
4. 何謂r字串?
**答:**
```
r字串為raw字串,轉譯符號會當成一般文字
```
5. Python有哪幾種格式化字串的方式?
**答:**
```
C style
str.format()
f字串
```
6. `4 < 0`的運算會產生甚麼結果?
**答:**
```
False
```
7. Python內如何使用註解?
**答:**
```
#: 單行註解
Python不支援多行註解,但可以使用'''字串來當作註解
```
8. 該怎麼去掉`4.5`的小數點? 請寫出程式碼。
**答:**
```
int(4.5)
```
9. 請用指派運算子寫出`a = a + 99`的精簡寫法。
**答:**
```
a += 99
```
10. 何謂轉型? 請舉例以程式碼示範將字串轉型為整數。
**答:**
```
將某一個基本型態轉換成另外一種基本型態,例如: int('3')會將字串3轉型成數字
```
## 群集型態
1. Python有哪4種群集型態?
**答:**
```
list: 清單
set: 集合
dict: 字典
tuple: 元組
```
2. 要如何取得['aaron', 'andy', 'abner']清單內的'abner'這筆資料? 請寫出程式碼。
**答:**
```
['aaron', 'andy', 'abner'][2]
```
3. 該怎麼判斷某個元素是否存在於list當中?
**答:**
```
in
```
4. `a = {}`會建立出甚麼群集型態?
**答:**
```
dict
```
5. 哪兩種方法可以取得dict內的值?
**答:**
```
get()方法跟索引運算子[]
```
6. 要刪除tuple內某一筆資料有哪些方法?
**答:**
```
tuple無法刪除資料
```
7. `a, b, c = (1, 2, 3)`這是資料的pack還是unpack?
**答:**
```
unpack
```
8. 如何用一行程式碼產生一個1~100之間偶數的`list`?
```
[2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 28, 30, 32, 34, 36, 38, 40, 42, 44, 46, 48, 50, 52, 54, 56, 58, 60, 62, 64, 66, 68, 70, 72, 74, 76, 78, 80, 82, 84, 86, 88, 90, 92, 94, 96, 98, 100]
```
**答:**
```
list(range(2, 101, 2))
```
9. 如何取出下面set()所有的數字並加總後使用print()函式輸出。
```
my_set = {28, 37, 16}
```
**答:**
```
sum(my_set)
```
10. 有一個`list`為:`['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k']`,請問:
a. 如何使用切片得到:`['b', 'd', 'f', 'h', 'j']`的結果?
**答:**
```
print(src[1::2])
print(src[1:11:2])
```
b. 如何使用索引切片得到:`['i', 'j', 'k']`的結果?
**答:**
```
print(src[8:11:1])
print(src[8:])
print(src[-3:])
```
c. 如何使用索引切片得到: `'c-b-a'`的結果?
**答:**
```
'-'.join(src[2::-1])
```
d. 如何使用索引切片得到:`'kakakaka'`的結果(搭配算術運算子)?
**答:**
```
k = src[-1]
a = src[0]
y = (k + a) * 4
```
```
''.join(src[::-10]) * 4
```
> k為最後一個值,a為第一個值。
11. `remove()`方法和`del`都可以用來刪除`list`的一個元素,請問這兩個刪除元素的方式有什麼差別?
**答:**
```
remove()傳入元素值
del 傳入索引
```
12. 有一個字串`list`為:`data = ['aaron', 'andy', 'apple', 'amber', 'aaron', 'abner']`,其中`'aaron'`出現了兩次,如何從該`list`中移除所有的`'aaron'`字串?
**答:**
```
list(set(data)).remove('aaron')
```
13. 有兩個`list`資料,一個為學生姓名,一個為對應的每個學生成績,請問該如何將這兩個`list`資料配對後合併成一個`dictionary`,例如:
將:
```
names = ['aaron', 'andy', 'amber', 'apple', 'abner']
scores = [100, 90, 60, 80, 50]
```
變成:
```
{'aaron': 100, 'andy': 90, 'amber': 60, 'apple': 80, 'abner': 50}
```
**答:**
```
dict(zip(names, scores))
```
14. 如何用一行程式碼,就將`data = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]`就將這個`list`的第一個植根最後一個值分別存放到`first`和`last`變數當中?
**答:**
```
first, *temp, last = data
```
> first將會是0,last為9
## 流程控制
1. 請問break放在if裡面作用是什麼?
**答:**
```
沒有效果
```
2. 請問continue放在while裡面的作用是什麼?
**答:**
```
忽略剩下的程式碼,直接進行下一次的迴圈
```
3. 請使用range()函式寫出可以產生0, 2, 4, 6, 8數字的程式碼。
**答:**
```
range(0, 9, 2)
```
4. 請問if內的程式碼為什麼一定要縮排?
**答:**
```
因為不縮排,代表該程式碼不屬於if
```
5. while迴圈可以做到的事的都可以使用for-in取代嗎?
**答:**
```
是
```
6. 請問else這個關鍵字的用途是什麼?
**答:**
```
與if一起使用,在條件皆不成立時會執行該區塊內的程式碼
```
7. 如何判斷一個數字是不是偶數?
**答:**
```
num % 2 == 0 代表該數字為偶數
```
8. 如果要寫出一個完整的九九乘法表,會需要幾層的迴圈?
**答:**
```
兩層
```
9. Python有哪幾種迴圈?
**答:**
```
while
for-in
兩種
```
10. 寫一個程式,將['aaron', 'apple', 'amanda']內的每個元素顯示到畫面上,並在每個元素前面顯示他的索引值。
輸出範例:
```
0: aaron
1: apple
2: amanda
```
**答:**
```
data = ['aaron', 'apple', 'amanda']
for e in enumerate(data):
print(f'{e[0]: {e[1]}})
```
11. 請問下面迴圈的print()會執行幾次?
```
i = 0
j = 100
while i < j:
if i % 10 == 0:
break
print(i)
```
**答:**
```
0次
```
12. Python內建什麼函式可以算list內數值資料的加總?
**答:**
```
sum()
```
13. 何謂迭代?
**答:**
```
將群集資料中每一個元素逐一取出處理
```
14. 請使用range()寫出可以產生[-10,-9,-8,-7,-6]的list。
**答:**
```
range(-10, -5, 1)
```
15. 將下面程式碼改用「for Comprehension」的寫法:
```python
data = [1, 2, 3, 4]
result = []
for item in data:
result.append(item ** 2)
```
**答:**
```
result = [item ** 2 for item in [1, 2, 3, 4]]
```
16. 如何在終端機畫面上輸出如下的圖案?
```
*
**
***
****
*****
```
**答:**
```python=
for i in range(5):
for j in range(0, i + 1):
print('*', end='')
print()
```
```python=
for i in range(1, 6):
print('*' * i)
```
## 函式
1. 可以用來將兩個list裡兩配對成一個新的集合的函式叫做什麼?
**答:**
```
zip()
```
2. 將一字串「Hello Python」裡的兩個單字之間改為「-」變成「Hello-Python」來輸出,請問該怎麼做?
**答:**
```python=
print( '-'.join(data.split(' ')) )
```
```python=
print(data.replace(' ', '-'))
```
3. import random的import關鍵字用意是什麼?
**答:**
```
引入套件或模組
```
4. `print()`函式用來輸出資料到終端機畫面,那如果要從終端機接收使用者輸入該使用什麼函式?
**答:**
```
input()
```
5. 實現一個`swap()`函式,呼叫後可以交換兩個變數內的資料,例如:
```
a = 9
b = 3
a, b = swap(a, b)
print(a, b)
```
會輸出:
```
3, 9
```
**答:**
```
def swap(a, b):
return b, a
```
6. 請問下面程式碼最後會在終端機上輸出什麼?
```
src = 'a' * 5
tar = list(set('rrr'.split()))
meta = ['o', 'n']
print(''.join(list(src) * 2 + tar + meta))
```
**答:**
```
aaaaaaaaaarrron
```
> 備註:
> 字串的乘法表示將字串內容重複。
7. 請問下面程式碼哪裡有語法上的錯誤?該如何修改?
```
def process(a = 10, b = 100, final):
a **= 2
b //= 2
return a + b + final
cal = process(a=8, 10)
print(cal)
```
**答:**
```
def process(a = 10, b = 100, final = 0):
a **= 2
b //= 2
return a + b + final
cal = process(a=8, b=10)
print(cal)
```
> 1. 預設參數的右邊所有參數都必須是預設參數,所以final必須有預設值。
> 2. 10也必須指定參數名稱。
8. 何謂一級函式?
**答:**
```
涵式可以如同資料一樣指派給變數
```
9. 當你看見下面函式定義時,會覺得該函式的功用是什麼?
```
def run():
pass
```
**答:**
```
沒有功用,僅是為了保持完整的程式架構
```
10. 寫一函式`total()`,可以接受不限定數量的`int`、`list`、`set`和`tuple`參數,加總全部`list`、`set`和`tuple`內的整數後回傳結果,例如:
範例ㄧ:
```
print(total(1, 2, 3, 4))
```
會輸出:
```
10
```
範例二:
```
a = 9
b = [1, 2]
c = (3, 4)
print(total(a, b, c))
```
會輸出:
```
19
```
範例三:
```
a = (1, 2)
b = {3, 4, 6}
c = 8
d = [10, 12]
result = total(a, b, c, d)
print(result)
```
會輸出:
```
46
```
**答:**
```
def total(*args):
total = 0
for i in args:
if isinstance(i, int):
total += i
else:
total += sum(i)
return total
```
11. 下面程式碼有幾個錯誤的地方?並指出來該怎麼修改:
```
import random
1_data = input()
2_data = random.randint(0, 2)
if 1_data = 2_data
print(猜對了)
else
print(猜錯了)
```
**答:**
```
import random
data1 = int(input())
data2 = random.randint(0, 2)
if data1 == data2:
print('猜對了')
else:
print('猜錯了')
```
> 1. 變數名稱第一個字元不可以是數字。
> 2. if...else 後面都了冒號。
> 3. 判斷是不是相等需要兩個「=」號。
> 4. 字串兩邊需要加上單引號或雙引號。
> 5.(邏輯錯誤)input()資料需要轉型。
12. 下面程式碼最後執行結果`total`會輸出什麼?
```
def result(a, b = 4):
return a * b
c1 = 10
c2 = 8
result = (c1 + c2) ** 2
total = result(c1, c2)
print(total)
```
**答:**
```
會發生TypeError例外
```
## 類別與模組
1. 兩個底線開頭的函式通常是做什麼用的?
**答:**
```
類別私有成員(屬性/方法)
```
2. 類別(class)和物件(object)有何不同?
**答:**
```
類別是定義物件的輪廓
物件是實際產生出來可以使用的類別
```
3. 下面程式碼中,有哪些屬性?有哪些方法?
請將名稱列出
```
class Foo:
def __init__(self):
self.color = 'None'
self.price = None
def set_color(self, color):
self.color = color
def show_price(self):
print(f'The price is {self.price}')
```
**答:**
```
屬性:
color, price
方法:
__init__, set_color, show_print
```
4. 承上題,請問該程式碼內的`self`有何用處?
**答:**
```
self代表物件本身
```
5. 在類別內,有個方法名稱為`__init__()`,請問他有什麼用處?
**答:**
```
建構式,在物件被建立的階段自動被呼叫
```
6. 請問下面程式碼執行後會在畫面上顯示什麼結果?
**答:**
```
class ParentClass:
def show(self):
print('This is ParentClass')
class ChildClass(ParentClass):
def show(self):
print('This is ChildClass')
class ChildClass2(ParentClass):
def __init__(self):
print('This is ChildClass2')
c = ChildClass2()
c.show()
```
**答:**
```
This is ChildClass2
This is ParentClass
```
## 其他
1. 請問下面程式碼會在畫面上產生什麼結果?
```
def foo():
print('start...')
a = yield 1
print(a)
b = yield 2
print(b)
c = yield 3
print(c)
y = foo()
print('next:', next(y))
print('send:', y.send('y'))
print('next:', next(y))
```
**答:**
```
start...
next: 1
y
send: 2
None
next: 3
```
2. 請問下面程式碼會在畫面上產生什麼結果? 程式中的 `@c`的用途是什麼?
```python=
def c(func):
def b(name, age):
print('---------------------')
result = func(name, age)
print("---------------------")
return result
return b
@c
def a(name, age):
print("函式執行中。。。")
return "我是 {}, 今年{}歲 ".format(name, age)
print(a('Amos', 24))
```
**答:**
```
將c函式裝飾給a函式
---------------------
函式執行中。。。
---------------------
我是 Amos, 今年24歲
```