banner
Magneto

Magnetoの小屋

Magneto在區塊鏈上の小屋,讓我們的文章在互聯網上永遠熠熠生輝!!

Python學習日記 – KillAliens 實現持續讀寫並運算

前言#

放下 Python 已經半年了,在期中考試之後,很快就要涉及算法初步了,我覺得通過 Python 的思維,對算法的學習有十分顯著的幫助,便花費幾小時寫了這個 KillAliens 小遊戲。

其中最重要的兩個部分,分別是 分數的持續讀寫並運算隨機事件的生成 這兩個部分,接下來我將詳細講述如何實現整個 KillAliens 小遊戲以及這兩個部分的實現過程。

基於
此 KillAilens 小遊戲,靈感來源於我很久之前寫的簡單的 擊殺外星人.py 這個只有不到 30 行的 簡單文字表達 遊戲,在 KillAilens 裡,記分系統是 擊殺外星人.py 沒有的,同時使用了字典,使用鍵值對實現每個種類的 Ailen 對應一個屬於自己的分數。

擊殺外星人.py 可以在我的 Python 學習倉庫內找到。

補充#

這個小遊戲 初次寫於 2022/5/14 在經過研究後,2022/5/19 修改了算法,提高了線程性能,舊代碼在倉庫中名稱為 KillAliens.pyKillAliens_NoComment.py ,新代碼在倉庫中名稱為 KillAliens_V2.pyKillAliens_NoComment_V2.py

輸出預覽#

你的名字:
	Magneto
你好  Magneto  ,接下來讓我為你介紹遊戲中有的 Alien 以及其對應的分數!
 
	擊殺 Big Alien 可以獲得 10 分
	擊殺 Middle Alien 可以獲得 5 分
	擊殺 A Alien 可以獲得 2 分
	擊殺 Small Alien 可以獲得 1 分
 
當前你的分數是  0  分
 
如果你想退出遊戲,請輸入 'quit' ,退出遊戲,或輸入其它任意值開始(繼續)遊戲。
	開始
請輸入你想要擊殺的 Alien 的  名稱  擊殺成功後,可獲得指定分數
	名稱:Big Alien
		對應分數:10
	名稱:Middle Alien
		對應分數:5
	名稱:A Alien
		對應分數:2
	名稱:Small Alien
		對應分數:1
請注意,你有概率無法擊殺 Alien 並且會因此結束遊戲,並且對應分數越高,擊殺機率越小。
請輸入對應名稱:
	Small Alien
你選擇了 Small Alien
恭喜你  Magneto  ,擊殺成功,獲得 1 分
當前總分: 1  分
 
 
 
 
當前你的分數是  1  分
 
如果你想退出遊戲,請輸入 'quit' ,退出遊戲,或輸入其它任意值開始(繼續)遊戲。
	繼續
請輸入你想要擊殺的 Alien 的  名稱  擊殺成功後,可獲得指定分數
	名稱:Big Alien
		對應分數:10
	名稱:Middle Alien
		對應分數:5
	名稱:A Alien
		對應分數:2
	名稱:Small Alien
		對應分數:1
請注意,你有概率無法擊殺 Alien 並且會因此結束遊戲,並且對應分數越高,擊殺機率越小。
請輸入對應名稱:
	Small Alien
你選擇了 Small Alien
恭喜你  Magneto  ,擊殺成功,獲得 1 分
當前總分: 2  分
 
 
 
 
當前你的分數是  2  分
 
如果你想退出遊戲,請輸入 'quit' ,退出遊戲,或輸入其它任意值開始(繼續)遊戲。
	繼續
請輸入你想要擊殺的 Alien 的  名稱  擊殺成功後,可獲得指定分數
	名稱:Big Alien
		對應分數:10
	名稱:Middle Alien
		對應分數:5
	名稱:A Alien
		對應分數:2
	名稱:Small Alien
		對應分數:1
請注意,你有概率無法擊殺 Alien 並且會因此結束遊戲,並且對應分數越高,擊殺機率越小。
請輸入對應名稱:
	Big Alien
你選擇了 Big Alien
很遺憾  Magneto  ,你嘗試擊殺 Big Alien 失敗了,分數清零,退出遊戲。
 
進程已結束,退出代碼0

代碼預覽#

############################
### Date 2022 May 14     ###
### Author Magneto       ###
### Name KillAliens      <——>
### Facility Windows 11  ###
### Language Python      ###
############################
 
import random
import time
aliens_name_and_mark = {
    'Big Alien': 10,
    'Middle Alien': 5,
    'A Alien': 2,
    'Small Alien': 1
}
Data = {'The_name': '', 'The_marks': 0}
state_one = ['1', '2', '3', '4', '5']
print("歡迎來到 KillAliens 小遊戲,字典已經初始化完成\n接下來請輸入內容\n")
Data['The_name'] = input("你的名字:\n\t")
print(f"你好 \033[94m{Data['The_name']}\033[0m ,接下來讓我為你介紹遊戲中有的 Alien 以及其對應的分數!\n")
time.sleep(1)
for name, marks in aliens_name_and_mark.items():
    print(f"\t擊殺 {name} 可以獲得 {marks} 分")
time.sleep(1)
while True:
    print(f"\n當前你的分數是 \033[35m{Data['The_marks']}\033[0m 分")
    exit_the_game = input("\n如果你想退出遊戲,請輸入 'quit' ,退出遊戲,或輸入其它任意值開始(繼續)遊戲。\n\t")
    if exit_the_game == 'quit':
        break
    print("請輸入你想要擊殺的 Alien 的 \033[94m 名稱 \033[0m 擊殺成功後,可獲得指定分數")
    for name, marks in aliens_name_and_mark.items():
        print(f"\t名稱:{name}\n\t\t對應分數:{marks}")
    print("請注意,你有概率無法擊殺 Alien 並且會因此結束遊戲,並且對應分數越高,擊殺機率越小。")
    time.sleep(1)
    ChoiseAliens = input("請輸入對應名稱:\n\t")
    if ChoiseAliens == 'Small Alien':
        state_two = ['1', '2', '3', '4', '5', '6', '7', '8']
        The_Random = random.choice(state_two)
        print("你選擇了 Small Alien")
        if The_Random in state_one:
            print(f"恭喜你 \033[94m{Data['The_name']}\033[0m ,擊殺成功,獲得 1 分")
            Data['The_marks'] += aliens_name_and_mark['Small Alien']
            print(f"當前總分:\033[35m{Data['The_marks']}\033[0m 分\n\n\n")
        else:
            print(f"很遺憾 \033[94m {Data['The_name']} \033[0m ,你嘗試擊殺 Small Alien 失敗了,分數清零,退出遊戲。")
            break
    elif ChoiseAliens == 'A Alien':
        state_two = ['1', '2', '3', '6', '7', '8']
        The_Random = random.choice(state_two)
        print("你選擇了 A Alien")
        if The_Random in state_one:
            print(f"恭喜你 \033[94m{Data['The_name']}\033[0m ,擊殺成功,獲得 2 分")
            Data['The_marks'] += aliens_name_and_mark['A Alien']
            print(f"當前總分:\033[35m{Data['The_marks']}\033[0m 分\n\n\n")
        else:
            print(f"很遺憾 \033[94m{Data['The_name']}\033[0m ,你嘗試擊殺 A Alien 失敗了,分數清零,退出遊戲。")
            break
    elif ChoiseAliens == 'Middle Alien':
        state_two = ['1', '2', '6', '7', '8']
        The_Random = random.choice(state_two)
        print("你選擇了 Middle Alien")
        if The_Random in state_one:
            print(f"恭喜你 \033[94m {Data['The_name']} \033[0m ,擊殺成功,獲得 5 分")
            Data['The_marks'] += aliens_name_and_mark['Middle Alien']
            print(f"當前總分:\033[35m{Data['The_marks']}\033[0m 分\n\n\n")
        else:
            print(f"很遺憾 \033[94m{Data['The_name']}\033[0m ,你嘗試擊殺 Middle Alien 失敗了,分數清零,退出遊戲。")
            break
    elif ChoiseAliens == 'Big Alien':
        state_two = ['1', '6', '7', '8']
        The_Random = random.choice(state_two)
        print("你選擇了 Big Alien")
        if The_Random in state_one:
            print(f"恭喜你 \033[94m{Data['The_name']}\033[0m ,擊殺成功,獲得 10 分")
            Data['The_marks'] += aliens_name_and_mark['Big Alien']
            print(f"當前總分:\033[35m{Data['The_marks']}\033[0m 分\n\n\n")
        else:
            print(f"很遺憾 \033[94m{Data['The_name']}\033[0m ,你嘗試擊殺 Big Alien 失敗了,分數清零,退出遊戲。")
            break
    else:
        print("您需要輸入對應的\033[94m名稱\033[0m,而不是其它內容。")

代碼分析#

分析說明#

本文的代碼分析,主要是講所使用的主要語法,不會具體分析每行代碼的作用,這需要自行理解。

註釋#

Python 中,註釋用 井號# 進行標識。井號後的內容將會被 Python 解釋器 忽略,在本文內附上的代碼是沒有功能性註釋的,只有作者註釋。

模塊引入
代碼 第 9-10 行 分別引入了 random 模塊和 time 模塊。

import random
import time

這兩個模塊的作用分別是隨機處理、使 Python 線程休眠指定時間。

random 的用法曾在 Python 學習日記 – 坐標移動 #random 模塊 中講過,這裡就不再多說。

time 的作用技術使 Python 線程休眠指定時間,而這個時間是按照秒為單位的,讓我們嘗試一下吧:

name = input("你的名字:")
time.sleep(1)
print(f"你好{name}")

這是運行結果

你的名字:Magneto
你好Magneto

上述代碼的第一行在 Python 線程開始運行後,立馬執行,詢問名字,在得到用戶輸入的值後,執行第二行的代碼,Python 解釋器在第二行得到指令,要求休眠 1 秒 進而休眠,在 Python 線程休眠了 1 秒 後,才繼續執行第三行的代碼,輸出名字。

字典 和 for 語句#

在 Python 中,字典是使用 {} 花括號括起來的內容,其中包括兩個內容,分別是鍵 (key) 和值 (value),我們稱之為鍵值對,每一個鍵對應一個值,在 KillAliens 中,第 12-17 行 是一個字典,第 18 行 是一個字典,這兩個字典書寫格式不同,但都是字典,沒有任何區別,第 12-17 行 的書寫格式是為了解決美觀問題,即我們在 Python 中被要求規範書寫代碼,這是一個良好的習慣。

使用字典,是為了方便 for 語句的輸出,讓我們寫一個 字典 和 for 語句的輸出試試吧:

name_and_money = {
    'Mark': '10',
    'Tom': '20',
}
for name, money in name_and_money.items():
    print(f"{name}{money} 元。")

為了方便觀看學習,我將每個鍵值對分開寫了。運行結果:

Mark 有 10 元。
Tome 有 20 元。

for 語句中,有嚴格的順序對應,name 對應鍵,money 對應值,而 items() 是為了循環輸出,直到字典沒有更多的鍵值對可以打印才跳出循環。

而在 for 語句內的 print 可以使用上述對鍵值對的命名,也就是可以使用 name 和 money 對應字典內的鍵和值,進行讀取。

除了 for 語句外,字典也可以被直接讀和寫,但這僅針對值的讀和寫。

讓我們先看讀取

# 首先定義字典
name_and_money = {
    'Mark': '10',
    'Tom': '20',
}
# 讓我們讀取字典
print(f"他有{name_and_money['Mark']}元")

print 中使用 { },代表讀取特定區域的內容,而在其中加入 [ ] ,是為了讀取特定區域內的某項特定值。

在上述代碼中,使用 {name_and_money['Mark']} 讀取了 name_and_money 字典中 Mark 這個鍵所對應的值 10 。讓我們來看看輸出結果

他有10元

現在讓我們看看寫入

# 首先定義字典
name_and_money = {
    'Mark': 10,
    'Tom': 20,
}
# 讓我們讀取原本的字典
print(f"他原來有{name_and_money['Mark']}元")
# 數字+1,即進行運算
name_and_money['Mark'] += 1
# 讓我們讀取新的的字典
print(f"但他現在有{name_and_money['Mark']}元")

讓我們看看輸出結果

他原來有10元
但他現在有11元

值得注意的是,與讀取部分不同,我沒有給這個值帶 引號 ' ' 這是因為,帶上引號就代表了這是一個字串符,需要我們轉換它為浮點數才能繼續進行運算,而不帶引號,就代表了這是一個純粹的數字,可以直接運算了。

當然,這是運算寫入,也可以直接寫入

# 首先定義字典
name_and_boyfriend = {
    'Mark': 'Williams',
    'Tom': 'Brown',
}
# 讓我們讀取原本的字典
print(f"他的前男友是{name_and_boyfriend['Mark']}")
# 覆蓋值
name_and_boyfriend['Mark'] = 'Wilson'
# 讓我們讀取新的的字典
print(f"他現男友是{name_and_boyfriend['Mark']}")

我們在這裡舉了一個男朋友的例子,直接覆蓋替換了鍵所對的值。

他的前男友是Williams
他現男友是Wilson

這裡覆蓋使用的是字串符,數字也是同樣的道理。

值得注意的是,如此覆蓋的修改是永久性的。

讓我們看看這意味著什麼

# 首先定義字典
name_and_boyfriend = {
    'Mark': 'Williams',
    'Tom': 'Brown',
}
# for 語句循環
for name, boyfriend in name_and_boyfriend.items():
    print(f'{name}曾經的男朋友是{boyfriend}')
# 讓我們讀取原本的字典
print(f"他的前男友是{name_and_boyfriend['Mark']}")
# 覆蓋值
name_and_boyfriend['Mark'] = 'Wilson'
# 讓我們讀取新的的字典
print(f"他現男友是{name_and_boyfriend['Mark']}")
# for 語句循環
for name, boyfriend in name_and_boyfriend.items():
    print(f'{name}現在的男朋友是{boyfriend}')

輸出結果

Mark曾經的男朋友是Williams
Tom曾經的男朋友是Brown
他的前男友是Williams
他現男友是Wilson

Tom 作為對照組,是沒有變過的,他的男朋友一直是 Brown,而 Mark 在更改後,for 語句讀取字典也同樣讀取的是修改後的值。

if-elif-else 進階#

KillAlines 中,使用了 if 語句的進階,在 if 語句中,嵌套 if 語句,並且使用了 in 語法,讓我們使用 KillAlines 節選的代碼,進行修改後講解吧。

# 引入 random 隨機模塊
import random
# 對照數字
state_one = ['1', '2', '3', '4', '5']
# 輸入對應的名字,這裡寫的是下面 if 語句所對的名稱
ChoiseAliens = input("請輸入對應名稱:\n\t")
# if 語句判斷,如果 ChoiseAliens 的值是 Small Alien 則執行 if 語句內的內容
if ChoiseAliens == 'Small Alien':
    # 實驗組,移交 The_Random 進行隨機處理。
    state_two = ['1', '2', '3', '4', '5', '6', '7', '8']
    The_Random = random.choice(state_two)
    print("你選擇了 Small Alien")
    # 嵌套 if 語句,所生成的隨機數如果在對照組中,則返回下值
    if The_Random in state_one:
        print(f"恭喜你,擊殺成功,獲得 1 分")
   # 嵌套 if 語句,子語句,所生成的隨機數如果不在對照組中,則返回下值
    else:
        print(f"很遺憾,你嘗試擊殺 Small Alien 失敗了")
# if 語句,子語句判斷,如果 ChoiseAliens 的值是 A Alien 則執行
elif ChoiseAliens == 'A Alien':
    # 實驗組,移交 The_Random 進行隨機處理。
    state_two = ['1', '2', '3', '6', '7', '8']
    The_Random = random.choice(state_two)
    print("你選擇了 A Alien")
    # 嵌套 if 語句,所生成的隨機數如果在對照組中,則返回下值
    if The_Random in state_one:
        print(f"恭喜你 ,擊殺成功,獲得 2 分")
    else:
   # 嵌套 if 語句,子語句,所生成的隨機數如果不在對照組中,則返回下值
        print(f"很遺憾 ,你嘗試擊殺 A Alien 失敗了")
# if 語句,子語句判斷,如果都輸入內容都不在if和elif中,則返回下值
else:
     print("您需要輸入的是指定名稱而不是其它內容。")

為了展示不同的結果,我進行了多次運行。

# 第一次
請輸入對應名稱:
	Small Alien
你選擇了 Small Alien
恭喜你,擊殺成功,獲得 1 分
 
# 第二次運行
請輸入對應名稱:
	A Alien
你選擇了 A Alien
很遺憾 ,你嘗試擊殺 A Alien 失敗了
 
# 第三次運行
請輸入對應名稱:
	Magneto
您需要輸入的是指定名稱而不是其它內容。

第一次運行,我們走了 if 的判斷,隨機挑選的一個數,在對照組 state_one 中,所以我們返回了成功,第二次運行,我們走了 elif 判斷,隨機挑選的一個數,不在對照組 state_one 中,所以我們返回了失敗,第三次運行,我們輸入了 Magneto,ifelif 判斷都不符合規則,移交 else 處理,返回了提示。

在 KillAliens 中,這樣有效避免了輸入不存在的內容,導致程序報錯。

While 循環#

While 循環在 KillAliens 中,僅僅進行了簡單使用,不進行過多講解,可以查看 Python3 循環語句 | 菜鳥教程 進行學習。

尾聲#

KillAlines 是我寫的一個較為複雜的程序,算是一個簡單的文字小遊戲,僅通過 Python 完成的記分系統、判斷系統、擊殺系統,都是很完善且較為簡單的,但這些數據僅存在線程當中,仍然有很大

此文由 Mix Space 同步更新至 xLog
原始鏈接為 https://fmcf.cc/posts/technology/Python_Notes_4


載入中......
此文章數據所有權由區塊鏈加密技術和智能合約保障僅歸創作者所有。