1. 程式人生 > >class 2-2 小專案練習

class 2-2 小專案練習

一. 判斷第幾天

閏年(四年一閏,百年不閏,四百年再閏)

元組(tuple)

用於表達固定資料項、函式多返回值等

特點: 1.元素可以是不同型別(元組通常不同資料組成,列表通常由相同型別資料組成)

   2.元組中各元素存在先後關係,可通過索引訪問元組中元素(元組表示的是結構,列表表示的是順序

集合(set):

  • python中的集合(set)型別同數學中集合概念一致,即包含0或多個數據項的無序組合
  • 集合中的元素不可重複
  • 集合時無序組合,沒有索引和位置的概念
  • set()函式用於集合的生成,返回結果是一個無重複且排序任意的集合
  • 集合通常用於表示成員間的關係、元素去重

集合的操作:

  • s-t 或 s.difference(t)  :返回在集合s中但不在t中的元素
  • s&t 或 s.intersection(t) :返回同時在集合s和t中的元素
  • s|t 或 s.union(t) : 返回在集合s和t中的所有元素
  • s^t 或 s.symmetric_difference(t):返回集合s和t中的元素,但不包含同時在其中的元素
from datetime import datetime

def is_leap_year(year):
    is_leap = False
    if (year % 400 == 0) or
(year % 4 == 0) and (year % 100 != 0): is_leap = True return is_leap #預設fail,如果滿足條件就變為True def main(): input_day_str = input('請輸入時間(yyyy/mm/dd): ') input_date = datetime.strptime(input_day_str,'%Y/%m/%d') year = input_date.year month = input_date.month day = input_date.day _30_day_in_month_list
= {4,6,9,11} _31_day_in_month_list = {1,3,5,7,8,10,12} days =day #初始化days for i in range(1,month): if i in _30_day_in_month_list: days += 30 elif i in _31_day_in_month_list: days += 31 else: days+=28 if month > 2 and is_leap_year(year): #函式判斷是否執行 days += 1
#days_in_month_list = [31,28,31,30,31,30,31,31,30,31,30,31]
#if is_leap_year(year):
#days_in_month_list[1] = 29
#days = sum(days_in_month_list[:month - 1]) + day
    print('這是第{}年的第{}天。'.format(year,days))

if __name__ == '__main__':
    main()

字典(dict):

  • 字典型別(dict)是“鍵--值”(通常鍵是唯一的)資料項的組合,每個元素都是一個鍵值對
    • 例:身份證號(鍵) --個人資訊 (值)
  • 字典型別資料通過對映查詢資料項
  • 對映:通過任意鍵查詢集合中的值得過程
  • 字典型別以鍵為索引,一個鍵對應一個值
  • 字典型別的資料是無序的

字典操作:

  • 增加某一項 :d[key] = value
  • 訪問: d[key]
  • 刪除某項: del d[key]
  • key是否在字典中: key in d

 字典遍歷

  1. 遍歷所有的key:
    for key in d.keys():
            print(key)
  2. b遍歷所有的value:
        for value in d.values():
            print(value)
  3. 遍歷所有的資料項:
        for item in d.items():
            print(items)
    --snip--

def main(): input_day_str = input('請輸入時間(yyyy/mm/dd): ') input_date = datetime.strptime(input_day_str,'%Y/%m/%d') year = input_date.year month = input_date.month day = input_date.day month_dict = {31:{1,3,5,7,8,10,12},30:{4,6,9,11}} days =day #初始化days for i in range(1,month): if i in month_dict[31]: days += 31 elif i in month_dict[30]: days += 30 else: days+=28 if month > 2 and is_leap_year(year): #函式判斷是否執行 days += 1 print('這是第{}年的第{}天。'.format(year,days)) if __name__ == '__main__': main()

 

二.判斷密碼強弱
設定一個8位包含數字,大小寫字母的密碼(設定一個變數strength_level用於記錄密碼強度,初始為0。滿足一個條件+1)

python判斷字串

  • str.isnumeric()   :檢測字串是否只由數字組成
  • str.isalpha()   :檢測字串是否只由字母組成
  • str.islower() :檢測字串中所有字母是否都為小寫
  • str.isupper() :檢測字串中所有字母都為大寫
  • 更多isxxx()方法參考:https://doc.python.org/3/library/stdtypes.html#string-methods
 1 def str_number(pass_word):
 2     for i in pass_word:
 3         if i.isnumeric():   #字串的使用
 4             return True  #return跳出函式迴圈,
 5     return False
 6 def str_letter(pass_word):
 7     for i in pass_word:
 8         if i.isalpha():
 9             return True
10     return False
11 
12 def main():
13     pass_word = input("please key in your pass word:")
14     strength_level = 0
15     if len(pass_word) >= 8:
16         strength_level += 1
17     else:
18         print("密碼長度至少為8位")
19     if str_letter(pass_word):
20         strength_level+= 1
21     else:
22         print("請輸入包含字母的密碼")
23     if str_number(pass_word):
24             strength_level +=1
25     else:
26         print("請輸入包含數字的密碼")
27 
28     if strength_level ==3:
29         print("恭喜,密碼設定成功!")
30     else:
31         print("密碼設定失敗")
32 
33 if __name__ =="__main__":
34     main()
View Code

 密碼嘗試超過5次

迴圈的終止

  • break 語句: 終止整個迴圈
  • continue語句:終止本次迴圈,而不終止整個迴圈的執行
  • 重點:減少一個函式中return使用次數
  • def str_number(pass_word_str):
        has_number = False
        for i in pass_word_str:
            if i.isnumeric():   #字串的使用
                has_number = True  #return跳出函式迴圈,
                break   
        return has_number
def str_number(pass_word):
    for i in pass_word:
        if i.isnumeric():   #字串的使用
            return True  #return跳出函式迴圈,
    return False
def str_letter(pass_word):
    for i in pass_word:
        if i.isalpha():
            return True
    return False

def main():
    pass_word = input("please key in your pass word:")
    strength_level = 0
    i = 0
    while i <= 4:
        i +=1
        if len(pass_word) >= 8:
            strength_level += 1
        else:
            print("密碼長度至少為8位")
        if str_letter(pass_word):
            strength_level+= 1
        else:
            print("請輸入包含字母的密碼")
        if str_number(pass_word):
                strength_level +=1
        else:
            print("請輸入包含數字的密碼")
        if strength_level ==3:
            print("恭喜,密碼設定成功!")
            break
        elif i<= 4:
            pass_word =input("密碼設定失敗,請再試一次:")
        else:
            print("您輸入的密碼嘗試超過5次。。。")

if __name__ =="__main__":
    main()
View Code
 1 def str_number(pass_word_str):
 2     has_number = False
 3     for i in pass_word_str:
 4         if i.isnumeric():   #字串的使用
 5             has_number = True  #return跳出函式迴圈,
 6             break
 7     return has_number
 8 
 9 def str_letter(pass_word_str):
10     has_number1 = 0
11     for x in pass_word_str:
12         if x.isalpha():
13             has_number1 = True
14             break
15     return has_number1
16 
17 def main():
18     pass_word = input("please key in your pass word:")
19 
20     times = 5
21     while times > 0:
22         strength_level = 0   #該位置對其進行重新初始化
23         if len(pass_word) >= 8:
24             strength_level += 1
25         else:
26             print("密碼長度至少為8位")
27         if str_letter(pass_word):
28             strength_level+= 1
29         else:
30             print("請輸入包含字母的密碼")
31         if str_number(pass_word):
32                 strength_level +=1
33         else:
34             print("請輸入包含數字的密碼")
35 
36         if strength_level == 3:
37             print("恭喜,密碼設定成功!")
38             break
39         else:
40             pass_word =input("密碼設定失敗,請再試一次:")
41             times -= 1
42 
43     if times <= 0:
44         print("您輸入的密碼嘗試超過5次。。。")
45 
46 if __name__ =="__main__":
47     main()
View Code

 第一個程式碼行中的 strength_level = 0 位置錯誤,在迴圈外對其初始化無效

 檔案的操作

  • 1. 開啟檔案:建立檔案與程式的關聯
    • open(filename,mode) ( filename:檔名(包括路徑) ;   mode: 開啟模式)
      • r: 只讀,檔案不存在則報錯
      • w:只寫,檔案不存在則自動建立(只寫w,每次重新覆蓋上次的存入)
      • a :在檔案末尾附件
      • r+:讀寫
  • 2. 操作檔案:寫入,讀取等
    • write():將文字資料寫入檔案中
    • writelines():將字串列表寫入檔案中
  • 3. 關閉檔案:終止程式與檔案的關聯
    • close()
 1 def str_number(pass_word_str):
 2     has_number = False
 3     for i in pass_word_str:
 4         if i.isnumeric():   #字串的使用
 5             has_number = True  #return跳出函式迴圈,
 6             break
 7     return has_number
 8 
 9 def str_letter(pass_word_str):
10     has_number1 = 0
11     for x in pass_word_str:
12         if x.isalpha():
13             has_number1 = True
14             break
15     return has_number1
16 
17 def main():
18     pass_word = input("please key in your pass word:")
19 
20     times = 5
21     while times > 0:
22         strength_level = 0   #該位置對其進行重新初始化
23         if len(pass_word) >= 8:
24             strength_level += 1
25         else:
26             print("密碼長度至少為8位")
27         if str_letter(pass_word):
28             strength_level+= 1
29         else:
30             print("請輸入包含字母的密碼")
31         if str_number(pass_word):
32                 strength_level +=1
33         else:
34             print("請輸入包含數字的密碼")
35         if strength_level ==1:
36             level = ''
37         elif strength_level ==2:
38             level = '較弱'
39         else:
40             level = ''
41         f = open('pass_word.txt', 'a')  # 注意引號'',如果不寫入路徑,預設儲存在當前檔案路徑下
42         f.write('密碼:{},強度:{}\n'.format(pass_word,level))
43         f.close()
44 
45         if strength_level == 3:
46             print("恭喜,密碼設定成功!")
47             break
48         else:
49             pass_word =input("密碼設定失敗,請再試一次:")
50             times -= 1
51 
52     if times <= 0:
53         print("您輸入的密碼嘗試超過5次。。。")
54 
55 if __name__ =="__main__":
56     main()
View Code
    --snip--

def main():
    --snip--
        if strength_level ==1:
            level = ''
        elif strength_level ==2:
            level = '較弱'
        else:
            level = ''
        f = open('pass_word.txt', 'a')  # 注意引號'',如果不寫入路徑,預設儲存在當前檔案路徑下
        f.write('密碼:{},強度:{}\n'.format(pass_word,level))
        f.close()

        if strength_level == 3:
            print("恭喜,密碼設定成功!")
            break
        else:
            pass_word =input("密碼設定失敗,請再試一次:")
            times -= 1

    if times <= 0:
        print("您輸入的密碼嘗試超過5次。。。")

if __name__ =="__main__":
    main()
  • 讀取檔案操作
    • read():返回值為包含整個檔案內容的一個字串
    • readline():返回值為檔案下一行內容的字串
    • readlines():返回值為整個檔案內容的列表,每項是以換行符為結尾的一行字串
    • 檔案遍歷:
      • f = open('tmp.txt', 'r')
        • for line in f  #或者for line in f.readlines
        • 處理一行資料
      •  f.close()
def main():
    f = open('pass_word.txt','r')
    """方法1:read()方法,輸出整個檔案內容"""
    # content = f.read()
    # print(content)
    """方法2:readline(),每次只能讀取一行"""
    # line = f.readline()
    # print(line)
    """方法3:readlines(),輸出的方式為列表[]"""
    lines = f.readlines()
    for line in lines: #或者for line in f:
        #處理一行資料
        print('read:{}'.format(line))
    f.close()
if __name__ =="__main__":
    main()

面向過程VS面向物件

  • 面向過程(POP):以程式執行過程為設計流程的程式設計思想
  • 面向物件(OOP):以事物為中心的程式設計思想
  • 面向物件 即現實世界中的物件:屬性,行為
  • 類(class):某種型別集合的描述
  • 屬性:類本身的一些特徵
  • 方法:類所能實現的行為

類的定義

  • class ClassName
  • __init__(self)    建構函式:初始化物件的各屬性
  • self代表類的例項
 1 class PasswordTool:
 2     def __init__(self, password):  #self代表類本身,
 3         #類的屬性
 4         self.password =password   #代表外部程式呼叫內部程式時,需要傳進來一個值給類當成附屬屬性
 5         self.strength_level = 0
 6     def process_password(self):
 7         #if len(pass_word) >= 8: #其中password的為類中的password應修改如下
 8         if len(self.password)>= 8:
 9             #strength_level += 1   #strength_level也是其中的類的屬性自身+1,應修改以下
10             self.strength_level +=1
11         else:
12             print("密碼長度至少為8位")
13         #if str_letter(self.password):  #此處也應呼叫自身的類
14         #if self.str_letter(self.password):       #此處不需要傳引數
15         if self.str_letter():
16             self.strength_level += 1
17         else:
18             print("請輸入包含字母的密碼")
19         if self.str_number():
20                 self.strength_level +=1
21         else:
22             print("請輸入包含數字的密碼")
23         #類的方法,是動態的
24     #def str_number(self, pass_word_str):    #在定義類的屬性時,都需要加一個self,當成預設的第一個引數,在類中都可以自己呼叫。
25     def str_number(self):
26         has_number = False
27         #for i in pass_word_str:  此處位置也應該修改為以下
28         for i in self.password:
29             if i.isnumeric():   #字串的使用
30                 has_number = True  #return跳出函式迴圈,
31                 break
32         return has_number
33     def str_letter(self):
34         has_number1 = 0
35         for x in self.password:
36             if x.isalpha():
37                 has_number1 = True
38                 break
39         return has_number1
40 
41 def main():
42 
43     times = 5
44     while times > 0:
45         pass_word = input("please key in your pass word:")
46         #例項化密碼工具物件
47         password_tool = PasswordTool(pass_word)  #此處需要傳入引數,初始化
48         password_tool.process_password()
49 
50         f = open('pass_word', 'a')
51         f.write('密碼:{},強度:{}\n'.format(pass_word, password_tool.strength_level))
52         f.close()
53 
54         if password_tool.strength_level == 3:
55             print("恭喜,密碼設定成功!")
56             break
57         else:
58             pass_word = print("密碼設定失敗,請再試一次")
59             times -= 1
60 
61     if times <= 0:
62         print("您輸入的密碼嘗試超過5次。。。")
63 
64 if __name__ == "__main__":
65     main()
View Code

 面向物件的特點

  • 封裝
    • 將資料及相關操作打包在一起
    • 支援程式碼複用
  • 繼承
    • 子類(subclass)借用父類(supperclass)的行為
    • 避免重複操作,機身程式碼複用率
    • 定義 class ClassName(SupperClassName)
  • 多型
    • 在不同情況下用一個函式名啟用不同方法
    • 靈活性
 1 class PasswordTool:
 2     def __init__(self, password):  #self代表類本身,
 3         #類的屬性
 4         self.password =password   #代表外部程式呼叫內部程式時,需要傳進來一個值給類當成附屬屬性
 5         self.strength_level = 0
 6     def process_password(self):
 7         #if len(pass_word) >= 8: #其中password的為類中的password應修改如下
 8         if len(self.password)>= 8:
 9             #strength_level += 1   #strength_level也是其中的類的屬性自身+1,應修改以下
10             self.strength_level +=1
11         else:
12             print("密碼長度至少為8位")
13         #if str_letter(self.password):  #此處也應呼叫自身的類
14         #if self.str_letter(self.password):       #此處不需要傳引數
15         if self.str_letter():
16             self.strength_level += 1
17         else:
18             print("請輸入包含字母的密碼")
19         if self.str_number():
20                 self.strength_level +=1
21         else:
22             print("請輸入包含數字的密碼")
23         #類的方法,是動態的
24     #def str_number(self, pass_word_str):    #在定義類的屬性時,都需要加一個self,當成預設的第一個引數,在類中都可以自己呼叫。
25     def str_number(self):
26         has_number = False
27         #for i in pass_word_str:  此處位置也應該修改為以下
28         for i in self.password:
29             if i.isnumeric():   #字串的使用
30                 has_number = True  #return跳出函式迴圈,
31                 break
32         return has_number
33     def str_letter(self):
34         has_number1 = False
35         for x in self.password:
36             if x.isalpha():
37                 has_number1 = True
38                 break
39         return has_number1
40 
41 class FileTool:
42     def __init__(self, filepath):   #定義屬性
43         self.filepath = filepath
44     def write_to_file(self,line):    #此處需要傳入形參line
45         f= open(self.filepath, 'a')
46         f.write(line)
47         f.close()
48     def readfile(self):
49         f = open(self.filepath, 'r')
50         #f.readlines(lines)  # 需要一個形參傳回,寫write則不需要
51         lines = f.readlines()
52         f.close()
53         return lines
54 
55 def main():
56 
57     times = 5
58     filepath = 'passworld_flie'
59     file_tool = FileTool(filepath)
60     while times > 0:
61         pass_word = input("please key in your pass word:")
62         #例項化密碼工具物件
63         password_tool = PasswordTool(pass_word)  #此處需要傳入引數,初始化
64         password_tool.process_password()
65 
66         line= '密碼:{},強度:{}\n'.format(pass_word, password_tool.strength_level)
67         #寫操作
68         file_tool.write_to_file(line)   #此處需要呼叫引數
69 
70         if password_tool.strength_level == 3:
71             print("恭喜,密碼設定成功!")
72             break
73         else:
74             pass_word = print("密碼設定失敗,請再試一次")
75             times -= 1
76     if times <= 0:
77         print("您輸入的密碼嘗試超過5次。。。")
78 
79     # 讀操作
80     lines = file_tool.readfile()  # 此處需要呼叫函式,不需要引數;又因為return lines,故用lines接收
81     print(lines)
82 
83 if __name__ == "__main__":
84     main()
View Code
class PasswordTool:
    --snip--

class FileTool:
    def __init__(self, filepath):   #定義屬性
        self.filepath = filepath
    def write_to_file(self,line):    #此處需要傳入形參line
        f= open(self.filepath, 'a')
        f.write(line)
        f.close()
    def readfile(self):      #不需要傳入實參
        f = open(self.filepath, 'r')
        #f.readlines(lines)  # 需要一個形參傳回,寫write則不需要
        lines = f.readlines()
        f.close()
        return lines

def main():
    times = 5
    filepath = 'passworld_flie'
    file_tool = FileTool(filepath)
    while times > 0:
        pass_word = input("please key in your pass word:")
        #例項化密碼工具物件
        password_tool = PasswordTool(pass_word)  #此處需要傳入引數,初始化
        password_tool.process_password()

        line= '密碼:{},強度:{}\n'.format(pass_word, password_tool.strength_level)
        file_tool.write_to_file(line)   #此處需要呼叫引數

        if password_tool.strength_level == 3:
            print("恭喜,密碼設定成功!")
            break
        else:
            pass_word = print("密碼設定失敗,請再試一次")
            times -= 1
    if times <= 0:
        print("您輸入的密碼嘗試超過5次。。。")

    lines = file_tool.readfile()  # 此處需要呼叫函式,不需要引數;又因為return lines,故用lines接收
    print(lines)

if __name__ == "__main__":
    main()

 

三.模擬擲骰子

通過計算機程式模擬擲骰子,並顯示個點數的出現次數及頻率(例:投擲2個骰子50次,出現點數和為7的次數是8,頻率是0.16)

 Random模組——用於生成隨機數

  • random() :生成一個[0,1.0)之間的隨機浮點數
  • uniform(a,b):生成一個a到b之間的隨機浮點數 
  • randint(a,b):生成一個a到b之間的隨機整數
  • choice(<list>):從列表中隨機返回一個元素
  • shuffle(<list>):將列表中元素隨機打亂
  • sample(<list>,k):從指定列表中隨機獲取k個元素
  • 更多模組參考:https://docs.python.org/3/library/random.html

 enumerate()函式

  • enumerate()函式用於可遍歷的組合轉換為一個索引序列
  • 一般用於for迴圈中,同時列出元素和元素的索引號
  • 圖表截圖 

模擬拋一個篩子

 1 """模擬拋一個篩子"""
 2 import random
 3 
 4 def roll_dice():
 5     roll= random.randint(1,6)
 6     return roll
 7 
 8 def main():
 9     total_times = 1000000
10     #初始化列表[0,0,0,0,0,0]
11     reslut_list = [0]*6      #等同於初始化[0,0,0,0,0,0]
12     for i in range(total_times):
13         roll = roll_dice()
14         for j in range(1,7):   #篩子的點數
15             if roll == j:
16                 reslut_list[j-1] +=1   #在j-1 的位置上+1
17     print(reslut_list)
18     for i,result in enumerate(reslut_list):     #enumerate()返回2個值, i為索引號,result為結果
19         print('點數{}的次數:{},頻率:{}'.format(i+1,result,result/total_times))
20 if __name__ =='__main__':
21     main()
View Code

zip()函式

  • zip()函式用於將對應的元素打包成一個個元組(注意:元組中元素不可修改)
  • dict(zip(|1, |2))為修改或轉換成字典(遍歷字典方式:items
  • 圖表截圖 
 1 """拋2個篩子,對應點數和次數關聯起來"""
 2 import random
 3 
 4 def roll_dice():
 5     roll= random.randint(1,6)
 6     return roll
 7 
 8 def main():
 9     total_times = 10
10     #初始化列表有11個值
11     reslut_list = [0]*11      #等同於初始化[0,0,0,0,0,0]
12     #初始化點數列表
13     roll_list = list(range(2,13))
14     roll_dict = dict(zip(roll_list, reslut_list))   #zip函式中為鍵—值對,zip(key,value)
15     for i in range(total_times):
16         roll1 = roll_dice()
17         roll2 = roll_dice()
18         for j in range(2,13):   #篩子的點數
19             if (roll1+ roll2) == j:
20                 roll_dict[j] +=1   #在j 的位置上+1
21     print(reslut_list)
22     for i,result in roll_dict.items():     #遍歷字典.items
23         print('點數{}的次數:{},頻率:{}'.format(i,result,result/total_times))
24 if __name__ =='__main__':
25     main()
View Code