zl程序教程

您现在的位置是:首页 >  Java

当前栏目

(三)数据的获取与表示

2023-02-18 15:50:07 时间

目录

本地数据的获取

上下文管理器

打开文件

写文件

 读文件

读写文件

网络数据的获取

抓取

解析


本地数据的获取

上下文管理器

        在python中,我们可以使用with语句来定义和控制代码块执行前的准备动作及执行后的收尾动作,语法为with open('d:\\test\\a.txt','w') as f:,将打开后的文件对象赋值给f,再进行之后的操作。

打开文件

        一般使用open函数打开文件,语法为open(filename, mode='r' , buffering=-1, …),filename表示文件名或路径,一般使用'd:\\infile.txt'、r'd:\outfile.txt'和'record.txt'这三种形式作为参数;mode表示为打开方式,具体功能如下:

mode

功能

r

以读模式打开

w

以写模式打开(清空原内容)

r

以写模式打开,若文件已存在则失败

a

以追加模式打开(从EOF开始,必要时创建新文件)

r+

以读写模式打开

w+

以读写模式打开(清空原内容)

a+

以读和追加模式打开

rb

以二进制读模式打开

wb

以二进制写模式打开(参见w)

ab

以二进制追加模式打开(参见a)

rb+

以二进制读写模式打开(参见r+)

wb+

以二进制读写模式打开(参见w+)

ab+

以二进制读写模式打开(参见a+)

buffering也为可选参数,默认值为-1(0代表不缓冲,1 或大于1的值表示缓冲一行或指定缓冲区大小)。

open的返回值是一个文件对象(设为f),此时,可用一些文件相关函数来操作这个对象,如f.read(), f.write(), f.readline(), f.readlines(), f.writelines(),f.close(),f.seek()等等。

写文件

         主要使用f.write()和 f.writelines()函数,f.write()写入一个字符串,f.writelines()写入一系列字符串,代码实现如下:

with open(r'd:\test\a.txt', 'w') as f:
    f.write('Hellow World!\n')
    f.writelines(['Hellow World!\n', 'Hellow\n', 'World\n'])
    f.close()

运行结果

图 1 运行结果

 读文件

        主要使用f.read()、 f.readline()和f.readlines()函数,f.read()写入一个字符串,带参数说明从文件中至多读出size字节数据,返回一个字符串,不带参数就是读文件直到文件结束,返回一个字符串;f.readlines()读出所有的字符串,返回一个列表;f.readline()读出一行字符串,返回一个字符串,代码实现如下:

with open('d:\\test\\a.txt') as f:
    p1 = f.read(8)
    f.seek(0)        #功能和用法的讲解在本小节末尾
    p2 = f.read()
    f.close()
print(p1)
print(p2)

#输出结果如下所示
#Hellow W
#Hellow World!Hellow World!
#Hellow
#World

图  2  b.txt 内容

with open('d:\\test\\b.txt') as f:
    p1 = f.readlines()
    f.seek(0)
    p2 = f.readline()
    f.close()
print(p1, type(p1))
print(p2, type(p2))

#运行结果如下
#['    A\n', '   ABC\n', '  ABCDC\n', ' ABCDEDC\n', 'ABCDEFEDC\n'] <class 'list'>
#    A                           #文件里带有一个换行符
# <class 'str'>
file_name = 'd:\\test\\b.txt'        #使用异常处理机制来判断文件有多少行
try:
    with open(file_name) as f:
        date = f.readlines()
except FileExistsError:
    print(file_name + 'does not exist')
lens = len(date)
print('b.txt' + ' has ' + str(lens) + ' line')

#输出结果如下:
#   b.txt has 5 line

        除此之外,还可以同时处理多个文件,代码如下所示:

def countLines(fname):
    try:
        with open(fname) as f:
            date = f.readlines()
    except FileExistsError:
        print(fname + ' does not exist')
    lens = len(date)
    print(fname + ' has ' + str(lens) + ' line')

files = ['d:\\test\\a.txt', 'd:\\test\\b.txt', 'd:\\test\\c.txt']
for fname in files:
    countLines(fname)

#运行结果为
#   d:\test\a.txt has 3 line
#   d:\test\b.txt has 5 line
#   d:\test\c.txt has 5 line

        还可以统计一个目录下所有txt文件的行数,代码如下所示:

import os
import shutil
def countLines(fname):
    try:
        with open(fname) as f:
            date = f.readlines()
    except FileExistsError:
        print(fname + ' does not exist')
    lens = len(date)
    print(fname + ' has' + str(lens) + ' line')

path = 'd:\\test'
for fname in os.listdir(path):
    if fname.endswith('.txt'):
        file_path = os.path.join(path, fname)
        countLines(file_path)

#运行结果为
#   d:\test\a.txt has 3 line
#   d:\test\b.txt has 5 line
#   d:\test\c.txt has 5 line

注:判断文件是否可读,可用f.readable()来判断

读写文件

        对于文件操作,往往需要对文件同时进行读和写,具体实现代码如下:

with open('d:\\test\\b.txt') as f1:
    cName = f1.readlines()
    f.close()
for i in range(0,len(cName)):
    cName[i] = str(i+1) + ' ' +cName[i]
with open('d:\\test\\c.txt','w') as f2:
    f2.writelines(cName)
    f.close()

 图 3 运行结果(c.txt文件)

        除了读写函数之外,文件操作里面还有一个特别重要的函数f.seek()函数,语法如下:f.seek(offset , whence=0),主要功能就是在文件中移动文件指针,从 whence(0表示文件头部,1表示 当前位置,2表示文件尾部)偏移offset个字节,whence参数可选,默认值为0,已在前面代码中使用过,此处就不再叙述了。

网络数据的获取

        本文目前只介绍一下简单的网络数据获取方式,更深入一点的在日后进行补充。

抓取

        实现抓取网页内容有许多种方法,目前只介绍使用Requests第三方库来进行抓取(首先要查看爬虫协议),可直接在命令提示符下输入pip install requests 来获取,或者使用Anaconda来导入第三方库,在此就不介绍具体方法,实现代码如下:

import requests
r = requests.get("https://www.baidu.com/")
print(r.status_code)
r.encoding = 'utf-8'
print(r.text)

        获取到的代码如下所示:

        运行结果如图所示:

 图 4 代码运行结果

解析

        对网页进行爬取之后,有时候要进行代码的解析,来获得我们所需要的信息,本文主要使用Beautifu Soup第三方库来解析代码,具体代码实现如下所示:

import requests
from bs4 import BeautifulSoup
import re

headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) '
                         'Chrome/78.0.3904.108 Safari/537.36'}
# 有些网站抓取时需要增加headers属性,将自己的浏览器信息告诉服务器

r = requests.get('https://book.douban.com/subject/1084336/comments/', headers=headers)
soup = BeautifulSoup(r.text, 'lxml')
pattern = soup.find_all('span', 'short')
for item in pattern:
    print(item.string)
pattern_s = re.compile('<span class="user-stars allstar(.*?) rating"')
p = re.findall(pattern_s, r.text)
s = 0
for star in p:
    s += int(star)
print(s)    # 统计评分总数
print(p)    # 查看每个评分数

        运行代码如下所示:

 图 5 代码运行结果