网站方案 模板,替代wordpress的软件,哪个平台做网站好,公关公司的职位编程范式 编程是 程序 员 用特定的语法数据结构算法组成的代码来告诉计算机如何执行任务的过程 #xff0c; 一个程序是程序员为了得到一个任务结果而编写的一组指令的集合#xff0c;正所谓条条大路通罗马#xff0c;实现一个任务的方式有很多种不同的方式#xff0c; 对这… 编程范式 编程是 程序 员 用特定的语法数据结构算法组成的代码来告诉计算机如何执行任务的过程 一个程序是程序员为了得到一个任务结果而编写的一组指令的集合正所谓条条大路通罗马实现一个任务的方式有很多种不同的方式 对这些不同的编程方式的特点进行归纳总结得出来的编程方式类别即为编程范式。 不同的编程范式本质上代表对各种类型的任务采取的不同的解决问题的思路 大多数语言只支持一种编程范式当然也有些语言可以同时支持多种编程范式。 两种最重要的编程范式分别是面向过程编程和面向对象编程。 面向过程编程(Procedural Programming) Procedural programming uses a list of instructions to tell the computer what to do step-by-step. 面向过程编程依赖 - 你猜到了- procedures一个procedure包含一组要被进行计算的步骤 面向过程又被称为top-down languages 就是程序从上到下一步步执行一步步从上到下从头到尾的解决问题 。基本设计思路就是程序一开始是要着手解决一个大的问题然后把一个大问题分解成很多个小问题或子过程这些子过程再执行的过程再继续分解直到小问题足够简单到可以在一个小步骤范围内解决。 举个典型的面向过程的例子 数据库备份 分三步连接数据库备份数据库测试备份文件可用性。 代码如下 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 def db_conn(): print(connecting db...) def db_backup(dbname): print(导出数据库...,dbname) print(将备份文件打包移至相应目录...) def db_backup_test(): print(将备份文件导入测试库看导入是否成功) def main(): db_conn() db_backup(my_db) db_backup_test() if __name__ __main__: main() 这样做的问题也是显而易见的就是如果你要对程序进行修改对你修改的那部分有依赖的各个部分你都也要跟着修改 举个例子如果程序开头你设置了一个变量值 为1 但如果其它子过程依赖这个值 为1的变量才能正常运行那如果你改了这个变量那这个子过程你也要修改假如又有一个其它子程序依赖这个子过程 那就会发生一连串的影响随着程序越来越大 这种编程方式的维护难度会越来越高。 所以我们一般认为 如果你只是写一些简单的脚本去做一些一次性任务用面向过程的方式是极好的但如果你要处理的任务是复杂的且需要不断迭代和维护 的 那还是用面向对象最方便了。 面向对象编程 OOP编程是利用“类”和“对象”来创建各种模型来实现对真实世界的描述使用面向对象编程的原因一方面是因为它可以使程序的维护和扩展变得更简单并且可以大大提高程序开发效率 另外基于面向对象的程序可以使它人更加容易理解你的代码逻辑从而使团队开发变得更从容。 面向对象的几个核心特性如下 Class 类 一个类即是对一类拥有相同属性的对象的抽象、蓝图、原型。在类中定义了这些对象的都具备的属性variables(data)、共同的方法 Object 对象 一个对象即是一个类的实例化后实例一个类必须经过实例化后方可在程序中调用一个类可以实例化多个对象每个对象亦可以有不同的属性就像人类是指所有人每个人是指具体的对象人与人之前有共性亦有不同 Encapsulation 封装 在类中对数据的赋值、内部调用对外部用户是透明的这使类变成了一个胶囊或容器里面包含着类的数据和方法 Inheritance 继承 一个类可以派生出子类在这个父类里定义的属性、方法自动被子类继承 Polymorphism 多态 多态是面向对象的重要特性,简单点说:“一个接口多种实现”指一个基类中派生出了不同的子类且每个子类在继承了同样的方法名的同时又对父类的方法做了不同的实现这就是同一种事物表现出的多种形态。 编程其实就是一个将具体世界进行抽象化的过程多态就是抽象化的一种体现把一系列具体事物的共同点抽象出来, 再通过这个抽象的事物, 与不同的具体事物进行对话。 对不同类的对象发出相同的消息将会有不同的行为。比如你的老板让所有员工在九点钟开始工作, 他只要在九点钟的时候说“开始工作”即可而不需要对销售人员说“开始销售工作”对技术人员说“开始技术工作”, 因为“员工”是一个抽象的事物, 只要是员工就可以开始工作他知道这一点就行了。至于每个员工当然会各司其职做各自的工作。 多态允许将子类的对象当作父类的对象使用某父类型的引用指向其子类型的对象,调用的方法是该子类型的方法。这里引用和调用方法的代码编译前就已经决定了,而引用所指向的对象可以在运行期间动态绑定 面向对象编程(Object-Oriented Programming )介绍 对于编程语言的初学者来讲OOP不是一个很容易理解的编程方式大家虽然都按老师讲的都知道OOP的三大特性是继承、封装、多态并且大家也都知道了如何定义类、方法等面向对象的常用语法但是一到真正写程序的时候还是很多人喜欢用函数式编程来写代码特别是初学者很容易陷入一个窘境就是“我知道面向对象我也会写类但我依然没发现在使用了面向对象后对我们的程序开发效率或其它方面带来什么好处因为我使用函数编程就可以减少重复代码并做到程序可扩展了为啥子还用面向对象”。 对于此我个人觉得原因应该还是因为你没有充分了解到面向对象能带来的好处今天我就写一篇关于面向对象的入门文章希望能帮大家更好的理解和使用面向对象编程。 无论用什么形式来编程我们都要明确记住以下原则 写重复代码是非常不好的低级行为你写的代码需要经常变更 开发正规的程序跟那种写个运行一次就扔了的小脚本一个很大不同就是你的代码总是需要不断的更改不是修改bug就是添加新功能等所以为了日后方便程序的修改及扩展你写的代码一定要遵循易读、易改的原则专业数据叫可读性好、易扩展。 如果你把一段同样的代码复制、粘贴到了程序的多个地方以实现在程序的各个地方调用 这个功能那日后你再对这个功能进行修改时就需要把程序里多个地方都改一遍这种写程序的方式是有问题的因为如果你不小心漏掉了一个地方没改那可能会导致整个程序的运行都 出问题。 因此我们知道 在开发中一定要努力避免写重复的代码否则就相当于给自己再挖坑。 还好函数的出现就能帮我们轻松的解决重复代码的问题对于需要重复调用的功能只需要把它写成一个函数然后在程序的各个地方直接调用这个函数名就好了并且当需要修改这个功能时只需改函数代码然后整个程序就都更新了。 其实OOP编程的主要作用也是使你的代码修改和扩展变的更容易那么小白要问了既然函数都能实现这个需求了还要OOP干毛线用呢 呵呵说这话就像古时候人们打仗杀人都用刀后来出来了枪它的主要功能跟刀一样也是杀人然后小白就问既然刀能杀人了那还要枪干毛线哈哈显而易见因为枪能更好更快更容易的杀人。函数编程与OOP的主要区别就是OOP可以使程序更加容易扩展和易更改。 小白说我读书少你别骗我口说无凭证明一下好吧那我们就下面的例子证明给小白看。 相信大家都打过CS游戏吧我们就自己开发一个简单版的CS来玩一玩。 暂不考虑开发场地等复杂的东西我们先从人物角色下手 角色很简单就俩个恐怖份子、警察他们除了角色不同其它基本都 一样每个人都有生命值、武器等。 咱们先用非OOP的方式写出游戏的基本角色 ? 1 2 3 4 5 6 7 8 9 10 11 #role 1 name Alex role terrorist weapon AK47 life_value 100 #rolw 2 name2 Jack role2 police weapon2 B22 life_value2 100 上面定义了一个恐怖份子Alex和一个警察Jack,但只2个人不好玩呀一干就死了没意思那我们再分别一个恐怖分子和警察吧 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 #role 1 name Alex role terrorist weapon AK47 life_value 100 money 10000 #rolw 2 name2 Jack role2 police weapon2 B22 life_value2 100 money2 10000 #role 3 name3 Rain role3 terrorist weapon3 C33 life_value3 100 money3 10000 #rolw 4 name4 Eric role4 police weapon4 B51 life_value4 100 money4 10000 4个角色虽然创建好了但是有个问题就是每创建一个角色我都要单独命名name1,name2,name3,name4…后面的调用的时候这个变量名你还都得记着要是再让多加几个角色估计调用时就很容易弄混啦所以我们想一想能否所有的角色的变量名都是一样的但调用的时候又能区分开分别是谁 当然可以我们只需要把上面的变量改成字典的格式就可以啦。 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 roles { 1:{name:Alex, role:terrorist, weapon:AK47, life_value: 100, money: 15000, }, 2:{name:Jack, role:police, weapon:B22, life_value: 100, money: 15000, }, 3:{name:Rain, role:terrorist, weapon:C33, life_value: 100, money: 15000, }, 4:{name:Eirc, role:police, weapon:B51, life_value: 100, money: 15000, }, } print(roles[1]) #Alex print(roles[2]) #Jack 很好这个以后调用这些角色时只需要roles[1],roles[2]就可以啦角色的基本属性设计完了后我们接下来为每个角色开发以下几个功能 被打中后就会掉血的功能开枪功能换子弹买枪跑、走、跳、下蹲等动作保护人质仅适用于警察不能杀同伴。。。我们可以把每个功能写成一个函数类似如下 ? 1 2 3 4 5 6 7 8 9 10 11 def shot(by_who): #开了枪后要减子弹数 pass def got_shot(who): #中枪后要减血 who[‘life_value’] - 10 pass def buy_gun(who,gun_name): #检查钱够不够,买了枪后要扣钱 pass ... so far so good, 继续按照这个思路设计再完善一下代码游戏的简单版就出来了但是在往下走之前我们来看看上面的这种代码写法有没有问题至少从上面的代码设计中我看到以下几点缺陷 每个角色定义的属性名称是一样的但这种命名规则是我们自己约定的从程序上来讲并没有进行属性合法性检测也就是说role 1定义的代表武器的属性是weapon, role 2 ,3,4也是一样的不过如果我在新增一个角色时不小心把weapon 写成了wepon , 这个程序本身是检测 不到的terrorist 和police这2个角色有些功能是不同的比如police是不能杀人质的但是terrorist可能随着这个游戏开发的更复杂我们会发现这2个角色后续有更多的不同之处 但现在的这种写法我们是没办法 把这2个角色适用的功能区分开来的也就是说每个角色都可以直接调用任意功能没有任何限制。我们在上面定义了got_shot()后要减血也就是说减血这个动作是应该通过被击中这个事件来引起的,我们调用get_shot()got_shot这个函数再调用每个角色里的life_value变量来减血。 但其实我不通过got_shot()直接调用角色roles[role_id][‘life_value’] 减血也可以呀但是如果这样调用的话那可以就是简单粗暴啦因为减血之前其它还应该判断此角色是否穿了防弹衣等如果穿了的话伤害值肯定要减少got_shot()函数里就做了这样的检测你这里直接绕过的话程序就乱了。 因此这里应该设计 成除了通过got_shot(),其它的方式是没有办法给角色减血的不过在上面的程序设计里是没有办法实现的。 现在需要给所有角色添加一个可以穿防弹衣的功能那很显然你得在每个角色里放一个属性来存储此角色是否穿 了防弹衣那就要更改每个角色的代码给添加一个新属性这样太low了不符合代码可复用的原则 上面这4点问题如果不解决以后肯定会引出更大的坑有同学说了解决也不复杂呀直接在每个功能调用时做一下角色判断啥就好了没错你要非得这么霸王硬上弓的搞也肯定是可以实现的那你自己就开发相应的代码来对上面提到的问题进行处理好啦。 但这些问题其实能过OOP就可以很简单的解决。 class Dog(object):nationality jpdef __init__(self,name): #传参 构造方法初始化方法self.NAME nameself.__heart normal #私有属性def sayhi(self): #类的方法类的功能print(hello,my name is ,self.NAME)def __del__(self):print(haha goodbye)
d Dog(lwq) #lwq是d的成员属性 #先去实例化 #Dog(d,lwq) #实例化后产生的对象就是实例。self其实就是实例本身
d2 Dog(hsc)
d.sayhi() #执行 #d.sayhi(d)
#d2.sayhi()
#print(d._Dog__heart) #强制调用
#print(d._heart) #不能打印打印出错
print(d.nationality)
d.nationality CN #自己修改公有属性相当于自己在内存上创建了一个空间就不会再调用公有的属性。
print(d2.nationality) #调用共有的属性除非自己修改后才是找自己的 之前的代码改成用OOP中的“类”来实现的话如下 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 class Role(object): def __init__(self,name,role,weapon,life_value100,money15000): self.name name self.role role self.weapon weapon self.life_value life_value self.money money def shot(self): print(shooting...) def got_shot(self): print(ah...,I got shot...) def buy_gun(self,gun_name): print(just bought %s %gun_name) r1 Role(Alex,police,AK47’) #生成一个角色 r2 Role(Jack,terrorist,B22’) #生成一个角色 先不考虑语法细节相比靠函数拼凑出来的写法上面用面向对象中的类来写最直接的改进有以下2点 代码量少了近一半角色和它所具有的功能可以一目了然看出来 在真正开始分解上面代码含义之之前我们现来了解一些类的基本定义 类的语法 ? 1 2 3 4 5 6 7 8 9 class Dog(object): print(hello,I am a dog!) d Dog() #实例化这个类 #此时的d就是类Dog的实例化对象 #实例化其实就是以Dog类为模版在内存里开辟一块空间存上数据赋值成一个变量名 上面的代码其实有问题想给狗起名字传不进去。 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 class Dog(object): def __init__(self,name,dog_type): self.name name self.type dog_type def sayhi(self): print(hello,I am a dog, my name is ,self.name) d Dog(LiChuang,京巴) d.sayhi() 为什么有__init__? 为什么有self? 此时的你一脸蒙逼相信不画个图你的智商是理解不了的 画图之前 你先注释掉这两句 ? 1 2 3 4 # d Dog(LiChuang, 京巴) # d.sayhi() print(Dog) 没实例直接打印Dog输出如下 ? 1 class __main__.Dog 这代表什么?代表 即使不实例化这个Dog类本身也是已经存在内存里的对不对 yes, cool那实例化时会产生什么化学反应呢 根据上图我们得知其实self,就是实例本身你实例化时python会自动把这个实例本身通过self参数传进去。 你说好吧假装懂了 但下面这段代码你又不明白了 为何sayhi(self),要写个self呢 好了明白 了类的基本定义接下来我们一起分解一下上面的代码分别 是什么意思 ? 1 2 3 4 5 6 7 class Role(object): #定义一个类 class是定义类的语法Role是类名(object)是新式类的写法必须这样写以后再讲为什么 def __init__(self,name,role,weapon,life_value100,money15000): #初始化函数在生成一个角色时要初始化的一些属性就填写在这里 self.name name #__init__中的第一个参数self,和这里的self都 是什么意思 看下面解释 self.role role self.weapon weapon self.life_value life_value self.money money 上面的这个__init__()叫做初始化方法(或构造方法) 在类被调用时这个方法(虽然它是函数形式但在类中就不叫函数了,叫方法)会自动执行进行一些初始化的动作所以我们这里写的__init__(self,name,role,weapon,life_value100,money15000)就是要在创建一个角色时给它设置这些属性那么这第一个参数self是干毛用的呢 初始化一个角色就需要调用这个类一次 ? 1 2 r1 Role(Alex,police,AK47’) #生成一个角色 , 会自动把参数传给Role下面的__init__(...)方法 r2 Role(Jack,terrorist,B22’) #生成一个角色 我们看到上面的创建角色时我们并没有给__init__传值程序也没未报错是因为类在调用它自己的__init__(…)时自己帮你给self参数赋值了 ? 1 2 r1 Role(Alex,police,AK47’) #此时self 相当于 r1 , Role(r1,Alex,police,AK47’) r2 Role(Jack,terrorist,B22’)#此时self 相当于 r2, Role(r2,Jack,terrorist,B22’) 为什么这样子你拉着我说你有些犹豫怎么会这样子 你执行r1 Role(Alex,police,AK47’)时python的解释器其实干了两件事 在内存中开辟一块空间指向r1这个变量名调用Role这个类并执行其中的__init__(…)方法相当于Role.__init__(r1,Alex,police,’AK47’),这么做是为什么呢 是为了把Alex,police,’AK47’这3个值跟刚开辟的r1关联起来是为了把Alex,police,’AK47’这3个值跟刚开辟的r1关联起来是为了把Alex,police,’AK47’这3个值跟刚开辟的r1关联起来重要的事情说3次 因为关联起来后你就可以直接r1.name, r1.weapon 这样来调用啦。所以为实现这种关联在调用__init__方法时就必须把r1这个变量也传进去否则__init__不知道要把那3个参数跟谁关联呀。明白了么哥所以这个__init__(…)方法里的self.name name , self.role role 等等的意思就是要把这几个值 存到r1的内存空间里。如果还不明白的话哥去测试一下智商吧 应该不会超过70哈哈。 为了暴露自己的智商此时你假装懂了但又问 __init__(…)我懂了但后面的那几个函数噢 不对后面那几个方法 为什么也还需要self参数么 不是在初始化角色的时候 就已经把角色的属性跟r1绑定好了么 good question, 先来看一下上面类中的一个buy_gun的方法 ? 1 2 def buy_gun(self,gun_name): print(“%s has just bought %s” %(self.name,gun_name) ) 上面这个方法通过类调用的话要写成如下 ? 1 2 r1 Role(Alex,police,AK47) r1.buy_gun(B21”) #python 会自动帮你转成 Role.buy_gun(r1,”B21) 执行结果 #Alex has just bought B21 依然没给self传值 但Python还是会自动的帮你把r1 赋值给self这个参数 为什么呢 因为你在buy_gun(..)方法中可能要访问r1的一些其它属性呀 比如这里就访问 了r1的名字怎么访问呢你得告诉这个方法呀于是就把r1传给了这个self参数然后在buy_gun里调用 self.name 就相当于调用r1.name 啦如果还想知道r1的生命值 有多少直接写成self.life_value就可以了。 说白了就是在调用类中的一个方法时你得告诉人家你是谁。 好啦 总结一下2点 上面的这个r1 Role(Alex,police,AK47’)动作叫做类的“实例化” 就是把一个虚拟的抽象的类通过这个动作变成了一个具体的对象了 这个对象就叫做实例刚才定义的这个类体现了面向对象的第一个基本特性封装其实就是使用构造方法将内容封装到某个具体对象中然后通过对象直接或者self间接获取被封装的内容面向对象的特性 封装 封装最好理解了。封装是面向对象的特征之一是对象和类概念的主要特性。 封装也就是把客观事物封装成抽象的类并且类可以把自己的数据和方法只让可信的类或者对象操作对不可信的进行信息隐藏。 继承 面向对象编程 (OOP) 语言的一个主要功能就是“继承”。继承是指这样一种能力它可以使用现有类的所有功能并在无需重新编写原来的类的情况下对这些功能进行扩展。 通过继承创建的新类称为“子类”或“派生类”。 被继承的类称为“基类”、“父类”或“超类”。 继承的过程就是从一般到特殊的过程。 要实现继承可以通过“继承”Inheritance和“组合”Composition来实现。 在某些 OOP 语言中一个子类可以继承多个基类。但是一般情况下一个子类只能有一个基类要实现多重继承可以通过多级继承来实现。 继承概念的实现方式主要有2类实现继承、接口继承。 Ø 实现继承是指使用基类的属性和方法而无需额外编码的能力 Ø 接口继承是指仅使用属性和方法的名称、但是子类必须提供实现的能力(子类重构爹类方法) 在考虑使用继承时有一点需要注意那就是两个类之间的关系应该是“属于”关系。例如Employee 是一个人Manager 也是一个人因此这两个类都可以继承 Person 类。但是 Leg 类却不能继承 Person 类因为腿并不是一个人。 抽象类仅定义将由子类创建的一般属性和方法。 OO开发范式大致为划分对象→抽象类→将类组织成为层次化结构(继承和合成) →用类与实例进行设计和实现几个阶段。 继承示例 class SchoolMember(object):member 0def __init__(self,name,age,sex):self.name nameself.age ageself.sex sexself.enroll()def enroll(self):print(just enrolled a new school member [%s]%self.name)SchoolMember.member 1def tell(self):print(----%s------%self.name)for k,v in self.__dict__.items():print(\t,k,v)def __del__(self):print(开除了[%s]....%self.name)SchoolMember.member -1
class School(object):学校类def open_branch(self,addr):print(openning a newbranch in ,addr)
class Teacher(SchoolMember,School): #这里的School是多继承讲师类def __init__(self,name,age,sex,salary,course):#SchoolMember.__init__(self,name,age,sex) #经典类写法super(Teacher,self).__init__(name,age,sex) #新式类写法self.salary salaryself.course coursedef teaching(self):print(Teacher [%s] is teaching [%s]%self.name,self.course)
class Student(SchoolMember):def __init__(self,name,age,sex,course,tuition):SchoolMember.__init__(self,name,age,sex)self.course courseself.tuition tuitionself.amount 0def pay_tuition(self,amount):print(student [%s] has just paied [%s]%(self.name,self.amount))self.amount amount
t1 Teacher(wusir,28,M,3000,python)
s1 Student(lwq,12,M,python,11000)
s2 Student(hsc,11,M,python,11000)
t1.tell()
s1.tell()
del t1 关联 class F1:def __init__(self,n):self.N nprint(F1)
class F2:def __init__(self,arg1):self.a arg1print(F2)
class F3:def __init__(self,arg2):self.b arg2print(F3)
o1 F1(alex)
o2 F2(o1)
o3 F3(o2)#####输出alex
o3.b.a.N 继承 class F1:def __init__(self):print(F1)def a1(self):print(F1a1)def a2(self):print(F1a2)
class F2(F1):def __init__(self):print(F2)def a1(self):self.a2()print(F2a1)def a2(self):print(F2a2)
class F3(F2):def __init__(self):print(F3)def a2(self):print(F3a2)
obj F3()
obj.a1() class SchoolMember(object):member 0def __init__(self,name,age,sex):self.name nameself.age ageself.sex sexself.enroll()def enroll(self):print(just enrolled a new school member [%s]%self.name)SchoolMember.member 1def tell(self):print(----%s------%self.name)for k,v in self.__dict__.items():print(\t,k,v)def __del__(self):print(开除了[%s]....%self.name)SchoolMember.member -1
class School(object):学校类def open_branch(self,addr):print(openning a newbranch in ,addr)
class Teacher(SchoolMember,School): #这里的School是多继承讲师类def __init__(self,name,age,sex,salary,course):#SchoolMember.__init__(self,name,age,sex) #经典类写法super(Teacher,self).__init__(name,age,sex) #新式类写法self.salary salaryself.course coursedef teaching(self):print(Teacher [%s] is teaching [%s]%self.name,self.course)
class Student(SchoolMember):def __init__(self,name,age,sex,course,tuition):SchoolMember.__init__(self,name,age,sex)self.course courseself.tuition tuitionself.amount 0def pay_tuition(self,amount):print(student [%s] has just paied [%s]%(self.name,self.amount))self.amount amount
t1 Teacher(wusir,28,M,3000,python)
s1 Student(lwq,12,M,python,11000)
s2 Student(hsc,11,M,python,11000)
t1.tell()
s1.tell()
del t1 小结 面向对象更容易扩展提高代码使用效率使代码更强更清晰更适合复杂项目的开发 类 对象 封装 1.防止数据被随意修改 2.使外部程序不需要关注对象内部的构造只需要通过此对象对外提供的接口进行直接访问即可。 继承 通过父类---〉子类的方式以最小代码量的方式实现不同角色的共同点和不同点同时存在。 多态 接口的继承。类的基本定义 类》模版 类----〉实例化----〉实例 __init__ 构造函数 self.name name 属性成员变量或者字段 def sayhi() 方法或者动态属性封装 成员属性》实例变量 公有属性在类里直接定义的属性既是公有属性存在类的内存里所有实例共享。 私有属性__private_attr_name value #两个下划线加名字 对外不提供只读访问接口 def get_heart(self): return self._heart 强制访问 r1._role__heart 类前加一个下划线属性前加两个下划线。 del 析构函数销毁实例时运行 关闭连接。继承 静态方法没有__init__可以有任意个参数直接通过类调用方法,保存在类中调用者是类 class F1: staticmethod def a1(): print(alex) F1.a1() ? 转载于:https://www.cnblogs.com/l-w-q/p/6082103.html