写在前面
在定义方法和属性的问题上
1.以下面的为例子
定义属性 self.name = name 这个self.后面的name 就是Person里面的一个属性
方法 def 后面就是定义的方法名
案例一.小明爱跑步小计划
class Person:
def __init__(self, name, weight):
# self.属性 = 形参
self.name = name
self.weight = weight
def __str__(self):
return "我的名字叫 %s 体重是 %.2f 公斤" % (self.name, self.weight)
def run(self):
print("%s 爱跑步,跑步锻炼身体" % self.name)
self.weight -= 0.5
def eat(self):
print("%s 说吃完这顿再减肥喽")
self.weight += 1
xiaoming = Person("小明", 75.00)
xiaoming.eat()
xiaoming.run()
print(xiaoming)
-封装
- 封装 是面向对象编程的一大特点
- 面向对象编程的 第一步 —— 将 属性 和 方法 封装 到一个抽象的 类 中
- 外界 使用 类 创建 对象,然后 让对象调用方法
- 对象方法的细节 都被 封装 在 类的内部
class Person:
def __init__(self, name, weight):
# self.属性 = 形参
self.name = name
self.weight = weight
def __str__(self):
return "我的名字叫 %s 体重是 %.2f 公斤" % (self.name, self.weight)
def run(self):
print("%s 爱跑步,跑步锻炼身体" % self.name)
self.weight -= 0.5
def eat(self):
print("%s 说吃完这顿再减肥喽" % self.name)
self.weight += 1
xiaoming = Person("小明", 75.00)
xiaoming.eat()
xiaoming.run()
print(xiaoming)
xiaomei = Person('小美',50)
xiaomei.run()
print(xiaomei)
提示!!
在 对象的方法内部,是可以 直接访问对象的属性 的
同一个类 创建的 多个对象 之间,属性 互不干扰
案例二.摆放家具
class HouseItem:
def __init__(self, name, area):
self.name = name
self.area = area
def __str__(self):
return "[%s] 占地 %.2f" % (self.name, self.area)
class House:
# 如果需要从外面传入参数,才需要定义成初始化的形参
def __init__(self, house_type, area):
self.house_type = house_type
self.area = area
# 剩余面积
self.free_area = area
# 家具名称列表
self.item_list = []
def __str__(self):
return ("户型: %s \n 总面积:%.2f [剩余:%.2f] \n家具:%s"
% (self.house_type, self.area,
self.free_area, self.item_list))
def add_item(self, item):
# 1. 判断家具的面积
# item 这里指的是 bed 然后bed在创建家具的时候已经被弄在内存那了
if item.area > self.free_area:
print("%s 的面积太大了,无法添加" % item.name)
return
# 2.家具的名称添加到列表中,
self.item_list.append(item.name)
# 3.计算剩余面积
self.free_area -= item.area
print("要添加 %s" % item)
# 1. 创建家具
bed = HouseItem("席梦思", 4)
chest =HouseItem("衣柜", 20)
table = HouseItem('餐桌', 1.5)
print(bed)
# print(chest)
# print(table)
# 2 创建房子对象
my_home = House("两室一厅", 60)
my_home.add_item(bed)
my_home.add_item(chest)
my_home.add_item(table)
print(my_home)
在第一次创建家具的时候,bed的名字,和大小已经存在一个实例里面了,所以说在class House 中 可以调用 调用bed 那个创建的实例
案例3-面向对象封装问题
一个对象的 属性 可以是 另外一个类创建的对象
class Gun:
def __init__(self, model):
# 1.枪的型号
self.model = model
# 2.子弹的数量 初始为0
self.bullet_count = 0 # ???
def add_bullet(self, count):
self.bullet_count += count # 加子弹
def shoot(self):
# 1. 判断是否有子弹
if self.bullet_count <= 0:
print("没有子弹了........")
return
# 2. 发射子弹
self.bullet_count -= 1
# 3. 提示发射信息
print('[%s] 突突突.....[%d]' % (self.model, self.bullet_count))
class Soldier:
def __init__(self, name):
# 1. 姓名
self.name = name
# 2. 枪 - 新兵没有枪 及定义属性,又不设置具体的枪对象
self.gun = None
def fire(self):
# 1. 判断士兵是否有枪
if self.gun == None:
print("士兵没有枪")
return
# 2. 喊口号
print("冲啊.....[%s]" % self.name)
# 3.让枪装填子弹
self.gun.add_bullet(50) # ??
# 4. 让枪发射子弹
self.gun.shoot()
# 1 创建枪对象
ak47 = Gun('Ak47')
# 2.创建许三多
xusanduo = Soldier('许三多')
xusanduo.gun = ak47
xusanduo.fire()
print(xusanduo.gun)
is 身份运算符
身份运算符用于 比较 两个对象的 内存地址 是否一致 —— 是否是对同一个对象的引用
在 Python 中针对 None 比较时,建议使用 is 判断
is 与 == 区别:
is 用于判断 两个变量 引用对象是否为同一个
== 用于判断 引用变量的值 是否相等
在python中,数据和变量是分别存储的,数据可以看成存储在内存中的小格子,变量就看成一个标签,
2. 一个比方 数据是 30 变量是 x 内存中有一个 30 的小格子 x挂在小格子上面
私有方法和属性
在实际开发中,对象 的 某些属性或方法 可能只希望 在对象的内部被使用,而 不希望在外部被访问到
class Women:
def __init__(self, name):
self.name = name
self.__age = 18
def __secret(self):
# 在对象方法内部,是可以访问对象的私有属性的
print("%s 的年龄是 %d" %(self.name, self.__age))
xiaofang = Women('小芳')
# # 私有属性在外界不能直接访问
# print(xiaofang.__age)
xiaofang.__secret()
伪私有方法和属性
class Women:
def __init__(self, name):
self.name = name
self.__age = 18
def __secret(self):
print("%s 的年龄是 %d" %(self.name, self.__age))
xiaofang = Women('小芳')
# 只需要在私有属性前,加入 "_类名"
print(xiaofang._Women__age)
# 只需要在私有对象前,加入 "_类名"
xiaofang._Women__secret()