版权声明:本文为博主原创文章,转载请注明出处。
6-2. 字符串标识符.修改例 6-1 的 idcheck.py 脚本,使之可以检测长度为一的标识符,并且可以识别 Python 关键字,对后一个要求,你可以使用 keyword 模块(特别是 keyword.kelist)来帮你.
- import string
- import keyword
- alphas=string.letters+'_'
- num=string.digits
- aplpnums=alphas+num
- print 'Testees must be at least 1 char long.'
- myinput=raw_input('Identifier to test? ')
- if len(myinput)>=1:
- if myinput[0] not in alphas:
- print 'invalid: first symbol must be alphabetic'
- else:
- for otherchar in myinput [1:]:
- if otherchar not in aplpnums:
- print 'invalid: remaining symbols must be alphanumeric'
- break
- else:
- if myinput in keyword.kwlist:
- print 'invalid: symbol is reserved as keyword'
- else:
- print 'okay as an identifier'
6-3
排序
(a) 输入一串数字,从大到小排列之.
(b) 跟 a 一样,不过要用字典序从大到小排列之
- (a)
- numstr=raw_input('input some numbers: ')
- numlist=list(numstr)
- n=len(numlist)
- for i in range(0,n):
- for j in range(0,n-i-1):
- if int(numlist[j])<int(numlist[j+1]):
- temp=numlist[j]
- numlist[j]=numlist[j+1]
- numlist[j+1]=temp
- numlist.sort()
- numlist.reverse()
- print numlist
- (b)
- numstr=raw_input('input some numbers: ')
- numlist=list(numstr)
- numlist.sort()
- numlist.reverse()
- print numlist
6-4 算术. 更新上一章里面你的得分测试练习方案,把测试得分放到一个列表中去.你的代码应该可以计算出一个平均分,见练习 2-9 和练习 5-3.
- score=[65,76,87,98]
- print (sum(score)/len(score))
6-5 字符串
(a)更新你在练习 2-7 里面的方案,使之可以每次向前向后都显示一个字符串的一个字符.
(b)通过扫描来判断两个字符串是否匹配(不能使用比较操作符或者 cmp()内建函数)。附加题:在你的方案里加入大小写区分.
(c)判断一个字符串是否重现(后面跟前面的一致).附加题:在处理除了严格的回文之外,加入对例如控制符号和空格的支持。
(d)接受一个字符,在其后面加一个反向的拷贝,构成一个回文字符串.
- (a)
- s=raw_input('Enter a string:')
- i=0
- while i<len(s):
- print s[0:i+1],
- i+=1
- j=0
- rs=''
- while j<len(s):
- rs+=s[-1-j]
- print rs,
- j+=1
- (b)
- str1=raw_input('Enter 1st string:')
- str2=raw_input('Enter 2nd string:')
- newstr1=str1.lower()
- newstr2=str2.lower()
- if len(str1) is not len(str2):
- print "not equal"
- else:
- for i in range(len(str1)):
- if newstr1[i] is not newstr2[i]:
- print "not equal"
- break
- else:
- print "equal"
- (C)
- str=raw_input('Enter 1st string:')
- l=len(str)
- if l % 2 == 0:
- for i in range(l/2):
- if str[i]!=str[l-1-i]:
- print "not repeat"
- break
- else:
- print "repeat"
- elif l % 2 != 0:
- for i in range(l/2):
- if str[i]!=str[l-i-1]:
- print "not repeat"
- break
- else:
- print "repeat"
- (d)
- str1=raw_input('Enter 1st string:')
- str2=str1 + str1[::-1]
- print str2
- str=raw_input('Enter a string:')
- i=0
- j=len(str)-1
- while 1:
- if str[i]==' ':
- i+=1
- else:
- break
- while 1:
- if str[j]==' ':
- j-=1
- else:
- break
- print str[i:j+1]
6-7 调试.看一下在例 6.5 中给出的代码(buggy.py)
(a)研究这段代码并描述这段代码想做什么.在所有的(#)处都要填写你的注释.
(b)这个程序有一个很大的问题,比如输入 6,12,20,30,等它会死掉,实际上它不能处理任何的偶数,找出原因.
(c)修正(b)中提出的问题.
- #功能:删除列表中能被输入的数整除的元素
- num_str=raw_input('Enter a number: ')
- num_num=int(num_str)
- fac_list=range(1,num_num+1)
- print "before:",fac_list
- i=0
- while i<len(fac_list):
- if num_num%fac_list[i]==0:
- del fac_list[i]
- else:
- i=i+1
- print "after:",fac_list
6-8 列表。给出一个整型值,返回代表该值得英文,比如输入89会返回“eight-nine”。附加题:能够返回符合英文语法规律的新式,比如输入89会返回“eighty-nine”。本练习中的值假定在0~1000。
- single=['','one','two','three','four','five','six','seven','eight','nine']
- double1=['ten','eleven','tweleve','thirting','fourting','fifting','sixting','seventing','eighting','nineting']
- double2=['','','twenty','thirty','fourty','fifty','sixty','seventy','eighty','ninety']
- numstr=raw_input('Enter a number 0--1000: ')
- numlen=len(numstr)
- num=int(numstr)
- if numlen==1:
- if int(numstr[0])>0:
- print single[num]
- else:
- print 'zero'
- elif numlen==2:
- if numstr[0]=='1':
- print double1[num-10]
- else:
- print double2[int(numstr[0])]+'-'+single[int(numstr[1])]
- elif numlen==3:
- if numstr[1]=='1':
- tmp=double1[int(numstr[2])]
- else:
- tmp=double2[int(numstr[1])]+'-'+single[int(numstr[2])]
- print single[int(numstr[0])]+' hundred '+tmp
- else:
- print 'one thousand'
6-9 转换。为练习5-13写一个姊妹函数,接受分钟数,返回小时数和分钟数。总时间不变,并且要求小时尽可能大。
- min=int(raw_input('please input a number as minutes: '))
- def totaltime(min):
- if min<60:
- print '0 hours %d minutes' %(min)
- elif min>=60:
- print '%d hours %d minutes' %(min/60,min%60)
- totaltime(min)
6-10 字符串。写一个函数,返回一个跟输入字符串相似的字符串,要求字符串的大小写反转,比如,输入“Mr.Ed”,应该返回“mR.eD”作为输出。
- ostr=raw_input('please input a string: ')
- def changecase(str):
- dstr=str.swapcase()
- print dstr
- changecase(ostr)
6-11 转换。
(a)创建一个从整型到IP地址的转换,如下格式: www.xxx.yyy.zzz。
(b)更新你的程序,使之可以逆转换。
- a)ip=int(raw_input('please input a number as IP: '))
- print 'IP'+'='+str(int(int(ip)/16777216) & 255)+'.'\
- +str(int(int(ip)/65536) & 255)+'.'+str(int(int(ip)/256) & 255)+'.'+str((int(ip) & 255))
- b)ip=raw_input('please input a IP like xxx.xxx.xxx.xxx : ')
- print 'IP'+'='+str(int(ip.split('.')[0])*16777216+int(ip.split('.')[1])*65536+\
- int(ip.split('.')[2])*256+int(ip.split('.')[3]))
6-12 字符串。
(a)创建一个名字为findchr()的函数,函数声明如下。
def findchr(string, char)
findchr()要在字符串string中查找字符char,找到就返回该值得索引,否则返回-1。不能用string.*find()或者string.*index()函数和方法。
(b)创建另一个叫rfindchr()的函数,查找字符char最后一次出现的位置。它跟findchr()工作类似,不过它是从字符串的最后开始向前查找的。
(c)创建第三个函数,名字叫subchr(),声明如下。
def subchr(string, origchar, newchar)
subchr()跟findchr()类似,不同的是,如果找到匹配的字符就用新的字符替换原先字符。返回修改后的字符串。
- a)
- def findchr(string, char):
- strlen=len(string)
- if char in string:
- for i in range(strlen):
- if char==string[i]:
- print i
- else:
- print -1
- b)
- def rfindchr(string, char):
- strlen=len(string)
- if char in string:
- for i in range(strlen):
- if char==string[-1-i]:
- print strlen-i-1
- break
- else:
- print -1
- c)
- def subchr(string, origchar, newchar):
- while(1):
- if findchr(string,origchar)==-1:
- break
- else:
- p=findchr(string,origchar)
- string=string[:p]+newchar+string[p+1:]
- print string
6-13 字符串.string模块包含三个函数,atoi(),atol()和atof(),他们分别负责把字符串转换成整型、长整型和浮点型数字。从Python 1.5起,Python的内建函数int()、long()、float()也可以做同样的事了,本文来,complex()函数可以把字符串转换成复数(然而1.5之前,这些转换函数只能工作于数字之上)
string模块中并没有实现一个atoc()函数,那么你来实现一个atoc(),接受单个字符串做参数输入,一个表示复数的字符串,例如'-1.23e+4-5.67j',返回相应的复数对象。你不能用eval()函数,但可以使用complex()函数,而且你只能在如下的限制之下使用:complex():complex(real, imag)的real和imag都必须是浮点值。
- str=raw_input('input a string as comlex number:')
- def atoc(str):
- strlen=len(str)
- for i in range(strlen):
- if '+'==str[-1-i] or '-'==str[-1-i]:
- op1=str[:-1-i]
- op2=str[-1-i:-1]
- break
- else:
- continue
- print complex(float(op1),float(op2))
- atoc(str)
6-14 随机数。设计一个“石头、剪子、布”游戏,有时又叫“Rochambeau”,你小时候可能玩过,下面是规则。你和你的对手,在同一时间做出特定的手势,必须是下面一种:石头、剪子、布。胜利者从下面的规则产生,这个规则本身是个悖论。(a)布包石头。(b)石头砸剪子。(c)剪子剪破布。在你的计算机版本中,用户输入他/她的选项,计算机找一个随机选项,然后由你的程序来决定一个胜利者或者平手。注意,最好的算法是尽量少使用if语句。
- import random
- print '0 siccsor'
- print '1 stone'
- print '2 fabric'
- print '3 quit'
- list = ['siccsor','stone','fabric']
- while True:
- i = input("pls input operation number: ")
- if (3 == i):
- break
- elif (i<0 or i>3):
- print 'Error input operation, try agin. 3 operation is quit\n'
- continue
- c = random.randint(0,2)
- if (i == c):
- print 'your is %s, computer is %s ' % (list[i],list[c])
- print 'it is draw'
- elif (i-c) == 2 or (i-c) == -1:
- print 'your is %s, computer is %s ' % (list[i],list[c])
- print 'computer win'
- else:
- print 'your is %s, computer is %s ' % (list[i],list[c])
- print 'you win'
6-15 转换。
(a)给出两个可识别格式的日期,比如MM/DD/YY或者DD/MM/YY格式。计算出两个日期之间的天数。
(b)给出一个人的生日,计算此人从出生到现在的天数,包括所有的闰月。
(c)还是上面的例子,计算出此人下次过生日还有多少天。
- import time
- def isLeapYear(year):
- if (year%4==0 and year%100!=0) or (year%400==0):
- return True
- def IntervalDays(str1,str2):
- month1 = [0,31,28,31,30,31,30,31,31,30,31,30,31]
- month2 = [0,31,29,31,30,31,30,31,31,30,31,30,31]
- #假定输入的日期都是正确的且后一个日期比前一个日期大
- bdate = str1.split('/')
- bdate[0],bdate[1],bdate[2]=int(bdate[0]),int(bdate[1]),int(bdate[2])
- edate = str2.split('/')
- edate[0],edate[1],edate[2]=int(edate[0]),int(edate[1]),int(edate[2])
- if bdate==edate:
- print '0 days'
- elif bdate[1]==edate[1] and bdate[2]==edate[2]:
- print '%d days' %abs(bdate[0]-edate[0])
- elif bdate[1]!=edate[1] and bdate[2]==edate[2]:
- bdays=0
- edays=0
- if isLeapYear(bdate[2]):
- for i in range(1,bdate[1]):
- bdays+=month2[i]
- bdays=bdays+bdate[0]
- for i in range(1,edate[1]):
- edays+=month2[i]
- edays=edays+edate[0]
- print '%d days' %abs(edays-bdays)
- else:
- for i in range(1,bdate[1]):
- bdays+=month1[i]
- bdays=bdays+bdate[0]
- for i in range(1,edate[1]):
- edays+=month1[i]
- edays=edays+edate[0]
- print '%d days' %abs(edays-bdays)
- elif bdate[2]!=edate[2]:
- days=0
- for i in range(bdate[2]+1,edate[2]):
- if isLeapYear(i):
- days+=366
- else:
- days+=365
- if isLeapYear(bdate[2]):
- for i in range(bdate[1]+1,13):
- days+=month2[i]
- days+=(month2[bdate[1]]-bdate[0])
- else:
- for i in range(bdate[1]+1,13):
- days+=month1[i]
- days+=(month1[bdate[1]]-bdate[0])
- if isLeapYear(edate[2]):
- for i in range(1,edate[1]):
- days+=month2[i]
- days+=edate[0]
- print '%d days' %(days)
- else:
- for i in range(1,edate[1]):
- days+=month1[i]
- days+=edate[0]
- print '%d days' %(days)
- if __name__=='__main__':
- #(a)
- date1=raw_input("input a start date as DD/MM/YYYY: ")
- date2=raw_input("input a end date as DD/MM/YYYY: ")
- IntervalDays(date1,date2)
- #(b)
- birth=raw_input("input a birth date as DD/MM/YYYY: ")
- today=str(time.strftime("%d/%m/%Y"))
- print 'today is %s ' %today
- IntervalDays(birth,today)
- #(c)
- birth=raw_input("input a birth date as DD/MM/YYYY: ")
- today=str(time.strftime("%d/%m/%Y"))
- print 'today is %s ' %today
- if today.split('/')[1]<birth.split('/')[1]:
- nbirth=str(birth.split('/')[0]+'/'+birth.split('/')[1]+'/'+today.split('/')[2])
- IntervalDays(today,nbirth)
- elif today.split('/')[1]==birth.split('/')[1]:
- if today.split('/')[0]<birth.split('/')[0]:
- print '%d days' %(int(birth.split('/')[0])-int(today.split('/')[0]))
- else:
- year=int(today.split('/')[2])+1
- nbirth=str(birth.split('/')[0]+'/'+birth.split('/')[1]+'/'+str(year))
- IntervalDays(today,nbirth)
6-16 矩阵。处理矩阵M和N的加和乘操作。
- a)两个矩阵的维数相等才能相加
- a = ([1,2,3],[4,5,6],[7,8,9])
- b = ([9,8,7],[6,5,4],[3,2,1])
- c = ([0,0,0],[0,0,0],[0,0,0])
- for i in range(0,len(a)):
- for j in range(0,len(b)):
- c[i][j] = a[i][j]+b[i][j]
- print c
- b)矩阵1的列数与矩阵2的行数相等两个矩阵才能相乘
- a = ([1,2,3,4],[5,6,5,8],[9,10,11,12])
- b = ([1,1,1],[1,1,1],[1,1,1],[1,1,1])
- c = ([0,0,0],[0,0,0],[0,0,0])
- for m in range(0,len(c)):
- for i in range(0,len(a)):
- for j in range(0,len(b)):
- c[m][i] += a[i][j]*b[j][i]
- print c
6-17 方法。实现一个叫myPop()的函数,功能类似于列表的pop()方法,用一个列表作为输入,移除列表的最新一个元素,并返回它。
- l=[1,2,3,4,5]
- def mypop(list):
- tmp=list[-1]
- del list[-1]
- return tmp
- print mypop(l)
- print l
6-18 zip()内建函数。在6.13.2节里面关于zip()函数的例子中,zip(fn,ln)返回的是什么?
返回一个列表,列表中的每个元素是一个元组
6-19 多列输出。有任意项的序列或者其他容器,把它们等距离分列显示。由调用者提供数据和输出格式。例如,如果你传入100个项并定义3列输出,按照需要的模式显示这些数据。这种情况下,应该是两列显示33个项,最后一列显示34个。你可以让用户来选者水平排序或者垂直排序。
- import random
- list = []
- nums = input("pls input a number for iterms: ")
- clns = input("pls input a number for columns: ")
- for i in range(0,nums):
- list.append(i+1)
- print list
- print '0 horizontal sort'
- print '1 vertical sort'
- print '2 quit'
- while True:
- i = input("pls input operation number: ")
- if (2 == i):
- break
- elif (i<0 or i>2):
- print 'Error input operation, try agin. 3 operation is quit\n'
- continue
- if (0 == i):
- n = 0
- for m in range(0,nums):
- print "%4d" %list[m],
- n += 1
- if n % clns == 0:
- elif (1 == i):
- n = 0
- for i in range(0,nums/clns+1):
- if i == nums/clns:
- for j in range(0,nums%clns):
- print 4*clns*' '+str(list[i*clns+j])
- else:
- for j in range(0,clns):
- print "%4s" %str(list[i+j*(nums/clns)]),
- n += 1
- if n % clns == 0:
- continue