剑指offer
Posted venicid
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了剑指offer相关的知识,希望对你有一定的参考价值。
一、Python基础
1、什么是python?使用python有什么好处?
python是一种编程语言,它有对象、模块、线程、异常处理和自动内存管理。它简洁,简单、方便、容易扩展、有许多自带的数据结果,而且它开源
Python是一种解释性语言,它的源代码可以直接运行,Python解释器会将源代码转换成中间语言,之后再翻译成机器码再执行
2、可变类型与不可变类型
可变类型:list、dict、可变集合set
不可变类型:数字,str,tuple元组,frozenset
内存中的那块内容(value)是否可变
可直接在原来的地址,修改
不可变的类型都可以被hash哈希
3、深浅copy
对不可变类型进行copy的话,都是深copy
对于可变类型进行copy的话,一般都是浅copy
浅拷贝只是增加了一个指针指向所复制的对象,共用一块内存
深拷贝是增加一个指针并且开辟了新的内存,这个增加的指针指向这个新的内存,
In [42]: li = [1,2,3,[4,5]]
In [43]: li2 = copy.copy(li)
In [44]: li3 = copy.deepcopy(li)
In [45]: li[-1][-1] = "222"
In [46]: li
Out[46]: [1, 2, 3, [4, '222']]
In [47]: li2
Out[47]: [1, 2, 3, [4, '222']]
In [48]: li3
Out[48]: [1, 2, 3, [4, 5]]
简单来说,如果有嵌套的话,浅copy只复制第一层,深copy会复制所有的
4、range-and-xrange
py2:
range() 生成的是列表
xrange() 生成的是一个生成器
py3:
range() 就是一个生成器
xrange() 没了
5、闭包
def func():
def inner():
print('aaaa')
return inner
func()() # aaaa
内部函数对外部函数作用域里变量的引用(非全局变量),则称内部函数为闭包。
闭包的意义:返回函数对象+一层作用域,这使得,该函数无论在何处调用,优先使用自己外层包裹的作用域
6、装饰器
调用装饰器其实是一个闭包函数,
不修改函数的代码与修饰方式,为其他函数添加附加功能
比如:插入日志、性能测试、事物处理、缓存、权限验证等
# 装饰器
import time
def login(func):
def inner():
start_time = time.time()
func()
end_time = time.time()
print("fun 执行时间",end_time-start_time)
return inner
@login
def test():
for i in range(10000):
for j in range(10000):
pass
print('test函数执行')
test()
# test函数执行
# fun 执行时间 2.0163347721099854
7、生成器
延迟操作,需要的时候才产生结果,而不是立即产生结果
在每次调用next()的时候执行,遇到yield语句返回
创建生成器的两种方式:
li = [i for i in range(100)]、yield方法
8、迭代器
for循环的数据类型:集合数据类型+生成器
list,tuple,dict,set,str + generator
不是一次性把数据加载到内存,而是被next()函数调用,不断返回下一个数据
9、*args与**kwargs
*args:位置参数 (‘alex‘,18)
**kwargs:关键字参数 {‘name‘=‘alex‘,‘age‘=18} 关键字参数一定要放在最后面
二、面向对象
1、经典类、新式类
经典类:深度优先,python2中
新式类:广度优先,Python3中
2、继承、多态、封装
(1)继承:类与类之间关系,Cat类是动物类,解决代码重用问题
重用 父类的属性与方法
def __init__(self, name, life_value, aggresivity, weapon):
super().__init__(name, life_value, aggresivity,) # python3格式
self.weapon = weapon
def attack(self, enemy):
super().attack(enemy)
(2)多态:同一类事物多种形态
一个接口,多种形态
不应关注对象的类型本身,而是它如何使用的
鸭子类型:如果看起来像、叫声像而且走起路来像鸭子,那么它就是鸭子’
(3)封装
私有化的属性,私有化的方法,封装起来,外部无法调用 双下划线__foo
3、classmethod,staticmethod,property
(1)property:特性 (统一访问 原则)
@property
def bmi(self):
return self.weight / (self.height ** 2)
把类的方法转换为属性,直接 alex.bmi 调用
(2)staticmethod 静态方法 (普通函数 ) 绑定到对象上
类内的函数实例化---> 普通函数 。 (类和对象都可以使用)
@classmethod
def from_conf(cls):
obj = settings.name,
return obj
(3)classmethod 类方法 (def foo(cls)) 绑定到类上
将cls 类本身当做参数传入,直接用类来调用函数,而不用借助类实例
优雅地实现某个类的实例的构造
4、 new.init区别,如何实现单例模式
创建一个新实例时调用new new()在 init()之前被调用
初始化一个实例时调用init
单例模式设计的类只能实例化1个对象
# 方式1 python模板自带单例模式
# admin.py
class Admin(object):
def register(self):
pass
site = Admin()
# test.py
from admin import site
site.register()
# 方式2 __new__ _instance
class Single(object):
_instance = None
def __new__(cls,*args,**kwargs):
if not cls._instance:
cls._instance = super(Single,cls).__new__(cls,*args,**kwargs)
return cls._instance
5、反射
“字符串”形式,操作对象的相关属性或方法。
hasattr, getattr, setattr, delattr
ret = getattr(obj,'get_file')() # 反射 obj是实例对象,name是方法
三、并发
1、线程、进程的区别
(1)进程:程序的运行过程, os 资源调度、分配的基本单位 os的并发
(2)线程:进程的实体, cpu 调度、分派的基本单位 进程内部的并发
区别
1、进程有独立的内存空间, 线程 共享 本进程 的内存空间
2、进程有独立的系统资源 ,线程只有(程序计数器,一组寄存器,栈) 共享本进程的资源(内存,I/O,cpu)
3、独立性:进程崩溃,不会影响其他的(健壮) 线程崩溃,本进程的全部线程死掉
4、开销:进程切换与创建 开销大于 线程的
5、线程不能独立执行 进程可以
联系
都可并发、一个进程由1or多个线程 组成、一个进程中的所有线程共享该进程全部资源
2、协程、GIL
GIL:全局解释器锁(cpython解释器), 同一时刻,在cpu只能有一个线程执行
协程:轻量级的线程,用户控制调度的
单线程下(的并发), 遇到I/O阻塞,多个任务,自动切换
3、进程同步方式
1、Event事件 。 通知操作
2、互斥量。 加锁
3、信号量。 生产者消费者模型 阻塞队列Queue
4、临界区 。保护区域
同步问题:生产者消费者模型,作者读者问题,哲学家进餐问题
4、通信方式
管道,系统IPC(消息队列,信号量,信号,共享内存),套接字,远程过程调用rpc
5、死锁
多个进程运行,争夺资源,一种僵局;没有外力,进程,无法继续执行
导致死锁的原因:循环等待、不可抢占、占有且等待、互斥
死锁处理:
1、预防 :破坏4个条件
2、避免:银行家算法
3、检测:算法检测,清除死锁
4、解除: 检测到,撤销进程or剥夺资源
6、select、poll和epoll (I/O多路复用)
可以监视多个描述符
一个描述符就绪,通知应用程序,执行读or写操作
(1)select :
把文件描述符 fd 集合maxSize=1024,用户态copy到内核态 开销大,在内核,遍历所有fd
(2)poll:
改善了连接数,不断轮询,fd集合 每次都copy到内核态
(3)epoll:
linux下的多路复用I/O接口, 只copy一次,只告知 ,刚变为就绪状态的fd
四、mysql数据库
1、索引
B+数:二叉树-->平衡二叉树-->B数
一个排序好,数据结构 (协助快速查询data) 范围查询
create index ix_age on t1(age);
create index 索引名1,索引名2 on 表名('字段1','字段2')
(1)什么时候用?
经常 select查询、表记录超多
经常需要搜索的列、主键列、连接的列(外键)、范围查找 age in [20,40]、排序的列 salary、where上的列
(2)什么时候不用?
经常update,delete,insert 表记录少
不经常使用的列 addr,数据值很少的列 blog,文本,image,bit 修改>查询的
2、存储过程
相当于 函数,封装了,一系列,可执行的sql语句,存放在mysql中
直接调用它的名称
create procedure p1()
BEGIN
select * from blog;
INSERT into blog(name,sub_time) values("xxx",now());
END
优点:网络传输量小,程序与slq解耦
缺点:程序猿拓展功能不方便
3、数据库引擎
INNODB 支持事务,外键,行锁, 查表总行数,全表扫描
MYISAM不支持事务,不支持外键,表锁(插入data,锁定这个表),查表总行数,不需要全表扫描
4、redis
key-value数据库 ,经常用的data放在redis
性能极高,支持多种数据类型 ,放在内存中 (必要时可以写入硬盘)
五、网络
1、http常用的状态码
200:请求成功 OK
202:服务器接受请求,尚未处理
302:重定向
304??:上次的文档,已被缓存, 还可继续使用
400:客户端请求语法or参数错误
403:服务器收到请求,拒绝提供服务,找不到cookie
404:客户端请求的资源url不存在
500: 服务器的程序出现错误
503:服务器当前时间不能处理客户端的请求,一段时间后恢复
2、HTTP请求方式
HTTP1.0 GET/HEAD/POST
HTTP1.1 PUT/DELETE/CONNECT/OPTIONS/TRACE
3.GET/POST区别
(1)get提交的数据放在url后 /?name=alex&age=18 http请求头
post的数据放在http报请求体
(2)GET的数据大小有限制,POST没有限制
(3)GET方式会带来安全问题,在url出现信息,可能获得username password
(4)在服务端 获取请求数据方式不同
4、http请求头,请求体
协议版本,状态码,状态码原因 HTTP /1.1 200 OK
Cookie:
Content-Language
Content-Type 文本类型
Content-Length 请求体长度
User-Agent: 浏览器的身份标识,类型,手机端or电脑端
Date:时间
请求体
5、TCP/UDP区别 (运输层)
1、TCP 传输控制协议,面向连接的,可靠的,数据流传输 ,注重data安全性,传输慢,面向字节流
2、UDP用户数据报文协议,非面向连接的,不可靠,数据流传输, data传输快,安全性一般,面向报文
以上是关于剑指offer的主要内容,如果未能解决你的问题,请参考以下文章
剑指 Offer(第 2 版)完整题解笔记 & C++代码实现(LeetCode版)
LeetCode(剑指 Offer)- 14- I. 剪绳子
LeetCode(剑指 Offer)- 14- I. 剪绳子
剑指 Offer 45. 把数组排成最小的数 剑指 Offer 61. 扑克牌中的顺子 剑指 Offer 40. 最小的k个数