Python文本管理之按行管理大文件的不二等秘书技

作者: 韦德国际1946手机版  发布:2019-05-31

以行的款式读出1个文书最轻易易行的点子是应用文件对象的readline()、readlines()和xreadlines()方法。

以行的款型读出三个文书最简便的不二诀假使使用文件对象的readline()、readlines()和xreadlines()方法。
Python2.二 为这种屡屡的操作提供了二个简化的语法——让文件对象自己在行上高效迭代(这种迭代是严刻的前进的)。
为了读取整个文件,或然要利用read()方法,且使用字符串的split()来将它拆分WEIGHT行或任何块。上面是局地事例:

字符串的基本操作

=”Shall I compare thee to a Summer’s day?
“Thou are more lovely =
= more temperate:”””

 monty 

Monty[20] monty[-1]

走访子字符串(获取记录中或多或少字段的多寡)

Python2.二 为这种反复的操作提供了二个简化的语法——让文件对象自己在行上高效迭代(这种迭代是严谨的向前的)。

      >>> for line in open('chap1.txt'): # Python 2.2 
      ...     # process each line in some manner
      ...     pass
      ...
      >>> linelist = open('chap1.txt').readlines()
      >>> print linelist[1849],
        EXERCISE: Working with lines from a large file
      >>> txt = open('chap1.txt').read()
      >>> from os import linesep
      >>> linelist2 = txt.split(linesep)

访问子字符串

Monty[6:10] monty[:5] monty[1:]

杀鸡取卵办法:

为了读取整个文件,也许要选拔read()方法,且使用字符串的split()来将它拆分WEIGHT行或别的块。

如果文件非常的小,读取整个文件内容也尚未提到。但如假设大文件,时间和内部存款和储蓄器正是要入眼关心的了。比如,复随想书档案恐怕活动日志文件,平日有上M,乃至很多G的轻重。就算那些文件的剧情并未有超过可用内部存款和储蓄器的尺码,读取他们依然是1对一耗费时间的。
很通晓,假若您须要管理文件的每一行,那就非得读取整个文件;即便得以按种类管理,xreadlines方法是一种更节外省部存款和储蓄器的措施。可是对于那八个单纯必要三个大文件的1部分行的使用,要拿走进步其实并简单。对于那或多或少,模块“linecache”特别适合。

愈来愈多的字符串操作

图片 1

Python文本管理之按行管理大文件的不二等秘书技,语言管理与Python。切开,但不得不获得二个字段 

上面是部分事例:

怀有缓存功用的行列表

动用linecache能够直接从一个文书中读取钦赐行:

      >>> import linecache
      >>> print linecache.getline('chap1.txt',1850),
        PROBLEM: Working with lines from a large file

切记,linecache.getline()的计数是从壹初叶的。

固然有一个即具备“linecache”的频率,又有列表的①对效益的对象就好了。这么些指标不仅仅可以枚举和目录,同一时间还帮助切成块。

#------------------ cachedlinelist.py --------------------#
      import linecache, types
      class CachedLineList:
          # Note: in Python 2.2 , it is probably worth including:
          # __slots__ = ('_fname')
          # ...and inheriting from 'object'
          def __init__(self, fname):
              self._fname = fname
          def __getitem__(self, x):
              if type(x) is types.SliceType:
                  return [linecache.getline(self._fname, n 1)
                          for n in range(x.start, x.stop, x.step)]
              else:
                  return linecache.getline(self._fname, x 1)
          def __getslice__(self, beg, end):
              # pass to __getitem__ which does extended slices also
              return self[beg:end:1]

运用那么些新对象差十分的少和行使1个由“open(fname).readlines()”成立的列表同样。除了它的频率要越来越高之外(特别是在内部存款和储蓄器使用方面):

      >>> from cachedlinelist import CachedLineList
      >>> cll = CachedLineList('../chap1.txt')
      >>> cll[1849]
      '  PROBLEM: Working with lines from a large filern'
      >>> for line in cll[1849:1851]: print line,
      ...
        PROBLEM: Working with lines from a large file
        ----------------------------------------------------------
      >>> for line in cll[1853:1857:2]: print line,
      ...
        a matter of using the '.readline()', '.readlines()' and
        simplified syntax for this frequent operation by letting the

链表与字符串的差别

链表和字符串都以1种队列;

都能够动用切成块;

 

链表是能够操作,可变的;

而字符串是不可变的;

=Shall I compare thee to a Summers day? Thou are more lovely = = more temperate: monty Monty[20]monty[-1] 访问子字符串 Monty[6:10]monty[:5]monty[1:]...

[python] 

  >>> for line in open('chap1.txt'): # Python 2.2 
  ...  # process each line in some manner
  ...  pass
  ...
  >>> linelist = open('chap1.txt').readlines()
  >>> print linelist[1849],
  EXERCISE: Working with lines from a large file
  >>> txt = open('chap1.txt').read()
  >>> from os import linesep
  >>> linelist2 = txt.split(linesep)

随机行

神迹,非常是为着测试,或许供给检讨某个规范的行。大家很轻便就误感到多少个对文本的后面几行和后边几行有效的拍卖就能适用别的其余地点。很不幸,繁多文本的前几行和最终几行平日都以非独立的:偶尔候是新闻头或表明,不常候大概是付出时的日志文件的前几行等等。穷举测试整个文件并不是您想要的,日常那样也非常的耗费时间。
在许多系统上,查找1个文件中的特定岗位要比读出该地点前的保有内容直到到达该地方快的多。
尽管使用linecache,要达到缓存行,你也急需一个字节贰个字节的读取前面包车型大巴内容。从贰个大文件中找随机行的最快的章程是,先找到1个自便地方,然后读取该职分相对前后的个别字节。

 #-------------------- randline.py ------------------------#
      #!/usr/bin/python
      """Iterate over random lines in a file (req Python 2.2 )
      From command-line use: % randline.py <fname> <numlines>
      """
      import sys
      from os import stat, linesep
      from stat import ST_SIZE
      from random import randrange
      MAX_LINE_LEN = 4096

      #-- Iterable class
      class randline(object):
          __slots__ = ('_fp','_size','_limit')
          def __init__(self, fname, limit=sys.maxint):
              self._size = stat(fname)[ST_SIZE]
              self._fp = open(fname,'rb')
              self._limit = limit
          def __iter__(self):
              return self
          def next(self):
              if self._limit <= 0:
                  raise StopIteration
              self._limit -= 1
              pos = randrange(self._size)
              priorlen = min(pos, MAX_LINE_LEN)   # maybe near start
              self._fp.seek(pos-priorlen)
              # Add extra linesep at beg/end in case pos at beg/end
              prior = linesep   self._fp.read(priorlen)
              post = self._fp.read(MAX_LINE_LEN)   linesep
              begln = prior.rfind(linesep)   len(linesep)
              endln = post.find(linesep)
              return prior[begln:] post[:endln]

      #-- Use as command-line tool
      if __name__=='__main__':
          fname, numlines = sys.argv[1], int(sys.argv[2])
          for line in randline(fname, numlines):
              print line

关于地点的贯彻,必要小心以下细节:(壹)在行迭代中,一样的行大概会被反复当选。当然,倘让你只是从大文件中选非常的少行的话,这种场地习认为常不会现出。(二)既然是选中蕴含自由地点的行,那就意味着更 有不小可能率选取长的行(译注:那是为啥?未有精通)。

本文翻译自Text Processing in Python
中“PROBLEM: Working with lines from a large file”

theline='I Love Python'  

假如文件十分小,读取整个文件内容也从不涉嫌。但壹旦是大文件,时间和内部存款和储蓄器正是要注重关注的了。比方,复随想书档案也许活动日志文件,平日有上M,乃至诸多G的大小。固然那么些文件的剧情尚未超过可用内部存款和储蓄器的尺码,读取他们依然是十三分耗费时间的。

afield=theline[2:6]  

很明显,若是你需求管理公事的每1行,那就务须读取整个文件;假若能够按类别管理,xreadlines方法是1种更省去内部存储器的法子。可是对于那一个单纯须求三个大文件的壹部分行的选用,要博取进步其实并简单。对于那一点,模块“linecache”极度体面。

print afield  

具备缓存功能的行列表

  

选拔linecache能够一直从多个文本中读取钦赐行:

结果  

  >>> import linecache
  >>> print linecache.getline('chap1.txt',1850),
  PROBLEM: Working with lines from a large file

Love  

牢记,linecache.getline()的计数是从1起来的。

若果急需思考字段的长短,使用struct.unpack 

如果有多少个即具备“linecache”的频率,又有列表的一对功效的靶子就好了。那几个目的不仅仅能够枚举和目录,同期还帮助切成块。

[python]  

#------------------ cachedlinelist.py --------------------#
  import linecache, types
  class CachedLineList:
   # Note: in Python 2.2 , it is probably worth including:
   # __slots__ = ('_fname')
   # ...and inheriting from 'object'
   def __init__(self, fname):
    self._fname = fname
   def __getitem__(self, x):
    if type(x) is types.SliceType:
     return [linecache.getline(self._fname, n 1)
       for n in range(x.start, x.stop, x.step)]
    else:
     return linecache.getline(self._fname, x 1)
   def __getslice__(self, beg, end):
    # pass to __getitem__ which does extended slices also
    return self[beg:end:1]

# -*- coding:gb2312 -*-  

运用那些新对象大约和行使贰个由“open(fname).readlines()”创立的列表同样。除了它的频率要越来越高之外(极其是在内部存款和储蓄器使用方面):

import struct  

  >>> from cachedlinelist import CachedLineList
  >>> cll = CachedLineList('../chap1.txt')
  >>> cll[1849]
  ' PROBLEM: Working with lines from a large filern'
  >>> for line in cll[1849:1851]: print line,
  ...
  PROBLEM: Working with lines from a large file
  ----------------------------------------------------------
  >>> for line in cll[1853:1857:2]: print line,
  ...
  a matter of using the '.readline()', '.readlines()' and
  simplified syntax for this frequent operation by letting the

baseformat='1s 6x 6s'  

随机行

#第一,baseformat制定了该如何对字符串实行分组,x代表跳过,s代表收取  

有时,极其是为着测试,大概要求检查有些规范的行。大家很轻易就误认为3个对文件的前方几行和后边几行有效的管理就可以适用别的别的地点。很不幸,诸多文书的前几行和终极几行平常都是非独立的:一时候是音信头或证明,一时候可能是支付时的日志文件的前几行等等。穷举测试整个文件并不是您想要的,平日那样也极度的耗费时间。

#就此地点的代码表示拿走三个字符,跳过多少个字符,拿走陆个字符  

在大部种类上,查找1个文本中的特定岗位要比读出该职位前的具备内容直到达到该地点快的多。

theline='I Love Python So Much'  

纵使使用linecache,要达到缓存行,你也需求一个字节贰个字节的读取后面包车型大巴剧情。从三个大文件中找随机行的最快的办法是,先找到多少个自便地点,然后读取该地点相对前后的少数字节。

numremain=len(theline)-struct.calcsize(baseformat)  

本文由韦德国际1946发布于韦德国际1946手机版,转载请注明出处:Python文本管理之按行管理大文件的不二等秘书技

关键词: python 文本处理