Python字符串解析与格式化输出

  • Post author:
  • Post category:python


输入

  • 命令行参数规范如下:
$ python3 format.py <input.txt> <output.txt> 

  • <input.txt>

    :有待解析清洗的原始数据文本文件名称。

  • <output.txt>

    :用于存储完成清洗后的格式化数据的新建文本文件名称。

输出

  • 代码要求读取输入的文本文件(名称为程序的第一个参数

    <input.txt>

    ),提取每一行的数字,并将其转换成

    xxx-xxx-xxx

    的格式后输出至指定文件。例如:
$ cat input.txt

3357^$*5033#*5

0&@6949@5*956

340980!381@

3938^917!*40

7063$45655#

73@$%7630$298^#

$ python3 format.py input.txt output.txt

$ cat output.txt

335-750-335

069-495-956

340-980-381

393-891-740

706-345-655

737-630-298


问题点:


1.完成文件读取:

在处理文件对象时,最好使用

with

关键字。优点是,子句体结束后,文件会正确关闭,即便触发异常也可以。而且,使用

with

相比等效的

try



finally

代码块要简短得多:

>>>

>>> with open('workfile') as f:
...     read_data = f.read()

>>> # We can check that the file has been automatically closed.
>>> f.closed
True

如果没有使用

with

关键字,则应调用

f.close()

关闭文件,即可释放文件占用的系统资源。


f.read(size)

可用于读取文件内容,它会读取一些数据,并返回字符串(文本模式),或字节串对象(在二进制模式下)。

size

是可选的数值参数。省略

size



size

为负数时,读取并返回整个文件的内容;文件大小是内存的两倍时,会出现问题。

size

取其他值时,读取并返回最多

size

个字符(文本模式)或

size

个字节(二进制模式)。如已到达文件末尾,

f.read()

返回空字符串(

''

)。

>>>

>>> f.read()
'This is the entire file.\n'
>>> f.read()
''


f.readline()

从文件中读取单行数据;字符串末尾保留换行符(

\n

),只有在文件不以换行符结尾时,文件的最后一行才会省略换行符。这种方式让返回值清晰明确;只要

f.readline()

返回空字符串,就表示已经到达了文件末尾,空行使用

'\n'

表示,该字符串只包含一个换行符。

>>>

>>> f.readline()
'This is the first line of the file.\n'
>>> f.readline()
'Second line of the file\n'
>>> f.readline()
''

从文件中读取多行时,可以用循环遍历整个文件对象。这种操作能高效利用内存,快速,且代码简单:

>>>

>>> for line in f:
...     print(line, end='')
...
This is the first line of the file.
Second line of the file

如需以列表形式读取文件中的所有行,可以用

list(f)



f.readlines()

f.write(string) 把 string 的内容写入文件,并返回写入的字符数。

>>>

>>> f.write('This is a test\n')
15


2.如何删除无关字符

Python 的re模块提供了re.sub用于替换字符串中的匹配项。

语法:

re.sub(pattern, repl, string, count=0, flags=0)

参数:

  • pattern : 正则中的模式字符串。
  • repl : 替换的字符串,也可为一个函数。
  • string : 要被查找替换的原始字符串。
  • count : 模式匹配后替换的最大次数,默认 0 表示替换所有的匹配。
  • flags : 编译时用的匹配模式,数字形式。

前三个为必选参数,后两个为可选参数。

实例

#!/usr/bin/python3 import re phone = “2004-959-559 # 这是一个电话号码”

# 删除注释 num = re.sub(r’#.*$’, “”, phone) print (“电话号码 : “, num)

# 移除非数字的内容 num = re.sub(r’\D’, “”, phone) print (“电话号码 : “, num)

以上实例执行结果如下:

电话号码 :  2004-959-559 
电话号码 :  2004959559


3.如何插入字符‘-’

python字符串不能直接在内部插入,可以另写一个函数,我这里用了一个偷懒的方法,将字符串转化为列表,插入后再将列表转换为字符串(如直接输出列表会报错)

遇到的bug:

1.列表转换后的字符串字母之间间会出现空格

['3', '3', '5', '-', '7', '5', '0', '-', '3', '3', '5']
3 3 5 - 7 5 0 - 3 3 5
['0', '6', '9', '-', '4', '9', '5', '-', '9', '5', '6']
0 6 9 - 4 9 5 - 9 5 6
['3', '4', '0', '-', '9', '8', '0', '-', '3', '8', '1']
3 4 0 - 9 8 0 - 3 8 1
['3', '9', '3', '-', '8', '9', '1', '-', '7', '4', '0']
3 9 3 - 8 9 1 - 7 4 0
['7', '0', '6', '-', '3', '4', '5', '-', '6', '5', '5']
7 0 6 - 3 4 5 - 6 5 5
['7', '3', '7', '-', '6', '3', '0', '-', '2', '9', '8']
7 3 7 - 6 3 0 - 2 9 8

解决:原来再join的时候前面的双引号打成了单引号,就会是按单个字符输出

2.在for循环里嵌套with open output的时候,只会输出一行数据,未解决,将其换为open close结构

代码如下:

import sys
import re
fOut = open(sys.argv[2], 'w')
with open(sys.argv[1], "r") as fIn:
    for line in fIn:
        line = re.sub(r'\D', "", line) #remove the undigital string
        new_line = list(line) #
        new_line.insert(3, '-')
        new_line.insert(7, '-')
        print(new_line)
        line = "".join(new_line)
        print(line)
        fOut.write(line + '\n')
fOut.close()



版权声明:本文为qq_53861870原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。