首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >类CatalogWalker可以遍历目录列表、计算和报告一些统计信息。

类CatalogWalker可以遍历目录列表、计算和报告一些统计信息。
EN

Code Review用户
提问于 2014-12-09 02:17:54
回答 1查看 62关注 0票数 0

仅供参考,也许对某人有用

代码语言:javascript
复制
from os import walk
from time import time

from abc import ABCMeta, abstractmethod

class Reporter(object):
    __metaclass__=ABCMeta

    @abstractmethod
    def report(self, catalogs_cntr, files_ctnr, speed):
        """ output catalogs_cntr, files_ctnr, speed to somewhere """
        #pass

class ConsoleIndicator(Reporter):
    def __init__(self, out_splitter):
        self.__out_splitter=out_splitter

    def report(self, catalogs_cntr, files_ctnr, speed):
        if self.__out_splitter and self.__out_splitter.pipes:
            _result = "\rcataloges:" + repr(catalogs_cntr).rjust(8) 
            _result += "\tfiles:" + repr(files_ctnr).rjust(13) 
            _result += "\tspeed: %12.3f"%speed + " files/s"

            self.__out_splitter.write(_result)
            self.__out_splitter.flush()        

class CatalogsWalker(object):
    """ """

    def __init__(self, catalogs, reporter=None):
        """ """

        self.__files_cntr, self.__catalogs_cntr, self.__start_time, self.__speed = 0, 0, 0, 0
        self.__reporter = reporter 
        self.__catalogs = catalogs if hasattr(catalogs, "__iter__") else [catalogs]

    def __iter__(self):
        self.__files_cntr, self.__catalogs_cntr, self.__start_time, self.__speed = 0, 0, 0, 0
        self.__start_time=time()
        for catalog in self.__catalogs:
            for p,d,ns in walk(catalog): 
                _ = d;
                self.__catalogs_cntr+=1
                for n in ns:
                    self.__files_cntr+=1
                    self.__speed=self.__files_cntr/(time()-self.__start_time)
                    if self.__reporter:
                        self.__reporter.report(self.__catalogs_cntr, self.__files_cntr, self.__speed)
                    yield p,n

    @property
    def reporter(self):
        return self.__reporter

    @property
    def catalog_counter(self):
        return self.__catalogs_cntr    

    @property
    def file_counter(self):
        return self.__files_cntr

    @property
    def start_time(self):
        return self.__start_time

    @property
    def speed(self):
        return self.__speed
EN

回答 1

Code Review用户

发布于 2014-12-09 14:14:47

我想谈谈一个微妙的问题。首先,看看此页面解释了可迭代和迭代器之间的区别。

现在,CatalogsWalker是可迭代的,但是它有跟踪迭代状态的实例属性。如果有人在同一个对象上并行地重复多次,这个跟踪就会出错。这个类更适合作为迭代器。

下面是如何重新排列代码以将CatalogsWalker转换为迭代器的方法。我还从jonrsharpe的出色答案中得到了一些建议。

代码语言:javascript
复制
class CatalogsWalker(object):
    def __init__(self, catalogs, reporter=None):
        self._files_cntr, self._catalogs_cntr, self._start_time, self._speed = 0, 0, 0, 0
        self._reporter = reporter 
        self.__catalogs = catalogs if hasattr(catalogs, "__iter__") else [catalogs]
        self._walker = self._walk()

    def __iter__(self):
        return self

    # def __next__(self):  # Python 3
    def next(self):    # Python 2    
        return next(self._walker)

    def _walk(self):
        self._start_time=time()
        for catalog in self._catalogs:
            for p,_,ns in walk(catalog): 
                self._catalogs_cntr+=1
                for n in ns:
                    self._files_cntr+=1
                    self._speed=self._files_cntr/(time()-self._start_time)
                    if self._reporter:
                        self._reporter.report(self._catalogs_cntr, self._files_cntr, self._speed)
                        yield p,n

    @property
    def reporter(self):
        return self._reporter

    @property
    def catalog_counter(self):
        return self._catalogs_cntr    

    @property
    def file_counter(self):
        return self._files_cntr

    @property
    def start_time(self):
        return self._start_time

    @property
    def speed(self):
        return self._speed
票数 3
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/72090

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档