python笔记二

一曲冷凌霜 提交于 2020-03-18 21:23:45
# 类可以起到模板的作用,因此,可以在创建实例的时候,把一些我们认为必须绑定的属性强制填写进去。
# 通过定义一个特殊的__init__方法,在创建实例的时候,就把属性绑上去
class Student(object):

    # 和普通的函数相比,在类中定义的函数只有一点不同,就是第一个参数永远是实例变量self
    # Python解释器自己会把实例变量传进去
    def __init__(self, attr1, attr2):
        self.attr1 = attr1
        self.attr2 = attr2
    pass
    def get_attr(self):
        print(self.attr1)

s = Student(111,222)
s.get_attr()

# 如果要让内部属性不被外部访问,可以把属性的名称前加上两个下划线__,
# 在Python中,实例的变量名如果以__开头,就变成了一个私有变量(private),只有内部可以访问,外部不能访问

class Student(object):

    def __init__(self, attr1, attr2):
        self.attr1 = attr1
        self.__attr2 = attr2
    pass

s = Student(111,222)
print(s.attr1)
print(s.__attr2)

#继承和多态
继承可以把父类的所有功能都直接拿过来,这样就不必重零做起,子类只需要新增自己特有的方法,也可以把父类不适合的方法覆盖重写     

class Parent():

    def say(self):
        print('i am parent')

# 继承
class child(Parent):
    pass

c = child()
c.say()

# 多态 子类覆盖了父类的同名方法 
class child2(Parent):

    def say(self):
        print('i am child')

c2 = child2()
c2.say()

# type

print(type(123))
print(type(123) == type(456)) # True
print(type(123) == int) # True
print(type('123')) # <class 'str'>

# isinstance()判断的是一个对象是否是该类型本身,或者位于该类型的父继承链上

class Hello(object):
    pass

print(isinstance(Hello, object)) # True

#类似__xxx__的属性和方法在Python中都是有特殊用途的,
# 比如__len__方法返回长度。在Python中,如果你调用len()函数试图获取一个对象的长度,
# 实际上,在len()函数内部,它自动去调用该对象的__len__()方法
# 下面两个等价
print(len('123'))
print('123'.__len__())


#不要对实例属性和类属性使用相同的名字,因为相同名称的实例属性将屏蔽掉类属性   
class Hello(object):
    name = 'hello'
    pass


h = Hello()
print(h.name) # hello
h.name = 'world'

print(Hello.name) # hello 类属性
print(h.name) # world 实例属性,屏蔽了类属性

del h.name
print(h.name) # hello 实例属性
print(Hello.name) # hello 类属性


__slots__  限制给类的实例添加属性   
class Hello(object):     
    __slots__ = ('name')  # 实例智能添加name属性      
    pass      

h = Hello()    
h.name ='leyi'      
print(h.name) # leyi    
h.other = '123'    # 会报错    
print(h.other) #       
  

# @property装饰器就是负责把一个方法变成属性调用

class Hello(object):

    def __init__(self, name):
        self.name = name;


h = Hello('leyi')
print(h.name)
# 实例可以随意修改类的属性,属性没经过校验,这样被认为不安全
h.name = 'xxx'
print(h.name)


# 为了控制属性,我们增加方法校验

class Hello2(object):

    def __init__(self, num = 0):
        pass

    def set_num(self, value):
        if not isinstance(value, int):
            raise ValueError('必须为数字类型')
        if value < 100 :
            raise ValueError('必须大于等于100')
        self.num = value

    def get_num(self):
        return self.num
    pass

h2 = Hello2()
h2.set_num(121)
print(h2.get_num())


# 使用property 装饰器简化

class Hello3(object):

    def __init__(self, n = 0):
        pass
    @property # 将下面的方法转换成属性
    def num(self):
        return self.n

    # @property本身又创建了另一个装饰器@score.setter,负责把一个setter方法变成属性赋值
    @num.setter
    def num(self,value):
        if not isinstance(value, int):
            raise ValueError('必须为数字类型')
        if value < 100:
            raise ValueError('必须大于等于100')
        self.n = value

    @property # 不定义setter的话,属性就是只读属性
    def num2(self):
        return self.n *12



h3 = Hello3()
h3.num = 111 # 赋值
print(h3.num) # 取属性
# h3.num2 = 3333 # 因为是只读属性,所以赋值会报错
print(h3.num2) # 取属性

 
logging  \  assert     


# 文件读写时都有可能产生IOError,一旦出错,
# 后面的f.close()就不会调用。所以,为了保证无论是否出错都能正确地关闭文件,
# 我们可以使用try ... finally来实现
try :
    f = open('./b.txt')
    print(f.read())

finally :
    if f:
        f.close()

# Python引入了with语句来自动帮我们调用close()方法

with open('./b.txt', 'r') as f1:
    print(f1.read())


# 如果文件很小,read()一次性读取最方便;如果不能确定文件大小,
# 反复调用read(size)比较保险;如果是配置文件,调用readlines()最方便

# 反复调用read
def readLines():
    pos = 0
    while True :
        with open('./b.txt', 'r') as f2:
            f2.seek(pos)
            data = f2.read(4) # 反复调用readline()也不错
            if data:
                pos = f2.tell()
                yield data
            else:
                return

for i in readLines():
    print(i)

# 读取所有行
with open('./b.txt', 'r') as f3:
    for l in f3.readlines():
        print(l)

  

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!