请选择 进入手机版 | 继续访问电脑版
设为首页收藏本站

Crossin的编程教室

 找回密码
 立即加入
查看: 46269|回复: 65

【Python 第33课】 处理文件中的数据

[复制链接]

10

主题

0

好友

52

积分

注册会员

Rank: 2

发表于 2013-7-25 19:33:30 |显示全部楼层
本帖最后由 mty1111 于 2013-7-25 19:34 编辑

我们已经知道了如何读取和写入文件。有了这两个操作文件的方法,再加上对文件内容的处理,就能写一些小程序,解决不少日常的数据处理工作。

比如我现在拿到一份文档,里面有某个班级里所有学生的平时作业成绩。因为每个人交作业的次数不一样,所以成绩的数目也不同,没交作业的时候就没有分。我现在需要统计每个学生的平时作业总得分。

记得我小的时候,经常有同学被老师喊去做统计分数这种“苦力”。现在电脑普及了,再这么干就太弱了。用python,几行代码就可以搞定。

看一下我们的文档里的数据:
  1. #-- scores.txt
  2. 刘备 23 35 44 47 51
  3. 关羽 60 77 68
  4. 张飞 97 99 89 91
  5. 诸葛亮 100
复制代码
1.先把文件读进来:
  1. f = file('scores.txt')
复制代码
2.取得文件中的数据。因为每一行都是一条学生成绩的记录,所以用readlines,把每一行分开,便于之后的数据处理:
  1. lines = f.readlines()
  2. f.close()
复制代码
提示:在程序中,经常使用print来查看数据的中间状态,可以便于你理解程序的运行。比如这里你可以print lines,看一下内容被存成了什么格式。

3.对每一条数据进行处理。按照空格,把姓名、每次的成绩分割开:
  1. for line in lines:
  2.    data = line.split()
复制代码
接下来的4、5两个步骤都是针对一条数据的处理,所以都是在for循环的内部。

4.整个程序最核心的部分到了。如何把一个学生的几次成绩合并,并保存起来呢?我的做法是:对于每一条数据,都新建一个字符串,把学生的名字和算好的总成绩保存进去。最后再把这些字符串一起保存到文件中:
  1. sum = 0
  2. for score in data[1:]:
  3.    sum += int(score)
  4. result = '%s\t: %d\n' % (data[0], sum)
复制代码
这里几个要注意的点:
对于每一行分割的数据,data[0]是姓名,data[1:]是所有成绩组成的列表。
每次循环中,sum都要先清零。
score是一个字符串,为了做计算,需要转成整数值int。
result中,我加了一个制表符\t和换行符\n,让输出的结果更好看些。

5.得到一个学生的总成绩后,把它添加到一个list中。
  1. results.append(result)
复制代码
results需要在循环之前初始化results = []

6.最后,全部成绩处理完毕后,把results中的内容保存至文件。因为results是一个字符串组成的list,这里我们直接用writelines方法:
  1. output = file('result.txt', 'w')
  2. output.writelines(results)
  3. outpus.close()
复制代码
大功告成,打开文件检验一下结果吧。

以下是完整程序,把其中print前面的注释符号去掉,可以查看关键步骤的数据状态。不过因为字符编码的问题,list的中文可能会显示为你看不懂的字符。
  1. f = file('scores.txt')
  2. lines = f.readlines()
  3. #print lines
  4. f.close()

  5. results = []

  6. for line in lines:
  7.    #print line
  8.    data = line.split()
  9.    #print data
  10.   
  11.    sum = 0
  12.    for score in data[1:]:
  13.        sum += int(score)
  14.    result = '%s \t: %d\n' % (data[0], sum)
  15.    #print result

  16.    results.append(result)

  17. #print results
  18. output = file('result.txt', 'w')
  19. output.writelines(results)
  20. output.close()
复制代码
0.jpg


#==== Crossin的编程教室 ====#
微信ID:crossincode
QQ群:312723402

面向零基础初学者的编程课
每天5分钟,轻松学编程

回复

使用道具 举报

0

主题

0

好友

20

积分

新手上路

Rank: 1

发表于 2014-2-6 23:59:06 |显示全部楼层
data[1:]
这个是下标为1以后的数组元素吗?
回复

使用道具 举报

174

主题

45

好友

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

发表于 2014-2-7 11:55:46 |显示全部楼层
福尔摩斯683 发表于 2014-2-6 23:59
data[1:]
这个是下标为1以后的数组元素吗?

是的,从1开始,包括1
如果是数字在冒号后面,则是到那个数字前,不包括它
#==== Crossin的编程教室 ====#
微信ID:crossincode
网站:http://crossincode.com
回复

使用道具 举报

0

主题

0

好友

24

积分

新手上路

Rank: 1

发表于 2014-5-31 10:33:31 |显示全部楼层
本帖最后由 Go_for_Math 于 2014-5-31 11:18 编辑

Traceback (most recent call last):
  File "E:/Python27/lesson/lesson33.py", line 10, in <module>
    result='%s\t%d\n'%(data[0],sum)
IndexError: list index out of range


我一运行就出现这样的提示,没法继续,这个原因“list index out of range”具体是啥呢?

(⊙o⊙)…找到原因了,因为我保存的score.txt文件里多加了2个回车,导致多了1行为空,就会报错(如果只是一个回车就行的样子)
回复

使用道具 举报

174

主题

45

好友

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

发表于 2014-5-31 16:00:52 |显示全部楼层
Go_for_Math 发表于 2014-5-31 10:33
Traceback (most recent call last):
  File "E:/Python27/lesson/lesson33.py", line 10, in
    result= ...

空行导致第一个data是空list,访问data[0],0这个index就out了data这个list的range
#==== Crossin的编程教室 ====#
微信ID:crossincode
网站:http://crossincode.com
回复

使用道具 举报

0

主题

0

好友

4

积分

新手上路

Rank: 1

发表于 2014-6-7 09:23:20 |显示全部楼层
我将字符输出打印,出现这个
['EncFile\x00\x01\x00\x00\x02\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00notepad.exe\x00\x00\x00\x00\x00\x00\x00\x00\x00\xfc\x1b\x00\x00J\xf4\xa2\t\xda\xa3 7\xa6\xb1G\xdc\xaa\x96\x9c\x9dk\x80\xa0\x08\xd1s']   
回复

使用道具 举报

174

主题

45

好友

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

发表于 2014-6-8 14:21:21 |显示全部楼层
Eagle 发表于 2014-6-7 09:23
我将字符输出打印,出现这个
['EncFile\x00\x01\x00\x00\x02\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00 ...

你这是把一个list对象整个打印了,所以程序不会解码。你要把list里面的元素拿出来打印
#==== Crossin的编程教室 ====#
微信ID:crossincode
网站:http://crossincode.com
回复

使用道具 举报

匿名  发表于 2014-7-26 20:13:23
f = file('E:/scores.txt')
output = file('E:/result.txt', 'w')
我把他们写成
f = file('E:\scores.txt')
output = file('E:\result.txt', 'w')
就是报错!!原来  \和/不一样。
回复

使用道具

174

主题

45

好友

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

发表于 2014-7-27 16:49:24 |显示全部楼层
QQ_E29166 发表于 2014-7-26 20:13
f = file('E:/scores.txt')
output = file('E:/result.txt', 'w')
我把他们写成

\是转义字符,会把很多字符变成特殊含义的,要用也是\\
#==== Crossin的编程教室 ====#
微信ID:crossincode
网站:http://crossincode.com
回复

使用道具 举报

0

主题

0

好友

36

积分

新手上路

Rank: 1

发表于 2015-3-14 16:25:53 |显示全部楼层
#coding:utf-8
#读取文件计算学生总成绩
#read file
results = []
f = file('scoreDate.txt')
scores = f.readlines()
for line in scores :
                data = line.split(' ')
                count = 0
                for core in data[1:] :
                                count += int(core)
                result = data[0] + '' + str(count) + '\n'
                results.append(result)
f2 = file('countScores.txt','w')
f2.writelines(results)
print '总成绩已经计算完毕啦!!快去查看吧!'
f2.close()
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即加入

QQ|手机版|Archiver|Crossin的编程教室 ( 苏ICP备15063769号  

GMT+8, 2024-3-29 21:01 , Processed in 0.028187 second(s), 25 queries .

Powered by Discuz! X2.5

© 2001-2012 Comsenz Inc.

回顶部