Python基础知识_第7节

1389-李同学

发表文章数:35

首页 » Python » 正文

函数用法和底层分析

嵌套函数(内部函数)

  • 在函数内部定义的函数。(只能在函数内部调用)
  • 一般在什么情况下使用嵌套函数?
    1. 封装:数据隐藏 外部无法访问“嵌套函数”。
    2. 贯彻DRY(Don’t Repeat Yourself)原则:嵌套函数,可以让我们在函数内部避免重复代码。
      def printChineseName(name,familyName): 
      	print("{0} {1}".format(familyName,name))
      def printEnglishName(name,familyName): 
      	print("{0} {1}".format(name, familyName))
      
      #使用 1 个函数代替上面的两个函数 
      def printName(isChinese,name,familyName): 
      	def inner_print(a,b): 
      		print("{0} {1}".format(a,b))
      	if isChinese: 
      		inner_print(familyName,name) 
      	else: 
      		inner_print(name,familyName)
      printName(True,"小七","高") 
      printName(False,"George","Bush")	
       3. 闭包:后面会详细讲解。
      

nonlocal 关键字

  • nonlocal 用来声明外部函数的局部变量。 声明之后,可以在内置函数内对外层函数的local变量进行修改。
  • global 用来声明全局变量。声明之后,可以在函数内对global变量进行修改。
a = 100

def outer(): 
	b = 10
	
	def inner(): 
		nonlocal b	# 声明外部函数的局部变量
		print("inner b:",b) 
		b = 20
		
		global a	# 声明全局变量
		a = 1000
	inner() 
	print("outer b:",b)
	
outer() 
print("a:",a)

LEGB规则

  • Python在查找“名称”时,是按照LEGB规则查找的:
    Local–>Enclosed–>Global–>Built in
    • Local:函数或者类的方法内部
    • Enclosed:嵌套函数(一个函数包裹另一个函数,闭包)
    • Global:模块中的全局变量
    • Built in:Python为自己保留的特殊名称。

面向对象(OOP)初步

  • Python支持面向过程面向对象函数式编程等多种编程范式。
  • 将不同类型的数据、方法(即函数)放到一起。
  • Python完全采用了面向对象的思想,完全支持面向对象的基本功能,例如:继承、多态、封装等。

面向对象和面向过程区别

  • 面向过程(procedure oriented)思维:更关注“程序的逻辑流程”,适合编写小规模的程序。
  • 面向对象(Object Oriented)思维:更加关注的是“软件中对象之间的关系”,适合编写大规模的程序。
  • 面向对象和面向过程的总结
    • 都是解决问题、组织代码的思维方式。
    • 简单问题:面向过程
    • 复杂问题:宏观上面向对象,微观上仍然是面向过程。

面向对象思考方式

  • 遇到复杂问题,先从问题中找名词(面向过程更多的是找动词),然后确立这些名词哪些可以作为类,再根据问题需求确定的类的属性和方法,确定类之间的关系。

类的定义

  • 类将不同类型的数据、方法(即函数)放到一起。
  • 从一个类创建对象时,每个对象结构是一样的,因为他们共享同一个方法。
    Python基础知识_第7节
  • 类的总结
    1. 类名首字母大写,多个单词使用“驼峰原则”。
    2. 类体中定义属性方法
    3. 属性用来描述数据,方法(即函数)用来描述这些数据相关的操作。
class Student: 

	def __init__(self,name,score): 	# init第一个参数必须为self,self为对象自己。 
		self.name = name 	# 实例属性 
		self.score = score

	def say_score(self): 	# 实例方法 
		print(self.name,'的分数是:',self.score)

s1 = Student('张三',80) 	# s1是实例对象,自动调用__init__()方法 
s1.say_score()

构造函数__init__()

  • 一个 Python 对象包含如下部分:
    1. id(identity 识别码)
    2. type(对象类型)
    3. value(对象的值)
      (1) 属性(attribute)
      (2) 方法(method)
  • 方法__new__(): 用于创建对象,但一般无需写出来。
  • 方法__init__(): 用来初始化实例对象的实例属性,给实例属性赋值。
  • init()方法:初始化创建好的对象,初始化指的是:“给实例属性赋值”s__new__()方法: 用于创建对象,但我们一般无需重定义该方法。
  • 加了self就是对象的属性,不加就是函数的形参。

实例属性

  • 实例属性一般在__init__()方法中通过self.实例属性名 = 初始值定义。
  • 在本类的其他实例方法中,通过self.实例属性名访问。
  • 创建实例对象后,通过实例对象访问:
    • obj01 = 类名() #创建对象,调用__init__()初始化属性
    • obj01.实例属性名 = 值 #可以给已有属性赋值,也可以新加属性

实例方法

  • 与普通函数的区别在于,方法定义时需要传递self。
  • 定义:def 方法名(self,形参列表): 函数体
  • 调用:对象.方法名(实参列表)
  • 其他操作:
    1. dir(obj)可以获得对象的所有属性、方法
    2. obj.dict 包含该类全部对象属性的字典
    3. pass 空语句,定义一个空类
    4. isinstance(对象,类型)判断“对象”是不是“指定类型”

类对象

  • 所有类都是对象,类型为type。相当于一个模具。

类属性

  • 类属性直接存储于类对象。实例属性存储于相应的、新创建出来的object对象。
    class Student:
    	company = "SXT"	#类属性 
    	count = 0	#类属性
    	
    	def __init__(self,name,score): 
    		self.name = name	#实例属性 
    		self.score = score
    		Student.count = Student.count+1
    	
    	def say_score(self):	#实例方法 
    		print("我的公司是:",Student.company) 			
    		print(self.name,'的分数是:',self.score)
    
    s1 = Student('张三',80)	#s1是实例对象,自动调用__init__()方法 
    s1.say_score() 
    print('一共创建{0}个Student 对象'.format(Student.count)) 
    
    # 我的公司是: SXT 
    # 张三 的分数是: 80 
    # 一共创建 1个Student 对象

    Python基础知识_第7节

类方法

  • 类方法和静态方法中,不能调用实例变量、实例方法。因为在类中模具已经造好了,但饼干(obj)还不知道有没有,所以不可以调用self。
  • 从属于类对象的方法。不会被引用到object的对象中。需要用@classmethod来定义,格式如下:
@classmethod 
def 类方法名(cls,形参列表) : 
	函数体 
class Student:
	company = "SXT"	#类属性
	
	@classmethod
	def printCompany(cls): 
		print(cls.company)
			
Student.printCompany()
# SXT

静态方法

  • 类方法和静态方法中,不能调用实例变量、实例方法。
  • 与普通函数无区别,只不过“静态方法”放到了类的空间里面。
  • 在类里面定义与“类对象”完全无关的方法。需要用@staticmethod来定义,格式如下:
    @staticmethod 
    def 静态方法名(形参列表)  : 
    	函数体 

__del__方法(析构函数)和垃圾回收机制

  • 一般不用写,自动垃圾回收。当对象引用计数为0的时候,由垃圾回收器调用__del__方法。
    # 析构函数 
    class Person:
    	def __del__(self): 
    		print("销毁对象:{0}".format(self))
    		
    p1 = Person() 
    p2 = Person() 
    del p2 
    print("程序结束")
    
    # 销毁对象:<__main__.Person object at 0x02175610>	P2
    # 程序结束 
    # 销毁对象:<__main__.Person object at 0x021755D0>	P1,因为引用为0,所以被自动删除。

__call__方法和可调用对象

  • 定义了__call__方法的对象,称为“可调用对象”,即该对象可以像函数一样被调用。
class SalaryAccount: 
	'''工资计算类'''	
	def __call__(self, salary): 
		print("算工资啦")
		yearSalary = salary*12 
		daySalary = salary//30 
		hourSalary = daySalary//8
		
		return dict(monthSalary=salary,yearSalary=yearSalary,daySalary=daySalary ,hourSalary=hourSalary)

s = SalaryAccount()
print(s(5000))	# 可以像调用函数一样调用对象的__call__方法

# 算工资啦
# {'monthSalary': 5000, 'yearSalary': 60000, 'daySalary': 166, 'hourSalary': 20}

未经允许不得转载:作者:1389-李同学, 转载或复制请以 超链接形式 并注明出处 拜师资源博客
原文地址:《Python基础知识_第7节》 发布于2020-11-09

分享到:
赞(0) 打赏

评论 抢沙发

评论前必须登录!

  注册



长按图片转发给朋友

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏

Vieu3.3主题
专业打造轻量级个人企业风格博客主题!专注于前端开发,全站响应式布局自适应模板。

登录

忘记密码 ?

您也可以使用第三方帐号快捷登录

Q Q 登 录
微 博 登 录