set集合
集合是一个无序的、不可重复的集合。主要作用有:
1.去重,把一个列表变成集合,就等于去重了。
2.关系测试,测试两组数据之前的交集、差集、并集等关系
常用操作
创建、交集、并集、差集、对称差集、子集、父集 长度、判断元素是否在集合中、删除
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 | # 创建集合: set1 = set ([ 1 , 2 , 3 , 4 , 5 , 90 ]) set2 = set ([ 2 , 378 , 98 ]) # 交集 (在set1和set2中都有的元素) print (set1.intersection(set2)) print (set1&set2) # 并 set1和set2的所有元素的集合 print (set1.union(set2)) print (set1|set2) # 差集 :在set1中不在set2中 print (set1.disfference(set2)) print (set1 - set2) # 对称差集 项在t或s中,但不会同时出现在二者中 print (set1^set2) print (set1.symmetric_difference(set2)) # 子集 print (set1.issubset(set2)) # 父集 print (set1.issuperset(set2)) # 在set中添加一项 print (set1.add( 45 )) # 在set 中添加多项 print (set1.update(set2)) # remove删除指定项,若不存在,会报错 print (set1.remove( 2 )) print (set1.discard( 2 )) # remove删除指定项,如不存在,不报错 print (set1.pop()) # 删除任意一项 set1.discard( 98 ) # 集合的长度 print ( len (set1)) x = '' if x in set1: # 判断 x是否在set1 中。 pass if x not in set1: # 判断集合不在set1中。 pass if set1.issubset(set2): # s <= t 测试是否s中的每一个元素都在t中 pass |
文件操作
对文件的操作流程:
1.打开文件,得到文件句柄并赋值给一个变量
2.通过句柄对文件进行操作
3.关闭文件
基本操作:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | f = open ( "yesterday" , 'r' ,encoding = 'utf-8' ) # 只可读 f2 = open ( "yesterday2" , 'w' ,encoding = "utf-8" ) # 可写,覆盖原来的内容 f3 = open ( "yesterday2" , 'a' ,encoding = "utf-8" ) # 追加不可读 data = f.read() # 打印所有内容 f2.write( "我爱北京天安门\n" ) f2.write( "天安门\n" ) f4 = open ( "yesterday" , "a+" ,encoding = 'utf-8' ) # 新建文件 print (f4.readline()) # print (f4.readline()) # 读一行 print (f4.encoding) # 打印文件句柄的编号方式 print (f4.tell()) # 显示当前文件句柄的位置 print (f4.seek( 10 )) # 件句柄调到第10个位置, # 备注:在写文件时,如果使用r+ ,w+,时,不使用seek时,在文件末尾追加写入的内容 # 若使用,seek(),就覆盖写入了,不在使用追加模式 f4.truncate( 10 ) # 从文件开头到10 截断 f4.flush() # 将数据由内存刷入到文件或者硬盘 print (f4.readline()) for line in f4: print (line) # 只在内存中保存一行 f5 = open ( "test.txt" , 'rb' ) print (f5.readline()) f5.close() |
打开文件的模式有:
r,只读模式(默认)。
w,只写模式。【不可读;不存在则创建;存在则删除内容;】
a,追加模式。【可读; 不存在则创建;存在则只追加内容;】
"+" 表示可以同时读写某个文件
r+,可读写文件。【可读;可写;可追加】
w+,写读
a+,同a
with语句:
1 2 3 4 5 6 7 8 | python 2.7 中 with open ( 'log' , 'r' ) as f: for line in f: print (line) python3中: with open ( 'log1' ) as obj1, open ( 'log2' ) as obj2: pass |
编码方式
在python2中,默认编码是ASSIC编码,若在文件中指定文件的编码方式为“utf-8",若想转化成gbk,需要先解码为unicode,转编码为gbk
例如:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | #!/usr/bin/env python #-*- coding:utf-8 -*- #author luotianshuai import chardet tim = '你好' print chardet.detect(tim) #先解码为Unicode编码,然后在从Unicode编码为GBK new_tim = tim.decode( 'UTF-8' ).encode( 'GBK' ) print chardet.detect(new_tim) #结果 ''' { 'confidence' : 0.75249999999999995 , 'encoding' : 'utf-8' } { 'confidence' : 0.35982121203616341 , 'encoding' : 'TIS-620' } |
python3中:
1 2 3 4 5 6 7 8 | 在python3中,默认的就是 unicode # author:snate tim = u "你好" new_tim = tim.encode( 'GBK' )直接编码就可以。 print (new_tim) new_time = tim.encode( "GBK" ).decode( "GBK" ).encode( "GB2312" ) print (new_tim) |
面向对象、面向过程、函数式编程
面向对象是把构成问题事务分解成各个对象,建立对象的目的不是为了完成一个步骤,而是为了描叙某个事物在整个解决问题的步骤中的行为。
面向过程就是分析出解决问题所需要的步骤,然后用函数把这些步骤一步一步实现,使用的时候一个一个依次调用就可以了。
简单说,"函数式编程"是一种"编程范式"(programming paradigm),也就是如何编写程序的方法论。
它属于"结构化编程"的一种,主要思想是把运算过程尽量写成一系列嵌套的函数调用
函数的基本语法及特征
定义: 函数是指将一组语句的集合通过一个名字(函数名)封装起来,要想执行这个函数,只需调用其函数名即可
函数的特征:
减少重复代码
使程序变的可扩展
使程序变得易维护
函数的定义:
语法:
1 2 | def function(): print ( "in the function" ) |
还可以传递参数:
1 2 3 | def Sum (x,y): sum = x + y return sum |
形参变量只有在被调用时才分配内存单元,在调用结束时,即刻释放所分配的内存单元。因此,形参只在函数内部有效。函数调用结束返回主调用函数后则不能再使用该形参变量
实参可以是常量、变量、表达式、函数等,无论实参是何种类型的量,在进行函数调用时,它们都必须有确定的值,以便把这些值传送给形参。因此应预先用赋值,输入等办法使参数获得确定值。
位置参数和关键字参数、默认参数、可变参数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | #!/usr/bin/env python # _*_ encoding:utf-8 _*_ # author:snate # 位置参数和关键字参数 def test(x,y,z): print (x,y,z) # 默认参数 def test2(sex,name = "alex" ,age = 12 ): print (sex,name,age) # 参数个数不固定的形式参数 def test3(name, * args): print (name,args) def test4(name, * * kwargs): print (name,kwargs) test( 1 , 2 , 3 ) # 位置参数:实参和形参必须一一对应 test(x = 1 ,y = 2 ,z = 2 ) test(x = 1 ,z = 2 ,y = 2 ) # 关键字参数与位置无关,不必一一对应 test2( "女" ,age = 25 ,name = 12 ) # 默认参数必须放到后面, test3( "gxw" , 1 , 1 , 23 , 4 ,[ "nihao" , 2 , 3 , 5 ]) #*args 会把多传入的多个参数变成一个元组形式 test3( "gxw" , * [ 1 , 2 , 3 , 4 , 5 ]) # *args 会把多传入的参数变成一个元组形式 test4(name = "alex" ,age = 12 ,sex = "f" , id = 1 ) # *kwargs 会把多传入的关键字参数变成一个dict形式 ''' 1 2 3 1 2 2 1 2 2 女 12 25 gxw (1, 1, 23, 4, ['nihao', 2, 3, 5]) gxw (1, 2, 3, 4, 5) alex {'id': 1, 'sex': 'f', 'age': 12} ''' |
return
在子程序中定义的变量称为局部变量,在程序的一开始定义的变量称为全局变量。
全局变量作用域是整个程序,局部变量作用域是定义该变量的子程序。
当全局变量与局部变量同名时:
在定义局部变量的子程序内,局部变量起作用;在其它地方全局变量起作用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | #!/usr/bin/env python # _*_ encoding:utf-8 _*_ # author:snate school = "oldboy Edu." name = "alec" def test1(name): print ( "修改前:" + name) name = "alex" print ( "修改后:" + name) global school school = "MaGe" print (school) test1(name) print (school) |
备注:为了在函数中修改全局变量的值,需要global声明,但是在以后的工作中禁用。
递归
在函数内部,可以调用其他函数。如果一个函数在内部调用自身本身,这个函数就是递归函数
1 2 3 4 5 6 7 8 9 10 11 12 | def calc(n): print (n) if int (n / 2 ) = = 0 : return n return calc( int (n / 2 )) calc( 10 ) ''' 10 5 2 1 ''' |
递归的特征:
递归特征:
1. 必须有一个明确的结束条件
2. 每次进入更深一层递归时,问题规模相比上次递归都应有所减少
3. 递归效率不高,递归层次过多会导致栈溢出(在计算机中,函数调用是通过栈(stack)这种数据结构实现的,每当进入一个函数调用,栈就会加一层栈帧,每当函数返回,栈就会减一层栈帧。由于栈的大小不是无限的,所以,递归调用的次数过多,会导致栈溢出)
高阶函数
变量可以指向函数,函数的参数能接收变量,那么一个函数就可以接收另一个函数作为参数,这种函数就称之为高阶函数
1 2 3 4 5 | def add(x,y,f): return f(x) + f(y) res = add( 3 , - 6 , abs ) print (res) |
作业1:用python实现简答的sed替换功能
ReadMe:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | 这个一个使用python实现简单sed功能的程序 个人介绍 name:Gaoxuewu nickName:snate blog_addr: http: / / www.cnblogs.com / itlinux / p / 5749369.html 项目需求 利用python实现shell中的sed的简单替换功能 功能介绍 将文件打开,一行一行的读,判断每行中,是否存在要替换的字符,若存在就替换 将替换后的行写入到新的文件;若不存在直接将读出的行写入到另一个文件。 环境依赖 python3. * window / linux os os模块 sys模块 目录结构 testSed ├── __init__.py ├── README.md # 程序介绍 ├── testSed FlowChart # 程序流程图 ├──yesterday # 需要读取的文件 ├── yesterday.bak #替换之前,文件的备份 运行说明 在搭建好的python环境中,运行python testshell.py "年少轻狂" "Alex 很狂" ,就能实现用 "Alex 很狂" 替换 "年少轻狂" 的功能。 |
流程图:
程序:
#!/usr/bin/env python # _*_ encoding:utf-8 _*_ # author:snate ''' 将yesterday文件中的“年少轻狂”替换成“alex 很狂" ''' from sys import argv import os f1 = open("yesterday", "r", encoding="utf-8") f2 = open("yesterday.bak", "w", encoding="utf-8") for line in f1: if argv[1] in line: #"年少轻狂" line = line.replace(argv[1], argv[2]) # "---》alex 很狂" f2.write(line) f1.close() f2.close() os.rename("yesterday","yesterday-bak") os.rename("yesterday.bak","yesterday")
作业2:查找、修改、增加和删除proxy的内容
Readme:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 | # 这个一个关于proxy配置文件增、删、查的程序 ### 个人介绍 * name:Gaoxuewu * nickName:snate * email:hangtiangazi@ 163.com * blog_addr:http: / / www.cnblogs.com / itlinux / p / 5749369.html ### 功能介绍 * 查询时,输入域名,显示域名的相关的backend的信息 * 删除时,输入域名,能够删除域名以及配置服务器相关的信息 * 增加时,需要输入配置信息的字典,字典中包含backend的域名信息,以及包含IP,Maxconn,server的record列表 1. 例如:输入内容为:修改需输入内容举例:{ "backend" : "test.oldboy.org" , "record" :{ "server" : "100.1.7.9" , "weight" : 20 , "maxconn" : 30 }} 程序会自动判断输入的格式是否正确,若不正确,提示用户重新输入,直到输入正确的格式。 2. 根据输入的内容的backend的域名,判断域名是否不在,不存在,添加域名,和需要配置的服务器信息; 3. 若域名存在,判断域名的服务器信息是否存在,若不在提供用户信息已存在,不需要修改文件;若不存在, 在域名信息后面增加该信息。 ### 环境依赖: * python3以上版本 * linux / windows os * sys 模块 * os 模块 * time模块 ###目录结构: testProxy ├── __init__.py ├── README.md # 程序介绍 ├── testProxy FlowChart # 程序流程图 ├──proxy # proxy 配置文件 ├── proxy.bak_.... proxy的备份文件 ├── proxy.log # 日志文件 ├── tetsProxy.py # 程序 ├──search_backend(search_domain_name) # 查找域名信息 ├──input_format(add_domain_info_str) # 判断输入域名及服务器的配置信息是否正确 ├──add_backend() # 添加域名信息 ├──dek_backend(del_domain_name) # 删除域名相关信息 ├──main() #主程序 ### 运行说明 在搭建好的python环境中,运行python testProxy.py 即可。 |
程序流程图:
程序:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 | #!/usr/bin/env python # _*_ encoding:utf-8 _*_ # author:snate # 通过域名查询proxy的函数 import json import time import os time_fort1 = "%Y-%m-%d %H:%M:%S" time_fort2 = "%Y-%m-%d-%H-%M-%S" current_time = time.strftime(time_fort1) bak_time = time.strftime(time_fort2) # 查找函数,根据输入的域名,返回域名的详细信息 def search_backend(search_domain_name): ''' :param : Domain name :return: the specific information of Daomain ,Fomat:list ''' f = open ( "proxy" , 'r' ,encoding = "utf-8" ) info_list = [] Flag = 0 # 设置标志位 默认值为0 表示为匹配 for line in f: line = line.strip() # 去掉两端的空格和换行 if line = = "backend %s" % search_domain_name: Flag = 1 # 若匹配上默认值为1 elif line.startswith( "backend" ): Flag = 0 elif Flag = = 1 and len (line) ! = 0 : # 接着循环,将doamain的信息保存到info_list中。 info_list.append(line) f.close() return info_list # 判断输入的的域名信息及服务器的配置信息是否正确 def input_format(add_domain_info_str): ''' :param add_domain_info_str: :return: boolean ''' add_domain_content = json.loads(add_domain_info_str) try : add_domain_name = add_domain_content[ "backend" ] add_domain_server = add_domain_content[ "record" ][ "server" ] add_domain_weight = add_domain_content[ "record" ][ "weight" ] add_domain_maxconn = add_domain_content[ "record" ][ "maxconn" ] except : return False else : return True # 添加域名信息 def add_backend(): ''' :return: None ''' while True : add_domain_info_str = input ( "请输入用户要增加的配置信息:" ) Fort_Flag = input_format(add_domain_info_str) if Fort_Flag : add_domain_content = json.loads(add_domain_info_str) add_domain_name = add_domain_content[ "backend" ] add_domain_server = add_domain_content[ "record" ][ "server" ] add_domain_weight = add_domain_content[ "record" ][ "weight" ] add_domain_maxconn = add_domain_content[ "record" ][ "maxconn" ] add_domain_server_info = "server %s %s weight %s maxconn %s " % (add_domain_server,add_domain_server,\ add_domain_weight,add_domain_maxconn) info_list = search_backend(add_domain_name) if len (info_list) = = 0 : with open ( "proxy" , "r" ,encoding = "utf-8" ) as proxy_read, \ open ( "new_proxy" , "w" ,encoding = "utf-8" ) as proxy_bak_write: content_list = proxy_read.readlines() content_list.append( "\n" ) content_list.append( "backend %s\n" % add_domain_name) content_list.append( "%s %s" % ( 8 * " " , add_domain_server_info)) proxy_bak_write.writelines(content_list) # 提示用户没有域名信息,将配置信息添加到配置文件最后 print ( "No domain name,We will add to the end of the proxy!" ) time.sleep( 1 ) print ( '''\033[31;1mInformation has been added successly!!!!\033[0m''' ) os.rename( "proxy" , "proxy.bak_%s" % bak_time) os.rename( "new_proxy" , "proxy" ) with open ( "proxy.log" , 'a+' ,encoding = 'utf-8' ) as log_write: log_write.write( "%s ad d the %s into proxy config successfully!\n" % (current_time,add_domain_server_info)) else : if add_domain_server_info in info_list: # 若服务器信息重叠,提示用户信息重叠,不需要配置文件 print ( "\033[31;1mServer_info:%s is existed!,don't need add!!!!\033[0m" % add_domain_server_info) else : info_list.append(add_domain_server_info) with open ( "proxy" , 'r' , encoding = 'utf-8' ) as proxy_read, \ open ( "proxy_bak" , 'w' , encoding = 'utf-8' ) as proxy_bak_write: begin_Flag = 0 # 设置获取目标内容的flag标志 end_Flag = 0 # 设置限制目标内容循环的标志 for line in proxy_read.readlines(): if line.strip() = = "backend %s" % add_domain_name: # 若其中一行的内容为“backend domain_name",更改获取内容表示符的值为1 begin_Flag = 1 # 更改获取表示符之后,继续循环表示列表,若碰到以“backend”开头的行,重新将开始标志位设置为0 elif line.strip().startswith( "backend" ): begin_Flag = 0 if begin_Flag = = 0 : # 若获取内容的表示符为0 表示非目标内容,直接写入到proxy_bak文件。 proxy_bak_write.writelines(line); elif begin_Flag = = 1 and end_Flag = = 0 : proxy_bak_write.write( "backend %s\n" % add_domain_name) for index,domain_info in enumerate (info_list): info_list[index] = = '%s%s\n' % ( 8 * " " ,domain_info) proxy_bak_write.writelines(info_list) proxy_bak_write.write( '\n' ) # 最后加一个空白行 end_Flag = 1 # 设置限制目标内容表示符为1 os.rename( "proxy" , "proxy.bak_%s" % bak_time) os.rename( "proxy_bak" , "proxy" ) with open ( "proxy.log" , "a+" ,encoding = 'utf-8' ) as log_write: log_write.write( "%s add the %s into %s proxy config\n" % (current_time, add_domain_server_info,\ add_domain_name)) break else : print ( "您输入的格式不正确,请重新输入!" ) # 删除域名信息 def del_backend(del_domain_name): ''' :param del_domain_name: :return: None ''' with open ( "proxy" , 'r' , encoding = 'utf-8' ) as proxy_read, \ open ( "proxy_bak" , 'w' ,encoding = 'utf-8' ) as proxy_bak_write: begin_Flag = 0 for line in proxy_read.readlines(): line = line.strip() if "backend %s" % del_domain_name = = line: begin_Flag = = 1 elif line.startswith( "backend" ): begin_Flag = 1 if begin_Flag = = 0 : proxy_bak_write.write(line) with open ( "proxy.log" , 'a+' ,encoding = 'utf-8' ) as log_write: log_write.write( "%s del the %s info!\n" % (current_time, del_domain_name)) os.rename( "proxy" , "proxy.bak_%s" % (bak_time)) os.rename( "proxy.bak" , "proxy" ) print ( "%s's info is successfully deleted!" % del_domain_name) # 主程序 def main(): ''' :return: none ''' while True : print ( ''' 1.查询 2.增加 3.删除 4.退出 ''' ) user_choose = input ( "请输入您的选择:" ) if user_choose.isdigit(): user_choose = int (user_choose) if user_choose = = 1 : search_domain_name = input ( "请输入您要查询详细的域名:" ) info_list = search_backend(search_domain_name) if len (info_list) = = 0 : print ( "The info of %s don't exist" % search_domain_name) else : for line in info_list: print ( '\033[31;1m%s\033[0m' % line) elif user_choose = = 2 : add_backend() elif user_choose = = 3 : del_domain_name = input ( "input the domain name you want to delete:" ) info_list = search_backend(del_domain_name) if len (info_list) = = 0 : print ( "要删除的域名信息不存在,不执行任何操作!" ) else : del_backend(del_domain_name) elif user_choose = = 4 : for i in range ( 3 ): print ( "程序在\033[31;1m[%s]\033[0m秒后退出!" % ( 3 - i)) time.sleep( 1 ) exit() else : print ( "您的输入有误,请重新输入:" ) main() |
· 从二进制到误差:逐行拆解C语言浮点运算中的4008175468544之谜
· .NET制作智能桌面机器人:结合BotSharp智能体框架开发语音交互
· 软件产品开发中常见的10个问题及处理方法
· .NET 原生驾驭 AI 新基建实战系列:向量数据库的应用与畅想
· 从问题排查到源码分析:ActiveMQ消费端频繁日志刷屏的秘密
· 《HelloGitHub》第 108 期
· Windows桌面应用自动更新解决方案SharpUpdater5发布
· 我的家庭实验室服务器集群硬件清单
· C# 13 中的新增功能实操
· Supergateway:MCP服务器的远程调试与集成工具