前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >极简Python入门

极简Python入门

作者头像
智能算法
发布2018-04-03 11:34:51
1.3K0
发布2018-04-03 11:34:51
举报
文章被收录于专栏:智能算法

本文旨在帮助从总体上帮助了解Python的一些基本属性,具体的使用技巧需要通过不断实践积累

一、Python的基本特性

二、Python的类

面向对象编程,是一种程序设计思想。OOP把对象作为程序的基本单元,一个对象包含了数据和操作数据的函数。

1、类

创建办法:

class Student(object): pass

如果没有合适继承类,使用object类,所有类都会继承的类。通过__init__方法,可以将必须绑定的属性强制写入。

class Student(object): def __init__(self, name, score): self.name = name self.score = score

第一参数永远是self,创建的实例本身。

2、访问限制

在类变量的前加入__,就会变成私有变量。内部能访问,外部不能访问。私有变量的实现其实是对变量别名。

class Student(object):

def __init__(self, name, score):

self.__name = name

self.__score = score

python解释器对外将__name变量改成_Student__name。访问_Student__name还是可以访问__name变量。

类似:__XXX__是特殊变量,可以直接引用,但是有特殊用途,如if __name__ == '__main__':,我们自己变量一般不用这种变量名。

_XXX和__XXX这样的函数和变量“不应该”被直接引用。

3、继承与多态

从现有的class继承,新的class称为子类。被继承的class称为基类、父类、或超类。如:

class Animal(object):

def run(self):

print('Animal is running...')

Dog,Cat从Animal继承:

class Dog(Animal):

pass

class Cat(Animal):

pass

作用:

(1)继承类获得父类的全部功能;Dog,Cat都有run()方法,也可以增加自己的方法。

(2)可以对继承方法修改。当子类和父类都有同一方法时,调用时,子类覆盖父类的方法。提现继承的多态性,一个Dog实例化的对象,即是属于Dog类,也属于Animal类。

(3)继承可以一级一级继承下来。因此一个类可以继承多个类的特性。

4、动态语言和静态语言

编写一个接受Animal类型的变量

def run_twice(animal):

animal.run()

animal.run()

可以对实例后传参,run_twice(Dog())、run_twice(Cat());

对于静态语言,如果需要传入Animal类型,则传入对象必须是Animal类或者它的子类,否则不能调用run方法。但是对于python这种动态语言而言,只需要保证传入对象有一个run()方法就可以了。

class Timer(object):

def run(self):

print('Start...')

因此也能调用run_twice函数调用run()方法。run_twice(Timer())。也就是只要一个对象“看起来像鸭子,走起路来像鸭子”,那它就可以看做鸭子。

5、获取对象信息

(1)type():判断对象类型;

(2)isinstance():判断class的类型,判断一个对象是否属于某个类。能用type判断的类型也能用isinstance()判断。

(3)dir():获取一个对象的所有属性和方法。

(4)之前说的__xxx__有特殊作用,比如__len__方法,我们调用len()函数获取对象长度时,len()函数内部会自动调用__len__()方法。

因此,计算len('ABC')等价'ABC'.__len__()

(5)利用getattr()、setattr、hasattr可以直接操作对象的状态。

hasattr():判断是否有某个属性;

getattr():获取属性值

setattr():设置一个属性值。


三、Python高级属性

1、__slots__

定义一个class,创建实例后,我们可以给实例绑定任何属性和方法。由于动态语言的灵活性。

class Student(object):

pass

实例化,s = Student()

s.name = 'Michiael'

或绑定方法

def set_age(self,age):

self.age = age

from types import MethodType

s.set_age = MethodType(set_age,s)

但是给一个实例绑定的方法,在另一个实例中不起作用。

如果需要限制实例的属性,只允许name和age属性。可以用__slots__变量限制。

class Student(object):

__slots__ = ('name','age')

__slots__定义属性只对当前实例起作用,对于继承的子类不起作用。

2、@property

在绑定属性时,属性的值可以随便改动,无法检查参数。如 s.score = 9999,需要限制score范围,因此可以设置set_score()和get_score()获取成绩

class Student(object):

def get_score(self):

return self._score

def set_score(self, value):

if not isinstance(value, int):

raise ValueError('score must be an integer!')

if value < 0 or value > 100:

raise ValueError('score must between 0 ~ 100!')

self._score = value

s = Student()后,s.set_score(60)是正常的,s.set_score(9999)会报错。

但是这种限制方法,调用比较复杂,是否能实现s.score = 9999这样简单的访问变量,又能检查参数,python的@property能够实现,它是将一个方法变成属性调用。

class Student(object):

@property

def score(self):

return self._score

@score.setter

def score(self, value):

if not isinstance(value, int):

raise ValueError('score must be an integer!')

if value < 0 or value > 100:

raise ValueError('score must between 0 ~ 100!')

self._score = value

上面将getter方法变成了属性值,@property又创建一个装饰器@score.setter将setter方法变成属性赋值。

3、多重继承

一个子类可以继承多个父类,通过多重继承,一个子类就可以同时获得多个父类的所有功能。

通常类的继承关系。都是主线单一继承下来的。这样在继承多个类时,会导致复杂而庞大的继承链。如果需要混入额外的功能,可以进行同时继承多个类,这种设计成为Mixin。

如:

class Dog(Mammal,RunnableMinxIN, \

CarnivorousMixin):

pass

4、定制类

Pythonc的class中有许多特殊用途的函数,可帮助定制类。

(1)__str__:显示字符

(2)__iter__:需要设置一个类,像for ...in循环访问,类似list或tuple,需要实现__iter__方法。

(3)__getitem__:虽然实现__iter__能够作用for循环,但是还是不能像list那样取元素,如果想像list按照下标取出元素,需要实现__getitem__方法。

def __getitem__(self, n):

a, b = 1, 1

for x in range(n):

a, b = b, a + b

return a

(4)__getattr__:python调用不存在的属性时,一般程序会报错,如果加入__getattr__,Python试图调用,来获取属性。

(5)__call__:调用实例方法时,是通过instance.method()调用,通过__call__可实现在实例本身调用。或者说,将类对象当做函数使用。如:

class DistanceForm(object):

def __init__(self, origin):

self.origin = origin

print "origin :"+str(origin)

def __call__(self, x):

print "x :"+str(x)

p = DistanceForm(100)

p(2000) #类似函数方式,直接赋值调用。

python还有很多定制方法。可查官网。

5、使用元类

type()函数既可以返回一个对象的类型,也可以创建一个新的类型。比如可以用type创建一个类。

Hello = type('Hello', (object,), dict(hello=fn))

创建的参数:

(1)class的名称;

(2)继承的父类集合,注意Python支持多重继承,如果只有一个父类,别忘了tuple的单元素写法;

(3)class的方法名称与函数绑定,这里我们把函数fn绑定到方法名hello上。除了通过type()动态创建类外,还可以是使用mataclass。元类是类的类。一个实例创建的完整过程应该是,先创建一个元类,元类创建类,类创建实例。

type函数实际就是一个元类,也是Python背后创建所有类的元类。

我们可以自定义元类:

# metaclass是类的模板,所以必须从`type`类型派生:

class ListMetaclass(type):

def __new__(cls, name, bases, attrs):

attrs['add'] = lambda self, value: self.append(value)

return type.__new__(cls, name, bases, attrs)

class MyList(list, metaclass=ListMetaclass): pass

Mylist创建时,是通过ListMetaclass.__new__创建。因此可以修改类的定义,或加入新方法。

__new__()方法接收到的参数依次是:

1、当前准备创建的类的对象;

2、类的名字;

3、类继承的父类集合;

4、类的方法集合。

实例化:

L = MyList() 此时可以实现 add调用。L.add(1)


四、Python小实践

实现模式向kindle中推送任意数量本地书籍:

# sendmail.py

from email.mime.text import MIMEText

from email.mime.multipart import MIMEMultipart

import smtplib

from os.path import basename

from_addr = "xxxxxx@126.com"

password = "######"

to_addr = "xxxxxx@kindle.cn"

smtp_server = "smtp.126.com"

def send_mail(attachments=None):

msg = MIMEMultipart()

msg['Subject'] = "SendingBook"

msg['From'] = from_addr

msg['To'] = to_addr

msg['Accept-Language'] = 'zh-CN,utf-8'

msg['Accept-Charset'] = 'ISO-8859-1,utf-8'

attachments = [ "D:/电子书/kindle/"+x for x in attachments]

for attachment in attachments or []:

files=attachment

file_name = basename(attachment)

attr = MIMEText(open('%s'%files,'rb').read(),'base64','utf-8')

attr["Content-Type"] = 'application/octet-stream'

attr["Content-Disposition"] = 'attachment;filename="%s"'%file_name

msg.attach(attr)

server = smtplib.SMTP(smtp_server)

server.starttls()

server.login(from_addr,password)

server.sendmail(from_addr,to_addr,msg.as_string())

server.quit()

if __name__=='__main__':

import sys

if len(sys.argv) > 1:

attachment = sys.argv[1:]

else:

attachment = []

send_mail(attachment)

调用方法:python sendmail.py Python-web-spider.mobi ,目前调用时,存在一个问题,书籍名中不支持中文。

参考地址:http://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000

免责声明:本文系网络转载。版权归原作者所有。如涉及版权,请联系删除!

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2017-05-20,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 智能算法 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档