我们可以写一个小程序,由用户输入数据,将数据存入到列表当中,也可以将数据从列表中查询出来,但像这种操作只适合在缓冲区内进行操作,因为存储在列表中的数据,程序执行完之后,数据会立即消失,所以我们可以通过文件的操作将我们要保存的数据存到文件当中,当然这只是一种方法,实际要存储数据的话我们会选择数据库,这样更方便,那么文件与目录的操作会实现什么样的功能。
第一节 文件读写
目标:
a.文件的打开和创建
b.文件读取
c.文件写入
d.内容查找和替换
e.文件删除,复制,重命名
f.目录操作
g.目录分析器
h.杀毒软件
j.系统垃圾清理工具
python文件读写
过程:打开--读写--关闭
a.python进行文件读写的函数是open或file
b.file_handler = open(filename,mode)
c.mode
[email protected]:~/Documents/py$ cat test.txt
www.cavt.net
i am milo
hello
首先使用open打开文件:
>>> fo = open(‘/home/hy/Documents/py/test.txt‘) 我们打开这个文件
>>> fo
<open file ‘/home/hy/Documents/py/test.txt‘, mode ‘r‘ at 0x7f00971af5d0>
>>> fo.read() 然后读取它
‘www.cavt.net\ni am milo\nhello\n‘
>>> fo.close() 我们关闭这个文件
>>> fo.read() 我们再次读取的时候已经读不了了
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: I/O operation on closed file
下面我们来通过使用file打开文件,并读取:
>>> f1 = file(‘/home/hy/Documents/py/test.txt‘)
>>> f1.read()
‘www.cavt.net\ni am milo\nhello\n‘
>>> f1.close()
>>> f1.read()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: I/O operation on closed file
下面我们使用w进行文件的写入:
如果源文件不存在会先创建,如果存在,它会先清空源文件的内容,然后再进行写操作
>>> fnew = open(‘/home/hy/Documents/py/new.txt‘,‘w‘) 回车后这个文件会被创建
>>> fnew.write(‘hello \ni am new\n‘) 写入的时候,内容会被保存到缓冲区中
>>> fnew.close() 关闭后数据被写入文件
下面我们对文件进行读写操作:
它会读取源文件,不会清空,,以追加的方式写入
>>> fnew = open(‘/home/hy/Documents/py/new.txt‘,‘r+‘) 注意‘r+‘这个参数
>>> fnew.read()
‘hello \ni am new\n‘
>>> fnew.write("new contents") 这里如果我们先读后写的话,他会以追加的方式写入
>>> fnew.close()
如果我们不想读,还想直接在后面追加,python中要使用a这种模式:
>>> f1 = open(‘new.txt‘,‘a‘)
>>> f1.write(‘aaaaaa\n‘)
>>> f1.close()
[email protected]:~/Documents/py$ cat new.txt 我们会发现我们所要写的东西已经被追加到了后面
hello
i am new
new contents
aaaaaa
第二节 文件对象的方法
1)文件对象方法
- FileObject.close()
- String = FileObject.readline([size])
- List = FileObject.readlines([size])
- String = FileObject.read([size])
- FileObject.next()
- FileObject.write(string)
- FileObject.writelines(List)
- FileObject.seek( 偏移量,选项)
- FileObject.flush()
>>> for i in open(‘new.txt‘): 我们使用open打开文件
... print i 然后使用print逐行读取数据
...
hello
i am new
new contents
aaaaaa
2)readline:
- 格式
String = FileObjectline.readline([size])
- 说明:
a.每次读取文件的一行
b.size:是指每行读取size个字节,直到行的末尾
>>> f1 = open(‘new.txt‘)
>>> f1.readline() 逐行读取操作,直至读完
‘hello \n‘
>>> f1.readline()
‘i am new\n‘
>>> f1.readline()
‘new contents\n‘
>>> f1.readline()
‘aaaaaa\n‘
>>> f1.readline()
‘‘
>>> f1 = open(‘new.txt‘)
>>> f1.readlines() 这次我们使用readlines读取,把每一个元素当做一个列表的元素,返回列表
[‘hello \n‘, ‘i am new\n‘, ‘new contents\n‘, ‘aaaaaa\n‘]
>>> f1.readlines()
[]
3)next:
- 格式:
FileObject.next()
- 说明:
返回当前行,并将文件指针到下一行
>>> f1 = open(‘new.txt‘)
>>> f1.readlines()
[‘hello \n‘, ‘i am new\n‘, ‘new contents\n‘, ‘aaaaaa\n‘]
>>> f1 = open(‘new.txt‘)
>>> f1.next() 我们使用next()这个方法和readline()其实是类似的
‘hello \n‘
>>> f1.next()
‘i am new\n‘
>>> f1.next()
‘new contents\n‘
>>> f1.next()
‘aaaaaa\n‘
4)write:
- 格式:
a.FileObject.write(string)
- 说明:
b.write和后面的writelines在写入前会是否清除文件中原来所有的数据,在重新写入粪新的内容,取决于打开文件的模式
5)writelines:
- 格式:
a.FileObject.writelines(List)
- 说明:
a.多行写
b.效率比write高,速度更快,少量写入可以使用write
>>> l = [‘one\n‘,‘two\n‘,‘three\n‘]
>>> f1 = open(‘new.txt‘,‘a‘)
>>> f1.writelines(l)
>>> f1.close()
[email protected]:~/Documents/py$ cat new.txt 在这里我们可以看到这三行已经被加进去了
hello
i am new
new contents
aaaaaa
one
two
three
>>> f1 = open(‘new.txt‘,‘r+‘)
>>> f1.read()
‘hello \ni am new\nnew contents\naaaaaa\none\ntwo\nthree\n‘
>>> f1.read()
‘‘
>>> f1.seek(0,0) 我们可以使用seek()这个函数将指针又重新移到开头
>>> f1.read()
‘hello \ni am new\nnew contents\naaaaaa\none\ntwo\nthree\n‘
>>> f1.seek(0,0)
>>> f1.seek(0,2) 当我们把后面的数字换成比0大的,它再次读取的时候就不会出现了
>>> f1.read()
‘‘
6)FileObject.seek(偏移量,选项)
- 选项=0时,表示将文件指针指向从文件头部到“偏移量”字节处。
- 选项=1时,表示将文件指针指向从文件的当前位置,向后移动“偏移量”字节。
- 选项=2时,表示将文件指针指向从文件的尾部,向前移动“偏移量”字节。
7)FileObject.flush()
- 提交更新
>>> f1.writelines(l) 当我们在不关闭文件的时候再次追加,文件的内容不会改变
>>> f1.flush() 我们需要做一下更新,然后再去查看的时候会发现文件的内容会再次改变
>>> f1.close()
8)文件查找
$ cat a.t
hello world
hello hello world
a.统计文件中hello的个数
9)文件内容替换
a.问题:把a.t中的hello替换为py,并保存结果到文件a2.t中
法一:
>>> fp1 = file("new.txt","r")
>>> fp2 = file("a2.t","w")
>>> for s in fp1.readlines():
... fp2.write(s.replace("new","py"))
...
>>> fp1.close()
>>> fp2.close()
法二:
>>> fp1 = file("new.txt","r+")
>>> s = fp1.read()
>>> fp1.seek(0,0)
>>> fp1.write(s.replace("new","py"))
>>> fp1.close()
[email protected]:~/Documents/py$ cat new.txt
hello
i am py 我们发现里面的new已经全部被换成了py
py contents
aaaaaa
one
two
three
one
two
three
e
第三节 OS模块
1)目录操作就是通过python来实现目录的创建,修改,遍历等功能
2)import os
- 目录操作需要调用os模块
- 比如:
os.mkdir(‘/home/hy/Document/py‘)
>>> import os
>>> os.mkdir(‘test‘)
[email protected]:~/Documents/py$ ls
test 我们可以看到test这个目录已经存在了
>>> os.makedirs(‘a/b/c/d‘) 我们可以使用这个命令创建多级目录
>>> os.rmdir(‘test‘) 删除test这个目录
>>> os.removedirs(‘a/b/c/d‘) 删除多级目录
>>> import os
>>> os.listdir(‘.‘) 如果我们想列出目录下的内容,我们要使用list来列出
[‘1.pyo‘, ‘7.py‘, ‘a2.t‘, ‘cal.pyc‘, ‘2.py‘, ‘contact_list.txt‘, ‘10.py‘, ‘__init__.py‘, ‘new.py‘, ‘5.py‘, ‘4.py‘, ‘14.py‘, ‘if_else.py‘, ‘contact_query.py‘, ‘16.py‘, ‘find.py‘, ‘8.py‘, ‘13.py‘, ‘test.txt‘, ‘9.py‘, ‘3.py‘, ‘cal.py‘, ‘if.py‘, ‘ask_for.py‘, ‘17.py‘, ‘12.py‘, ‘1.pyc‘, ‘while.py‘, ‘1.py‘, ‘__init__.pyc‘, ‘CSDN.py‘, ‘new.txt‘, ‘ask_name_if_else.py‘, ‘11.py‘, ‘jpg‘, ‘6.py‘, ‘15.py‘]
>>> os.listdir(‘/‘)
[‘run‘, ‘root‘, ‘cdrom‘, ‘etc‘, ‘dev‘, ‘vmlinuz.old‘, ‘opt‘, ‘tmp‘, ‘initrd.img.old‘, ‘usr‘, ‘sbin‘, ‘var‘, ‘bin‘, ‘lib32‘, ‘lost+found‘, ‘initrd.img‘, ‘media‘, ‘lib64‘, ‘srv‘, ‘proc‘, ‘vmlinuz‘, ‘sys‘, ‘mnt‘, ‘lib‘, ‘boot‘, ‘home‘]
>>> os.getcwd() 通过它可以获得当前的路径
‘/home/hy/Documents/py‘
>>> os.chdir(‘/‘) 切换目录到 / 下
>>> os.listdir(‘.‘)
[‘run‘, ‘root‘, ‘cdrom‘, ‘etc‘, ‘dev‘, ‘vmlinuz.old‘, ‘opt‘, ‘tmp‘, ‘initrd.img.old‘, ‘usr‘, ‘sbin‘, ‘var‘, ‘bin‘, ‘lib32‘, ‘lost+found‘, ‘initrd.img‘, ‘media‘, ‘lib64‘, ‘srv‘, ‘proc‘, ‘vmlinuz‘, ‘sys‘, ‘mnt‘, ‘lib‘, ‘boot‘, ‘home‘]
>>> os.getcwd()
‘/‘
下面我们来写一个小程序,让这个程序来遍历一个目录:
[email protected]:~/Documents/py$ mkdir testdir
[email protected]:~/Documents/py$ cd testdir/
[email protected]:~/Documents/py$ tree testdir/
testdir/
├── f1
├── f2
├── f3
└── jpg
└── getjpg.py
如果我们想要将这个目录下的文件的绝对路径都显示出来的话,我们应该如何操作:
第四节 目录遍历
1)案例
- 系统垃圾清理小工具
2)方式:
- 递归函数
- os.walk()函数
[email protected]:~/Documents/py$ vim list_dir_file.py
1 #!/usr/bin/python
2 #coding:utf8
3
4 import os
5
6 def dirlist(path):
7 filelist = os.listdir(path)
8 fpath = os.getcwd()
9 allfile = []
10 for filename in filelist:
11 allfile.append(fpath+‘/‘+filename)
12 return allfile
13
14 allfile = dirlist(‘testdir‘)
15 print allfile
[email protected]:~/Documents/py$ python list_dir_file.py
[‘/home/hy/Documents/py/f3‘, ‘/home/hy/Documents/py/f1‘, ‘/home/hy/Documents/py/f2‘, ‘/home/hy/Documents/py/jpg‘]
另外一种方法:
1 #!/usr/bin/python
2 #coding:utf8
3
4 import os
5
6 def dirlist(path):
7 filelist = os.listdir(path)
8 fpath = os.getcwd()
9 allfile = []
10 for filename in filelist:
11 filepath = os.path.join(fpath,filename) 我们使用这个函数可以直接将文件的路径返回
12 allfile.append(filepath) 然后再去追加
13 return allfile
14
15 allfile = dirlist(‘testdir‘)
16 print allfile
我们可以使用下面的遍历来进行递归操作完成递归目录的文件的操作:
1 #!/usr/bin/python
2 #coding:utf8
3
4 import os
5
6 def dirlist(path):
7 filelist = os.listdir(path)
8 fpath = os.getcwd()
9 allfile = []
10 for filename in filelist:
11 filepath = os.path.join(fpath,filename)
12 if os.path.isdir(filepath): 判断是否是一个目录,如果是执行递归操作
13 dirlist(filepath) 这里我们使用了一个递归操作
14 allfile.append(filepath)
15 return allfile
16
17 allfile = dirlist(‘testdir‘)
18 print allfile
第三种:我们要想直接去遍历出包括递归目录的所有目录的文件的绝对路径
1 #!/usr/bin/python
2 #coding:utf8
3
4 import os
5
6 def dirlist(path):
7 filelist = os.listdir(path)
8 for filename in filelist:
9 filepath = os.path.join(path,filename)
10 if os.path.isdir(filepath):
11 dirlist(filepath)
12 print filepath
13
14 allfile = dirlist(‘/home/hy/Documents/py/testdir‘)
[email protected]:~/Documents/py$ python list_dir_file.py 我们可以看到所有的文件包括递归文件都被列出
/home/hy/Documents/py/testdir/f3
/home/hy/Documents/py/testdir/f1
/home/hy/Documents/py/testdir/f2
/home/hy/Documents/py/testdir/jpg/getjpg.py
/home/hy/Documents/py/testdir/jpg
[email protected]:~/Documents/py$ vim list_dir_file.py
1)os.walk()
- 函数声明:os.walk(path)
2)该函数返回一个元组,该元组有3个元素,这3个元素分别表示每次遍历的路径名,目录列表和文件列表
>>> g=os.walk(‘/home/hy/Documents/py/testdir‘) 使用walk直接做的话,他会直接做一个遍历,我们将其返回值定义成了一个生成器
>>> g.next()
(‘/home/hy/Documents/py/testdir‘, [‘jpg‘], [‘f3‘, ‘f1‘, ‘f2‘])
下面我们对这个返回的元组做一个拆分,(路径,目录,文件名)
>>> for path,d,filelist in os.walk(‘/home/hy/Documents/py/testdir‘):
... for filename in filelist:
... os.path.join(path,filename)
...
‘/home/hy/Documents/py/testdir/f3‘
‘/home/hy/Documents/py/testdir/f1‘
‘/home/hy/Documents/py/testdir/f2‘
‘/home/hy/Documents/py/testdir/jpg/getjpg.py‘
练习:1.我们将所有文件名含有f的文件全部删除2.当文件中含有abcd这样的字符串的时候就删除
第五节 异常处理
1)异常以及异常抛出
异常抛出机制,为程序开发人员提供了一种在运行时发现错误,进行恢复处理,然后继续执行的能力。
下面是一个异常处理实例:
[email protected]:~/Documents/py$ vim te.py
1 try:
2 open(‘abc.txt‘)
[email protected]:~/Documents/py$ python te.py
File "te.py", line 3
^
SyntaxError: invalid syntax 我们在执行的时候会出现一个异常,因为这个文件是不存在的
[email protected]:~/Documents/py$ vim te.py
1 try:
2 open(‘abc.txt‘)
3 except IOError,msg: 我们给它加上一个接受这个异常
4 pass
[email protected]:~/Documents/py$ python te.py
[email protected]:~/Documents/py$ 我们发现不在出现异常,这时异常已经被处理了
[email protected]:~/Documents/py$ vim te.py 这样用户体验就会好一点
1 #!/usr/bin/python
2 #coding:utf8
3
4 filename = raw_input(‘请输入你要操作的文件:‘)
5 try:
6 open(filename)
7 except IOError,msg:
8 print "你指定的文件不存在"
9 except NameError,msg:
10 print "内部变量调用错误"
2)抛出机制
a.如果在运行时发生异常的话,解释器会查找相应的处理语句(称为handler)。
b.要是在当前函数里没有找到的话,它会将异常传递给上层的调用函数,看看那里不能处理。
c.如果在最外层(全局“main”)还是没有找打的话,解释器就会退出,同时打印出traceback以便让用户找出错误产生的原因
注意:虽然大多数错误会导致异常,但一个异常不一定代表错误。有时候他们只是一个警告,有时候他们可能是一个终止信号,比如退出循环等。
1 #!/usr/bin/python
2 #coding:utf8
3
4 filename = raw_input(‘请输入你要操作的文件:‘)
5 try:
6 f = open(filename)
7 print hello
8 except IOError,msg:
9 print "你指定的文件不存在"
10 except NameError,msg:
11 print "内部变量调用错误"
12 finally: 无论异常代码会不会被执行,finally下的语句都会被执行都会被执行
13 f.close()
3)finally子句
python提供try-finally子句用来表述这样的情况:我们不关心扑抓到是什么错误,无论错误是不是发生,这些代码“必须”运行,比如文件关闭,释放锁,把数据库链接还给连接池等。比如:
4)raise抛出异常
到目前为止,我们只讨论了如何扑捉异常,那么如何抛出异常呢?
使用raise来抛出异常:
1 #!/usr/bin/python
2 #coding:utf8
3
4 filename = raw_input(‘请输入你要操作的文件:‘)
5 try:
6 f = open(filename)
7 print hello
8 except IOError,msg:
9 print "你指定的文件不存在"
10 except NameError,msg:
11 print "内部变量调用错误"
12 finally:
13 try: 在异常当中我们还可以再嵌套异常
14 f.close()
15 except NameError,msg:
16 pass
17
18 if filename == "hello":
19 raise TypeError("nothing!!!!")
第六节 Mysql数据库模块
>>> import MySQLdb
>>> conn = MySQLdb.connect(user=‘root‘,passwd=‘‘,host=‘localhost‘)
>>> cur = conn.cursor() 创建一个游标保存到cur这个对象中
>>> conn.select_db(‘hy_db‘) 连接到一个库中
>>> cur.execute("insert into hy_tb(name,age,university) value(‘aa‘,22,‘xiyou‘)")
1L 向一张表中插入一条记录
mysql> select * from hy_tb;
+------+------+------------+
| name | age | university |
+------+------+------------+
| hy | 24 | xiyou |
| milo | 25 | zhongshan |
+------+------+------------+
2 rows in set (0.00 sec)
mysql> select * from hy_tb;
+------+------+------------+
| name | age | university |
+------+------+------------+
| hy | 24 | xiyou |
| milo | 25 | zhongshan |
| aa | 22 | xiyou | 我们可以看一下这个记录已经被插入了
+------+------+------------+
>>> sqli = "insert into hy_tb(name,age,university) value(%s,%s,%s)"
>>> cur.execute(sqli,(‘csvt‘,5,‘hello‘)) 我们通过上面定义,再次插入的时候就不需要那么麻烦另外
1L
mysql> select * from hy_tb;
+------+------+------------+
| name | age | university |
+------+------+------------+
| hy | 24 | xiyou |
| milo | 25 | zhongshan |
| aa | 22 | xiyou |
| csvt | 5 | hello |
+------+------+------------+
>>> sqlim = "insert into hy_tb(name,age,university) values(%s,%s,%s)" 一次插入多条值
>>> cur.executemany(sqlim,[(‘vt‘,5,‘hello‘),(‘c‘,1,‘s‘),(‘s‘,2,‘m‘)]) 注意函数
3L
>>> cur.execute(‘delete from hy_tb where age=2‘) 我们可以删除多条记录
1L
>>> cur.execute(‘delete from hy_tb where age=1‘)
1L
在数据库里面查看的时候我们的age=1和age=2的数据就没有了
>>> cur.execute("update hy_tb set name=‘xyt‘ where age=22") 修改里面的一条记录
1L
>>> cur.execute(‘select * from hy_tb‘) 实现查询
5L
>>> cur.fetchone() 这样每次只能顺序的查询到一条记录
(‘hy‘, 24L, ‘xiyou‘)
>>> cur.fetchone()
(‘milo‘, 25L, ‘zhongshan‘)
>>> cur.scroll(0,‘absolute‘) 使用scroll来定位移动的位置
>>> cur.fetchone()
(‘hy‘, 24L, ‘xiyou‘)
>>> cur.fetchmany(5) 一次取多条记录
((‘xyt‘, 22L, ‘xiyou‘), (‘csvt‘, 5L, ‘hello‘), (‘vt‘, 5L, ‘hello‘))
>>> cur.scroll(0,‘absolute‘) 在这里我们将指针移动到表头
>>> cur.fetchmany(5)
((‘hy‘, 24L, ‘xiyou‘), (‘milo‘, 25L, ‘zhongshan‘), (‘xyt‘, 22L, ‘xiyou‘), (‘csvt‘, 5L, ‘hello‘), (‘vt‘, 5L, ‘hello‘))
>>> cur.fetchmany(cur.execute("select * from hy_tb")) 我们在查询的时候想直接显示出来
((‘hy‘, 24L, ‘xiyou‘), (‘milo‘, 25L, ‘zhongshan‘), (‘xyt‘, 22L, ‘xiyou‘), (‘csvt‘, 5L, ‘hello‘), (‘vt‘, 5L, ‘hello‘))
>>> cur.close() 增删改查都执行完了,我们需要关闭,先关闭游标
>>> conn.close() 然后在关闭连接
第七节 面向对象编程之类和对象
python它将所有的事物都看做是对象
1)类和对象
面向过程和面向对象的编程
面向过程的编程:函数式编程,C程序等
面向对象的编程;C++,java,Python等
类和对象:是面向对象中的两个重要概念
类:是对象事物的抽象,比如:汽车模型
对象:是类的一个实例,比如:QQ轿车,大客车
范例说明:
汽车模型可以对汽车的特征和行为进行抽象,然后可以实例化为一台真实的汽车视体出来。
2)python类定义
python类的定义:
使用class关键字定义一个类,并且类名的首字母要大写;
当程序员需要创建的类型不能用简单类型表示时就需要创建类;
类把需要的变量和函数组合在一起,这样包含也称之为“封装”。
python类的结构
>>>class 类名:
... 成员变量
... 成员函数
...
>>> class Test:
... first = 123
... second = 456
... def f(self):
... return ‘test‘
...
>>> 这样我们就定义好了一个类
在类的方法中至少有一个参数self
>>> hy = Test() 我们去使用这个类
>>> hy.f()
‘test‘
>>> hy.first 同时也可以查看里面的属性
123
对象的创建:
创建对象的过程称之为实例化;当一个对象被创建后,包含三个方面的特性:对象的句柄、属性和方法。
句柄用于区分不同的对象
对象的属性和方法与类中的成员变量和成员函数对应
>>> if __name__ == "__main__":
... myClass1 = MyClass() #创建类的一个实例(对象)
...