一看就懂的Python基础之【文件和异常】

简单生活的秘诀是:有自己的收入,有自己喜欢的人,有自己的追求。远离不喜欢你的人。

一、读取整个文件

(一)整篇读取

在你所写python代码的文件夹中,创建一个文本文档复制保存下面数字:

3.1415926535
  8979323846
  2643383279

下面用python 读取这个文件:

with open("pi_digits.txt") as file_object:
    contents=file_object.read()
    print(contents)

1、函数open()返回一个表示文件的对象。此处,open("pi_digits.txt")返回一个代表文件pi_digits.txt的对象。

2、python 将代表pi_digits这个文件的对象存储在file_object中,用的语句是 as +file_object

【注意】as file_object后面是有个分号的:

3、read()读取文件的全部内容,并将其作为一个长字符串存储在变量contents中,这样,通过打印contents的值就可以将这个文本的全部内容显示出来。

4、【重点】这里用的open没用close()是因为,这里使用了with这个结构,关键字with 在不需要访问文件后将其关闭。

为什么不用colse()呢?

其一:如果程序存在bug,导致 colse()语句无法执行,文件将不会关闭,会导致数据丢失或受损。

其二:关闭文件的时机不好控制,如果过早的关闭会导致需要访问时无法访问。

使用with结构,你只管打开文件夹,并在需要的时候打开它,python自动会在合适的时机关闭它。

 

下面是在任何文件夹中读取数据:

file_path='C:\\Users\\Administrator\\Desktop\\pi_digits.txt'
with open(file_path) as file_object:
	contents=file_object.read()
	print(contents)

【注意】文件的路径要么是加两个反斜杠要么是在引号前面加个r,否则会报错。详情见这里,别问我怎么知道的 T ^ T

 

(二)逐行读取

file_path='C:\\Users\\Administrator\\Desktop\\pi_digits.txt'
with open(file_path) as file_object:
	for line in file_object:
		print(line)

即通过一个for 循环把文件按行打出。 结果如下:

上面结果中每行都多了空行,是因为文件内每行末尾本身都有一个看不见的换行符,而print() 语句也会加一个换行符。这样每行都有了两个换行符。可在print 语句中用rstrip()来去掉换行。即把输出语句改为:print(contents.rstrip())

结果如下 :

(三)创建一个包含文件各行内容的列表

使用with关键字时,open()返回的文件对象只在with代码块内可用。如果要在with代码块外访问文件的内容,可在with代码块内将文件夹的各行存储在一个列表中,并在with代码块外使用该列表。 

file_path='C:\\Users\\Administrator\\Desktop\\pi_digits.txt'
with open(file_path) as file_object:
	lines=file_object.readlines()

for line in lines:
	print(line.rstrip())

【重点】方法readlines从文件中读取每一行并将其存储在一个列表中。列表中的每个元素其实是文件中的每一行。

(四)使用文件中的内容

file_path='pi_digits.txt'
with open(file_path) as file_object:
	lines=file_object.readlines()
pi_string=''
for line in lines:
	pi_string+=line.strip()

print(pi_string)
print(len(pi_string))

上面代码把文件中的内容存储到一个列表中,因为读取文本文件时,python将其中的所有文本都解读为字符串,所以列表中每个元素是字符串。pi_string变量先是一个空串再拼接列表中的一系列字符串,最后得到一个完整的字符串并打印。

【注意】也正因python在解读文本文件时把所有内容都解读为字符串,当你读取是数字时它也是字符串,如果是整数,你需要将其用 int() 转换为数字再使用。如果是浮点数,你需要转换为float 再使用。

(五)包含一百万位的大型文件

你需只要一个圆周率的文件,以保证百万位。然后按上面的方式操作即可。

file_path=r'C:\Users\Administrator\Desktop\pi_digits.txt'
with open(file_path) as file_object:
	lines=file_object.readlines()
	
pi_string=''
for line in lines:
	pi_string+=line.strip()

print(pi_string[:52]+"...")
print(len(pi_string))

思考题:如何用python计算出圆周率并保存后100 0000位小数呢?

如果你没有一个百万位数字的文件,这里可以下载。

链接:https://pan.baidu.com/s/1v6xinNfhlW1opd0ksineCQ 
提取码:yl31

二、写入文件

(一)写入空白文件

file_name="Alice in wonderLand"
with open(file_name,'w') as file_object:
    file_object.write("She is in a magic world! ")

【重点】写入文件只是在open的括号里多了第二个参数。w代表覆盖原文件内容写入新内容,a代表在原文内容后附加新内容,r代表读取文件内容。

【注意】python 只能把字符串写入文件,如果你想写入数值需要用str()将数值变成字符串。

(二)写入多行时注意事项

file_name="programming.txt"
with open(file_name,'w') as file_object:
    file_object.write("The most important time in your life is now.\n")
    file_object.write("Because only this moment can you control.\n")
    file_object.write("The past is over and the future will always come.\n")
    file_object.write("Anything you want to get ,Just do it.\n")

所谓写入多行时的“注意事项”就是一定要在写入的内容后面加上换行符“\n”,否则写入的内容都会写在一行上。

(三)附加到文件

file_name="alice.txt"
with open(file_name,'a') as file_objec和:
    file_object.write("Do not let your self regert.\n")
    file_object.write("Because your life is just this,not the imagine in your mind.\n")

三、异常

异常 在python中是一个特殊对象,python 使用被称为“异常”的特殊对象来管理执行期间发生的错误。每发生错误都创建对象。

如果你编写了处理异常的代码,python在遇到问题时就会执行下去,否则会报出一个traceback并停止执行。

异常,使用try-except来处理。使用了try-except代码块时,即使出现异常程序也可以继续进行,显示出你编写的错误信息而不会显示trackback。

(一)ZeroDivisionError异常

try:
    print(5/0)
except ZeroDivisionError:
    print("U can't divide by zero!")

try-except代码块类似于java中的try-catch代码块。try中代码出问题时会执行except中的内容而不是报出traceback给用户。我们尽量避免报出traceback而是报出易读懂的内容。

下面模拟一个做除法的计算器:

print("Give me to number and i will divide them.")
print("Enter 'q' to quit.\n")
while True:
	num_1=input("please enter your first number: ")
	if num_1=='q':
		break
	num_2=input("please enter your second number: ")
	if num_2=='q':
		break
	answer = int(num_1)/int(num_2)
	print(answer)

这里有一点值得借鉴:每输入一个数后就判断这个数是不是“q”,而不是输入两个数字后再判断有没有“q”,而且,使用input时,python将输入内容理解为字符串,不要忘记把字符串变成数值。

try -except-else代码块中,else代码块内写的是try中没有出问题时需要执行的代码。

try-except-else代码块工作原理:

把有可能引发异常的代码放在try中,把try成功执行时才执行的代码放在else中。except代码块的内容负责告诉python当try中的代码异常时该怎么做。

(二)FileNotFoundedError异常

就是在使用文件时找不到文件。

file_name="Alice in wonderLand"
try:
    with open(file_name,'w') as file_o:
        file_o.write("I will try my best to conquer any hardship.")
except FileNotFoundError:
    msg="Sorry we can't find "+file_name+" in this computer."
    print(msg)

(三)分析文本

应用一:把句子中单词划分出来并存储在一个列表中,就是一个split()方法。

title="Alice in wonderLand"
print(title.split())

应用二:在划分出单词的基础上可以统计出一本书有多少单词。

title="Alice in wonderLand"
try:
    with open(title) as file_o:
        contents=file_o.read()
except FileNotFoundError:
    print("SOrry the "+title_+"does not exit.\n")
else:
    words=contents.split()
    num=len(words)
    print("The file"+title+" have '+str(num)+" words.")

(四)综合应用

写一个函数,用事业统计文件中的单词个数。

def word_count(file_name):
	'''统计一个文件中有多少个单词'''
	try:
		with open(file_name) as file_object:
			contents=file_object.read()
	except FileNotFoundError:
		print("Sorry the "+"\'"+file_name+"\'"+" does not exit.")
	else:
		words=contents.split()
		num=len(words)
		print("The "+file_name+" have "+str(num)+" words in it.")

file_name="alice.txt"
word_count(file_name)
file_name2='aha.java'
word_count(file_name2)

 四、存储数据

值得一提的是,我们始终会把数据保存在某种数据结构中,如列表或字典。比如把用户当前关卡记录在一个列表中。

模块json让你能够把简单的PYTHoN数据结构存储到文件中,并在程序再次运行时加载 该文件中的数据。

你还可以使用json在程序之间分享数据。

存储数据:json.dump()

读取数据:json.load()

#引入json,把一个列表写入一个文件中。
import json
numbers=[1,3,5,7,11,13]

filename='numbers.json'
with open(filename,'w') as f:
    json.dump(numbers,f)
#使用json.load将这个列表读取到内存中。注意读取时是没有'r'的
import json

filename="numbers.json"
with open(filename) as f:
    numbers=json.load(f)
print(numbers)

实用举例:

用户首次登陆记住他的名字:

import json

user_name=input("Please enter your name: ")
filename="username.txt"
with open(filename,'w') as f:
	json.dump(user_name,f)
	print("Welconem you, "+user_name+".")

现在,向存储的这个用户发一条消息,问是否从上次记录开始玩游戏:

import json

file_name="username.txt"
with open(file_name) as f:
	name=json.load(f)
	print(name.title()+" do you want to start at your last record?")

现在把上面两段代码融合一下:

import json
#先从文件中加载
#如果文件中不存在,提示输入用户名并存储它。
try:
	filename="username.txt"
	with open(filename) as f:
		name=json.load(f)
except FileNotFoundError:
	user_name=input("Please enter your name: ")
	with open(filename,'w') as f:
		json.dump(user_name,f)
		print("Welconem you, "+user_name+".")
else:
	print(name.title()+" do you want to start at your last record?")

【重构】代码能够正确运行,但可以做进一步的改进——将代码划分为一系列完成具体工作的函数。这样的过程叫重构。‘

import json

def greet():
	'''问候用户,并指出其名字'''
	filename="username.txt"
	try:
		with open(filename) as f:
			name=json.load(f)
	except FileNotFoundError:
		user_name=input("Please enter your name: ")
		with open(filename,'w') as f:
			json.dump(user_name,f)
			print("Welconem you, "+user_name+".")
	else:
		print(name.title()+" do you want to start at your last record?")
greet()

’上面 的代码还不够好,因为我们要做到一个函数只执行一个任务。

import json
file_name="username.json"
def get_sorted_user():
	'''获取存储的用户名'''
	with open(file_name) as f:
		user_name=json.load(f)
	if user_name:
		return user_name
	else:
		return None

def get_new_user():
	'''获取新的用户名'''
	user_name=input("Enter your name: ")
	with open(file_name,'w') as f:
		json.dump(user_name,f)
	return user_name

def greet():
	'''问候用户并指出名字'''
	user=get_sorted_user()
	if user:
		print("Welcome "+user+"~")
	else:
		user=get_new_user()
		print("Welcome "+user+"~")
greet()

最终版本的文件中,一个函数都执行单一而清晰的任务。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

纸城

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值