内置函数、反射、__str__、__del__、元类

一、内置函数的补充

isinstance(obj,cls)检查是否obj是否是类 cls 的对象

class Foo:
    pass

obj=Foo()
print(isinstance(obj,Foo)) # 推荐使用该函数来判断一个函数的类型,判断obj(对象)是否是Foo(类)的对象,是则为真,否则为假

也可用下面main方法判断
print(type(obj) is Foo)


issubclass(sub, super)检查sub类是否是 super 类的派生类

 class Foo(object):
2     pass
3  
4 class Bar(Foo):
5     pass
6  
7 issubclass(Bar, Foo)

二、反射

 #下述四个函数是专门用来操作类与对象属性的,如何操作?

#通过字符串来操作类与对象的属性,这种操作称为反射
class People:
    country="China"
    def __init__(self,name):
        self.name=name
    def tell(self):
        print('%s is aaa' %self.name)

obj=People('egon')

# 1、hasattr            #判断object中有没有一个name字符串对应的方法或属性
# print(hasattr(People,'country'))       #判断类中有没有一个 'country' 字符串对应的方法或属性
# print('country' in People.__dict__)       #判断country是否在类的字典中
# print(People.__dict__)                #拿到类的字典
# print(hasattr(obj,'name'))
# print(hasattr(obj,'country'))           #判断obj(对象)有没有一个 'country' 字符串对应的方法或属性
# print(hasattr(obj,'tell'))

# 2、getattr
# x=getattr(People,'country')             #获取类中country的属性是China
# x=getattr(People,'country1',None)          #获取country1的属性,没有则返回None
# print(x)

# f=getattr(obj,'tell',None)#obj.tell          #获取obj(对象)中tell的函数属性,没有则返回None
# print(f == obj.tell)          #True
# f()
# obj.tell()                   #与f()调用结果相等


# 3、setattr              #设置属性
# People.x=111
# setattr(People,'x',111)
# print(People.x)

# obj.age=18
# setattr(obj,"age",18)
# print(obj.__dict__)

# 4、delattr               #删除属性
# del People.country
# delattr(People,"country")
# print(People.__dict__)

# del obj.name
# delattr(obj,"name")
# print(obj.__dict__)





class Foo:
    def run(self):
        while True:
            cmd=input('cmd>>: ').strip()
            # print('%s run...' %cmd)
            if hasattr(self,cmd):            #查看属性,用户输入的字符串是download或upload程序才会获得该属性,否则重复循环输入
                func=getattr(self,cmd)         #获取属性
                func()

    def download(self):
        print('download....')

    def upload(self):
        print('upload...')

obj=Foo()
obj.run()

三、__str__ 方法

class People:
    def __init__(self,name,age,sex):
        self.name=name
        self.age=age
        self.sex=sex

    def __str__(self):             #改变对象的字符串显示,如果要把一个类的实例变成 str,就需要实现特殊方法__str__():
        # print('========>')           #__str__()用于显示给用户
        return '<名字:%s 年龄:%s 性别:%s>' %(self.name,self.age,self.sex)

obj=People('egon',18,'male')
print(obj) #print(obj.__str__())

# l=list([1,2,3])
# print(l)

四、__del__ 方法

 import time
#
# class People:
#     def __init__(self,name,age,sex):
#         self.name=name
#         self.age=age
#         self.sex=sex
#
#     def __del__(self): # 在对象被删除的条件下,自动执行,没有被删除时不会执行
#         print('__del__')
#
#
# obj=People('egon',18,'male')
# time.sleep(5)                  #通过延迟后删除属性,可以看到__del__,才会自动执行
# del obj #obj.__del__()






# class Mysql:
#     def __init__(self,ip,port):
#         self.ip=ip
#         self.port=port
#         self.conn=connect(ip,port) # 申请系统资源
#
#     def __del__(self):            #
#         self.conn.close()
#
# obj=Mysql('1.1.1.1',3306)


class MyOpen:
    def __init__(self,filepath,mode="r",encoding="utf-8"):
        self.filepath=filepath
        self.mode=mode
        self.encoding=encoding
        self.fobj=open(filepath,mode=mode,encoding=encoding)

    def __str__(self):      #定义一个字符串并将其值返回
        msg="""
        filepath:%s
        mode:%s
        encoding:%s
        """ %(self.filepath,self.mode,self.encoding)
        return msg

    def __del__(self):
        self.fobj.close()

f=open('a.txt',mode='r',encoding='utf-8')

f=MyOpen('aaa.py',mode='r',encoding='utf-8')
print(f.filepath,f.mode,f.encoding)
print(f)

print(f.fobj)
res=f.fobj.read()
print(res)

五、元类

定义:

元类:类的类就是元类
 code="""
# global x
# x=0
# y=2
# """
# global_dic={'x':100000}
# local_dic={}
# exec(code,global_dic,local_dic)
#
# print(global_dic)
# print(local_dic)

#
# code="""
# x=1
# y=2
# def f1(self,a,b):
#     pass
# """
# local_dic={}
# exec(code,{},local_dic)
# print(local_dic)
#



#1、一切皆为对象:

# Chinese=type(...)
# class Chinese:
#     country="China"
#
#     def __init__(self,name,age,sex):
#         self.name=name
#         self.age=age
#         self.sex=sex
#
#     def speak(self):
#         print('%s speak Chinese' %self.name)
#
# print(Chinese)
# p=Chinese('egon',18,'male')
# print(type(p))

# print(type(Chinese))
# 元类:类的类就是元类,
#我们用class定义的类使用来产生我们自己的对象的
#内置元类type是用来专门产生class定义的类的

class Foo: #Foo=type(...)
    pass

# print(type(Foo))
# f=Foo
#
# l=[Foo,]
# print(l)

#2、用内置的元类type,来实例化得到我们的类
# class_name='Chinese'
# class_bases=(object,)
# class_body="""
# country="China"
# def __init__(self,name,age,sex):
#     self.name=name
#     self.age=age
#     self.sex=sex
# def speak(self):
#     print('%s speak Chinese' %self.name)
# """
# class_dic={}
# exec(class_body,{},class_dic)

# 类的三大要素
# print(class_name,class_bases,class_dic)

# Chinese=type(class_name,class_bases,class_dic)
# print(Chinese)

# p=Chinese('egon',18,'male')
# print(p.name,p.age,p.sex)


#3、储备知识__call__
# class Foo:
#     def __init__(self):
#         pass
#     def __str__(self):
#         return '123123'
#
#     def __del__(self):
#         pass
#
#     # 调用对象,则会自动触发对象下的绑定方法__call__的执行,
#     # 然后将对象本身当作第一个参数传给self,将调用对象时括号内的值
#     #传给*args与**kwargs
#     def __call__(self, *args, **kwargs):
#         print('__call__',args,kwargs)
#
#
# obj=Foo()
# # print(obj)
#
# obj(1,2,3,a=1,b=2,c=3) #


# #4 、自定义元类:
# class Mymeta(type):
#     # 来控制类Foo的创建
#     def __init__(self,class_name,class_bases,class_dic): #self=Foo
#         # print(class_name)
#         # print(class_bases)
#         # print(class_dic)
#         if not class_name.istitle():
#             raise TypeError('类名的首字母必须大写傻叉')
#
#         if not class_dic.get('__doc__'):
#             raise TypeError('类中必须写好文档注释,大傻叉')
#
#         super(Mymeta,self).__init__(class_name,class_bases,class_dic)
#
#     # 控制类Foo的调用过程,即控制实例化Foo的过程
#     def __call__(self, *args, **kwargs): #self=Foo,args=(1111,) kwargs={}
#         # print(self)
#         # print(args)
#         # print(kwargs)
#
#         #1 造一个空对象obj
#         obj=object.__new__(self)
#
#         #2、调用Foo.__init__,将obj连同调用Foo括号内的参数一同传给__init__
#         self.__init__(obj,*args,**kwargs)
#
#         return obj
#
#
#
# #Foo=Mymeta('Foo',(object,),class_dic)
# class Foo(object,metaclass=Mymeta):
#     """
#     文档注释
#     """
#     x=1
#     def __init__(self,y):
#         self.Y=y
#
#     def f1(self):
#         print('from f1')
#
#
# obj=Foo(1111) #Foo.__call__()
#
# # print(obj)
# # print(obj.y)
# # print(obj.f1)
# # print(obj.x)





# 单例模式
import settings

class MySQL:
    __instance=None
    def __init__(self,ip,port):
        self.ip=ip
        self.port=port

    @classmethod
    def singleton(cls):
        if not cls.__instance:
            obj=cls(settings.IP, settings.PORT)
            cls.__instance=obj
        return cls.__instance

obj1=MySQL('1.1.1.2',3306)
obj2=MySQL('1.1.1.3',3307)
obj3=MySQL('1.1.1.4',3308)

# obj4=MySQL(settings.IP,settings.PORT)
# print(obj4.ip,obj4.port)

obj4=MySQL.singleton()
obj5=MySQL.singleton()
obj6=MySQL.singleton()

print(obj4 is obj5 is obj6)

  


原文地址:https://www.cnblogs.com/sui776265233/p/8868222.html