内功心法果然和基本功没关系,绕来绕去的确实很容易懵,所以今天内容其实不多,但是各种试错还是很多的
一、class知识的继续补充
关于class的一些应该说明的本质问题 还是以狗狗为例 class Dog: '这里一般放置关于这个类的描述,还是应该专业点,这是一个狗狗的类' def __init__(self, name, gender, age, type): self.name = name self.gender = gender self.age = age self.pinzhong = type __init__函数是不能又返回值的,如果你强行返回,系统会告诉你你错了 没有return 下面就可以定义一些关于狗的方法了 def xiaogou(self): #这里你会发现当你定义了一个函数之后,class会自动要求把你在__init__中的self作为变量传输进去 print('%s的狗才能生小狗'%self.gender) def jiao(self): print('%s正在汪汪汪叫'%self.name) def chishi(self): print('%s岁之后狗才会吃屎'%self.age) def yang(self): print('%s容易掉毛'%self.pinzhong) dog1 = Dog('旺财','woman','5','金毛') 这里这句其实相当于在执行类Dog,输入参数的过程和函数没有区别 上面这一句做的事情其实和下面这句是一样的 dog1 = Dog.__init__(dog1,'旺财','woman','5','金毛') 当你在执行Dog的时候其实就是__init__方法,他会默认将dog1传给self 这一步就是对象的实例化的过程 print(dog1) print(dog1.__dict__) {'pinzhong': '金毛', 'gender': 'woman', 'age': '5', 'name': '旺财'} 你会发现当一个类实例化之后,功能属性(即函数)不在上述字典中 但是Dog类里面还是在的哦 print(Dog.__dict__) {'__module__': '__main__', 'chishi': <function Dog.chishi at 0x000001F3123A4598>, '__init__': <function Dog.__init__ at 0x000001F3123A40D0>, '__dict__': <attribute '__dict__' of 'Dog' objects>, '__doc__': '这里一般放置关于这个类的描述,还是应该专业点,这是一个狗狗的类', '__weakref__': <attribute '__weakref__' of 'Dog'objects>, 'jiao': <function Dog.jiao at 0x000001F3123A4510>, 'yang': <function Dog.yang at 0x000001F3123A4620>, 'xiaogou': <function Dog.xiaogou at 0x000001F3123A4488>} 此时你是否看到,我们在输出对象的字典的时候是只有数据属性部分的 那么如何调用功能属性呢 先是使用老式方法开始 Dog.__dict__['yang'](dog1) 准确的输出了:金毛容易掉毛 但是这种方法太low了,现在的class类可以帮我们实现 dog1.yang() 这里也是输出了:金毛容易掉毛 但是你会发现,yang这个函数是需要你传递一个参数self的 这里传递参数由class协助完成,会默认将__init__方法形成的对象传入其中 如果使用老方法不传参数会怎样呢 Dog.__dict__['yang']() 这个时候就会报错:TypeError:yang() missing 1 required positional argument: 'self' 说你没传参数 还有就是关于class里面的作用域问题 之前我们提到,如果个变量找不到自己的值,会不停往外找,直到找到为止,但是在class中 如果找到class的最外层还没找到就不会找了 重新来一个类验证一下吧 dang = '党' class Chinese: pep = '党' print(Chinese.dang) #输出:党 但是我们把党注释掉,放到class外面 print(Chinese.dang) 此时会报错:AttributeError: type object 'Chinese' has no attribute 'dang'
二、类的增删改查
类的增删改查 class Chinese: 'Chinese类,增删改查测试' country = 'China' def __init__(self,name): self.xingming = name def play(self,ball): print('%s正在打%s'%(self.xingming,ball)) 类的增加,首先是数据属性的增加 Chinese.goverment = '党' p1 = Chinese('alex') print(p1.country , p1.goverment) 输出:China 党 完成增加新的数据属性的增加 类的增加,关于增加功能属性的部分 def test(self): print('这是测试部分的内容') Chinese.test_add = test p1.test_add() #这是测试部分的内容 删除类的功能,我们就删除掉上面刚才新增的类 del Chinese.test_add del Chinese.goverment print(Chinese.__dict__) {'__init__': <function Chinese.__init__ at 0x00000200A8DC40D0>, '__weakref__': <attribute '__weakref__' of 'Chinese' objects>, 'play': <function Chinese.play at 0x00000200A8DC4488>, 'country': 'China', '__doc__': 'Chinese类,增删改查测试', '__dict__': <attribute '__dict__' of 'Chinese' objects>, '__module__': '__main__'} 此时刚才新增的两个数据属性和功能属性就都删除掉了 关于类的修改,其实修改的方式和新增的方式是类似的 Chinese.country = '小日本' def eat_food(self , food): print('%s在吃 %s'%(self.xingming , food)) Chinese.play = eat_food print(p1.country) #输出:小日本 p1.play('xiang') 输出:alex在吃 xiang 查看,就直接用类.属性名直接调用查看就可以了
三、实例对象的增删改查
# 实例对象的增删改查 # class Dog: # '测试实例对象的增删改查,包括他的功能属性的修改' # def __init__(self,name): # self.name = name # # def wang(self,people): # print('%s正在冲着%s汪汪叫'%(self.name , people)) # # p1 = Dog('wangcai') # print(p1.name) #wangcai # p1.name = '旺财' # print(p1.name) #旺财 # p1.wang('如花') #旺财正在冲着如花汪汪叫 # def yaoweiba(self , people): # print('%s正在对着%s摇尾巴' % (self.name, people)) # p1.wang = yaoweiba # p1.wang(p1,'如花') #旺财正在对着如花摇尾巴 # 上面这一句需要注意的是,因为这里修改的是针对p1的功能属性,之前p1是没有功能属性的,他的功能属性是调用Dog类的功能属性 # 这里进行修改之后,对类里面的功能并没有影响,所以新增的功能也不具备class优越性,所以我们不仅需要传递参数people,还需 # 要传递参数self,此时我如果使用另一个对象实例去调用Dog的wang方法,结果还是之前的 # p2 = Dog('小白') # p2.wang('美伢') #小白正在冲着美伢汪汪叫 # 所以针对实例对象的功能属性修改是没有实际意义的 # 也不提倡使用
四、接下来是些比较有意思的东西,看着蛮有意思的,但是想多了反而更容易错,先记录在这里吧
# 下面是一些关于class模块和平时的局部作用域的奇葩案例,加深理解 # country = '外国' # class China: # country = '中国' # def __init__(self,name): # print(country) # self.name = name # # def kaixin(self): # print('%s今天很开心'%s) # # p1 = China('马云') # 对China类进行实例化生成实例对象的过程中,在__init__函数下的print输出的country # 输出结果是'外国' # print(p1.country) #而此处的country是中国 # 上面这个例子就反应了一个问题,country = '中国' 是作为一个类的属性保存在China类中,如果我们以类名.属性名, # 或者实例对象.属性名调用时,会在China类中查看属性对应的值,而__init__中的print语句输出的country只是一个单 # 纯的变量,虽然近在眼前的就是country = '中国' 但是,这部分是属于类的属性的 # 下面是关于修改的范围 # p2 = China('alex') # print(p2.country) # p2.country = '日本' # print('class的是',China.country) # print('实例对象',p2.country) # class的是 中国 # 实例对象 日本 # 可以明显看处p2.country修改了属性对class不会有任何影响 # 接下来是一个比较狠的 class Test: '测试类' a = ['a','b'] def __init__(self,name): self.name = name p1 = Test('alex') # p1.a = ['a','b','c'] print('实例对象',p1.a) print('Test类的',Test.a) # 实例对象 ['a', 'b', 'c'] # Test类的 ['a', 'b'] # 这样修改其实是相当于新建了一个p1.a的列表 # 如果修改换种方式呢 p1.a.append('c') print('实例对象',p1.a) print('Test类的',Test.a) # 实例对象 ['a', 'b', 'c'] # Test类的 ['a', 'b', 'c'] # 这里其实是直接在列表a上面进行修改,导致类的发生了变化
今天的内容就是这些了,class部分告一段落,这个功能的确很强大,之前的内容完全都被他整合了。
我擦,吐槽一下,敏感词汇,没想到这还有。。。