深入Python(四)

先来看一段Python代码:

import os

import sys

from UserDict import UserDict



def stripnulls(data):

    "strip whitespace and nulls"

    return data.replace("\00", "").strip()



class FileInfo(UserDict):

    "store file metadata"

    def __init__(self, filename=None):

        UserDict.__init__(self)

        self["name"] = filename



class MP3FileInfo(FileInfo):

    "store ID3v1.0 MP3 tags"

    tagDataMap = {"title"   : (  3,  33, stripnulls),

                  "artist"  : ( 33,  63, stripnulls),

                  "album"   : ( 63,  93, stripnulls),

                  "year"    : ( 93,  97, stripnulls),

                  "comment" : ( 97, 126, stripnulls),

                  "genre"   : (127, 128, ord)}



    def __parse(self, filename):

        "parse ID3v1.0 tags from MP3 file"

        self.clear()

        try:                               

            fsock = open(filename, "rb", 0)

            try:                           

                fsock.seek(-128, 2)        

                tagdata = fsock.read(128)  

            finally:                       

                fsock.close()              

            if tagdata[:3] == "TAG":

                for tag, (start, end, parseFunc) in self.tagDataMap.items():

                    self[tag] = parseFunc(tagdata[start:end])               

        except IOError:                    

            pass                           



    def __setitem__(self, key, item):

        if key == "name" and item:

            self.__parse(item)

        FileInfo.__setitem__(self, key, item)



def listDirectory(directory, fileExtList):                                        

    "get list of file info objects for files of particular extensions"

    fileList = [os.path.normcase(f)

                for f in os.listdir(directory)]           

    fileList = [os.path.join(directory, f) 

               for f in fileList

                if os.path.splitext(f)[1] in fileExtList] 

    def getFileInfoClass(filename, module=sys.modules[FileInfo.__module__]):      

        "get file info class from filename extension"                             

        subclass = "%sFileInfo" % os.path.splitext(filename)[1].upper()[1:]       

        return hasattr(module, subclass) and getattr(module, subclass) or FileInfo

    return [getFileInfoClass(f)(f) for f in fileList]                             



if __name__ == "__main__":

    for info in listDirectory("/music/_singles/", [".mp3"]): 

        print "\n".join(["%s=%s" % (k, v) for k, v in info.items()])

        print

  

  这个程序的输入要取决于你硬盘上的文件。为了得到有意义的输出,你应该修改目录路径指向你自已机器上的一个 MP3 文件目录。

你不需要完全明白上述代码的意义,因为本代码只是为了说明Python中的对象和面向对象的内容。

首先你会看到这样的代码 from UserDict import UserDict      (from module import *)

这意味着你可以在自己的模块中直接使用UserDict模块的UserDict类(当然如果是使用的后面括号里的那条语句的话也可以直接使用其他对象,如函数)。但不提倡这样用,因为假如你自己的模块中也有一个UserDict类,就不好分辨了,判定一个特殊的函数或属性是从哪来的有些困难,并且会造成调试和重构都更困难。

关于Python中类的定义可以看这里的类及继承

关于Python中类的方法可以看这里的方法  会发现类的方法与函数的区别就是,定义类方法时第一个参数必须是self,而调用类方法是则不需要这个self参数(除了调用父类的方法时,调用父类的方法也需要传递self参数)。

而Python的类里也有类似静态变量,实例变量的概念。静态变量就是像上述代码MP3FileInfo类tagDataMap那样在那个位置定义。而实例变量一般是在__init__()方法里通过self.变量名来定义。 由于Python是动态类型语言,所以这些变量都不用声明,在第一次赋值时会自动确定其类型,并且由于Python是强类型语言,所以一旦这些变量的类型确定了,如果不做明确的类型转换,不能一种类型当另一种类型使用。

在Python中也有私有的概念,如果一个函数名是以__(双下划线)开始,那么它是私有的,只能在该模块内使用。类似的如果一个类的方法名或类的变量名是__开始,那么它们是私有的,只能在该类内被使用。如上述代码中MP3FileInfo类的__parse方法。

而想__init__方法这样两边都有双下划线的方法称为专有方法,你可以手动调用,但它们主要是你使用特殊语法时Python替你调用的,如当你创建一个类的实例时,Python会帮你调用__init__方法。

posted @ 2011-08-03 15:20  何塞穆里尼奥  阅读(602)  评论(2编辑  收藏  举报