面试题
- 面试题(更新中...)
- 1.python基础
- 1.为什么学习python
- 3.公司线上和开发环境使用什么系统?
- 4.Python和Java,PHP,C,C#,C++等其他语言对比.
- 5.简述解释性语言和编译型编程语言
- 6.python解释器种类以及特点
- 7. 位和字节的关系:
- 8.b.B.KB.MB,GB的关系
- 9.请至少列举5个PEP8规范
- 10.求结果or and
- 11.ascii,unicode,utf-8,gbk的区别?
- 12.字节码和机器码的区别
- 13.三元运算编写格式
- 14.列举你了解的所有py2和py3的区别
- 16 用一行代码实现数值交换
- 17. python3和python2中int和long的区别
- 19.range和xrang有什么不同
- 20.写一个脚本,接收两个参数。
- 1.python基础
- 执行脚本: python test.py oldboy.txt 你好
- 21.def f(a,b=[ ]) 这种写法有什么陷阱?
- 22.json序列化时,如何保留中文?
- 23.sys.path.append( )的作用?
- 24.递归的最大次数是多少?
- 25.readline()和readlines()的区别
- 26.*args和**kwargs这俩参数是什么意思?我们为什么要用它。
- 27.python中的垃圾回收机制
- 28.什么是匿名函数?
- 29.filter/map/reduce是什么意思?
- 30.发红包(拼手气红包)
- 31.计算任意一个文件夹的大小(考虑绝对路径的问题)
- 32.校验大文件的一致性
- 33.GIL锁
- 33.一句话说清楚继承多态封装
- 34.生成器题
- 35.锁、队列、池
- 36.GIL锁,线程,进程,协程
- null
面试题(更新中...)
1.python基础
1.为什么学习python
- 语法简洁,适合小白入门
- 类库强大,是运维自动化\数据分析,机器学习的首选编程语言
3.公司线上和开发环境使用什么系统?
一般是Linux系统和centos(服务器)Ubuntu(个人开发)
4.Python和Java,PHP,C,C#,C++等其他语言对比.
python相对于其他语言的优点:1.简单2.免费开源3.兼容性好4.面向对象5.有很多python库
5.简述解释性语言和编译型编程语言
解释型:一边解释(解释器)一边执行.
编译型:先编译(编译器)后执行
6.python解释器种类以及特点
Cpython:Python的官方版本,使用C语言实现,使用最广泛,Cpython实现会将源文件(py文件)转换为字节码文件(pyc文件),然会运行在python虚拟机上
JPython:python的Java实现,JPython会将Python代码动态编译成Java字节码然后再JVM上运行
IronPython:Python的C#实现,IronPython将Python代码编译成C#字节码,然后再CLR上运行.(与Jpython类似)
pypy:python实现的python,将python的字节码在编译成机器码.
.rubypython prython等
7. 位和字节的关系:
1字节等于8位
8bit=1byte
8.b.B.KB.MB,GB的关系
8bit =1byte
1024byte = 1KB
1024KB = 1MB
1024MB = 1GB
9.请至少列举5个PEP8规范
-
使用4个空格缩进,不要使用制表符。
4个空格是一个在小缩进(允许更大的嵌套深度)和大缩进(更容易阅读)的一种很好的折中方案。制表符会引入混乱,最好不要使用它。
-
换行,使一行不超过79个字符。
这有助于使用小型显示器的用户,并且可以在较大的显示器上并排放置多个代码文件。
-
使用空行分隔函数和类,以及函数内的较大的代码块。
-
如果可能,把注释放到单独的一行。
-
使用文档字符串。
-
在运算符前后和逗号后使用空格,但不能直接在括号内使用:
a = f(1, 2) + g(3, 4)
。 -
类和函数命名的一致性;规范是使用
CamelCase
命名类,lower_case_with_underscores
命名函数和方法。始终使用self
作为第一个方法参数的名称。 -
如果你的代码旨在用于国际环境,请不要使用花哨的编码。Python 默认的 UTF-8 或者纯 ASCII 在任何情况下都能有最好的表现。
-
同样,哪怕只有很小的可能,遇到说不同语言的人阅读或维护代码,也不要在标识符中使用非ASCII字符。
10.求结果or and
1.v1 = 1 or 3
v1 = 1
2. v2 = 1 and 3
v2 = 3
3.v3 =0 and 2 and 1
v3 = 0
4. v4 = 0 and 2 or 1
v4 = 1
5. v5 = 0 and 2 or 1 or 4
v5 = 1
6.v6 =0 or Flase and 1
v6 = 0
11.ascii,unicode,utf-8,gbk的区别?
ascii :1个字节表示一个字符
Unicode:4个字节表示一个字符
utf-8:unicode的压缩,最少使用1个字节表示一个字符,3个字节表示一个中文字符
gbk:2个字节表示一个中文字符
12.字节码和机器码的区别
机器码是电脑CPU可以直接解读的数据
字节码,一种包含执行程序,由一序列操作代码/数据组成的二进制文件.它是一种中间代码需要转译可以变成机器码
总结:字节码的出现实现了软件运行与硬件无关.编译器将源码编译成字节码,字节码经过虚拟机转译成可以在机器上直接执行的机器码.
13.三元运算编写格式
表达式1 计算条件 表达式 else 表达式2
c = a if a < b else b
14.列举你了解的所有py2和py3的区别
-
py2的解释器默认编码:ascii py3的解释器默认编码:utf-8
-
输入py2:raw_input py3:input
-
输出py2:print 'xx' py3:print("xx")
-
py2 整型有int和long py3:只有int
-
py2 除法/只有整数部分 py3除法/整数小数都有
-
字符串类型不同 py3: str bytes py2: unicode str
-
range和xrang
-
模块和包 py2 文件夹中有_ _ init _ _才能是包
-
字典 / map / filter不一样
keys values items map/filter py2 列表 列表 列表 列表 py3 迭代器,可以循环但不可以索引 迭代器,可以循环但不可以索引 迭代器,可以循环但不可以索引 返回迭代器,可以循环但不可以索引
16 用一行代码实现数值交换
-
a=1
-
b=2
a,b=b,a
17. python3和python2中int和long的区别
py3中只有int
py2中有int和long
19.range和xrang有什么不同
range会直接生成一个list对象
xrange不直接生成List,而是在访问的时候再生成相应的值
20.写一个脚本,接收两个参数。
- 第一个参数:文件
- 第二个参数:内容
请将第二个参数中的内容写入到 文件(第一个参数)中。
执行脚本: python test.py oldboy.txt 你好
import sys
if len(sys.argv) < 3:
print('参数不够,请重新运行')
# sys.exit(0)
else:
file_path = sys.argv[1]
content = sys.argv[2]
with open(file_path,mode='w',encoding='utf-8') as f:
f.write(content)
# 备注 :在cmd运行 执行py文件之前,输入文件名,
21.def f(a,b=[ ]) 这种写法有什么陷阱?
···
b是可变类型,给b传参的时候,会一直往b列表里添加值,而不会接收到新的值
'''
22.json序列化时,如何保留中文?
import json
a={"a":"你好","b":"sdas"}
data=json.dumps(a,ensure_ascii=False) #序列化保留中文
print(data)
23.sys.path.append( )的作用?
sys.path.append( "/root/mods" )
把"/root/mods"加到python模块导入的路径地址中,即添加到环境变量中
24.递归的最大次数是多少?
import sys
a=sys.getrecursionlimit()
print(a) #1000
25.readline()和readlines()的区别
![img](file:///D:\MyBackup\我的文档\Tencent Files\799147897\Image\Group\PIL73XQP3LZ]KYU~JMAM5S1.png)
26.*args和**kwargs这俩参数是什么意思?我们为什么要用它。
如果我们不确定要往函数中传入多少个参数,或者我们想往函数中以列表和元组的形式传递参数时要用 * args;如果我们不知道要往函数中传入多少个关键词参数,或者想传入字典的值作为关键词参数时,那就要使用 ** kwargs。
注意: * args和 ** kwargs可以同时在函数的定义中,但是 * args必须在 * *kwargs前面。
*接受参数可聚集,*传入参数可解包
27.python中的垃圾回收机制
28.什么是匿名函数?
一般和map filter 搭配使用,需要把函数赋值给一个变量,调用变量,
def func():
pass
v = [lambda x:x+100,]
29.filter/map/reduce是什么意思?
map,循环每个元素(第二个参数),然后让每个元素执行函数(第一个参数),将每个函数执行的结果保存到新的列表中,并返回。
result = map(lambda x:x+100,v1) # 特殊 python3出来的是一个对象(可迭代),python3为了节省内存,python2直接返回列表
filter 对于序列中的元素进行筛选,最终获取符合条件的序列
result = filter(lambda x: type(x) == int ,v1) #如果函数返回True,filter就拿到该元素
reduce 对于序列内所有元素进行累计操作 【前2个累计(相加),累计的结果与后面下一个元素相加】
30.发红包(拼手气红包)
每个人抢到的金额是随机 1# 每一个人能够抢到金额的概率都是平均的 2# 小数的不准确性的问题
# ############################ 算法分析 ############################
比如10个人抢,一条绳子 上随机取9个点,再加上一头一尾,从小到大排序,相邻2个数相减,得到10个值
抢红包就是抢:随机抢这十个值
############### Eva_J ####################
import random
def red_pack(money,num):
ret = random.sample(range(1,money*100),num-1)
# 乘以100。 random.sample()拿不到重复的,一次性拿9个,每个不重复
ret.sort()
ret.insert(0,0)
ret.append(money*100)
for i in range(len(ret)-1):
yield (ret[i+1] - ret[i])/100
#除以100,精确到分钱 解决了小数不准确的问题
ret = red_pack(200,5)
for i in ret:
print(i)
################## my code #########################
import random
class Red_package:
def __init__(self,people,money):
self.people=people
self.money=money
def func(self):
point_list=[]
money_list=[]
for i in range(self.people-1):
point=round(random.randint(0,self.money*100),2) random.randint
point_list.append(point)
point_list.extend([0,self.money*100])
point_list.sort()
for i in range(self.people):
x=(point_list[i+1]-point_list[i])/100
money_list.append(x)
random.shuffle(money_list)
return iter(money_list)
obj=Red_package(10,1)
v=obj.func()
print(v)
for i in v:
print(i)
31.计算任意一个文件夹的大小(考虑绝对路径的问题)
基础需求 : # 这个文件夹中只有文件
进阶需求 : # 这个文件夹中可能有文件夹,并且文件夹中还可能有文件夹...不知道有多少层
##### my code ###### os。walk()
import os
def calculate(arg):
result=os.walk(arg)
size=0
for a,b,c in result: # a是当前文件夹路径,b所有文件夹,c是所有文件
print(c)
for item in c:
path = os.path.join(a, item)
size+=os.path.getsize(path)
# getsize() 要传文件的路径(不一定是绝对路径),能找到文件即可,前面用join()拼接
return size
path=r"D:\MyBackup\我的文档\Tencent Files\799147897\FileRecv"
val=calculate(path)
print(val)
####### Evj_code ##### os。walk()
import os
def dir_size(path):
ret = os.walk(path)
sum_size = 0
for base_path,dir_lst,file_lst in ret:
for file_name in file_lst:
size = os.path.getsize(os.path.join(base_path,file_name))
sum_size += size
return sum_size
ret = dir_size(r'D:\视频\全栈 21期\day23')
print(ret)
####### 基于listdir完成计算文件夹总大小 #####
基于listdir完成计算文件夹总大小
# 1.递归 http://www.cnblogs.com/Eva-J/articles/7205734.html
# 2.堆栈 递归函数-三级菜单 http://www.cnblogs.com/Eva-J/articles/7197403.html
32.校验大文件的一致性
基础需求 # 普通的文字文件
进阶需求 # 视频或者是图片
#
import hashlib
path1 = r'D:\视频\全栈21期\day14\05 python fullstack s21day14 回顾和补充:作业题讲解.mp4'
path2 = r'D:\视频\全栈21期\day14\back.mp4'
import os
def file_md5(path):
size = os.path.getsize(path) # 先把
md5 = hashlib.md5()
with open(path,mode='rb') as f: # 按字节读,读出来的是Byte类型的数据
while size>1024:
content = f.read(1024) # 就算 后面的不够1024个字节,就把剩下的都拿到
md5.update(content)
size -=1024
else: # size<1024 跳出循环,执行else,往下走
content = f.read(size)
md5.update(content)
size = 0
return md5.hexdigest()
print(file_md5(path1)== file_md5(path2))
33.GIL锁
# 全局解释器锁
# Cpython解释器提供的
# 导致了一个进程中多个线程同一时刻只有一个线程能当问CPU -- 多线程不能利用多核
33.一句话说清楚继承多态封装
34.生成器题
绝招
生成器取一次值就没了
不取不执行(惰性计算)
第一步:看从哪里开始取值
第一题
生成器主题
1.读代码猜答案
g1 = filter(lambda n:n%2==0,range(10)) #生成器
g2 = map(lambda n:n*2,range(3)) #生成器
for i in g1: # 0 2 4 6 8
for j in g2: # 0 2 4
print(i*j)
# 结果:0 0 0
第二题
2.以下代码的输出是什么?请给出答案并解释。
def multipliers():
return [lambda x:i*x for i in range(4)]
print([m(2) for m in multipliers()])
请修改multipliers的定义来产生期望的结果。
######################################## 第一问 结果 ##########################################
# 结果 [6,6,6,6]
解析:
print([m(2) for m in multipliers()])
i=3
print([m(2) for m in [lambda x:i*x,lambda x:i*x,lambda x:i*x,lambda x:i*x])
######################################## 第二问 结果 ##########################################
def multipliers():
return (lambda x:i*x for i in range(4))
解析:返回的是个生成器
print([m(2) for m in (lambda x:i*x for i in range(4)))
# 结果 :[0,2,4,6]
35.锁、队列、池
# 锁 - 都可以维护线程之间的数据安全
# 互斥锁 :一把锁不能在一个线程中连续acquire,开销小
# 递归锁 :一把锁可以连续在一个线程中acquire多次,acquire多少次就release多少次,开销大
# 死锁现象
# 在某一些线程中出现陷入阻塞并且永远无法结束阻塞的情况就是死锁现象
# 出现死锁:
# 多把锁+交替使用
# 互斥锁在一个线程中连续acquire
# 避免死锁
# 在一个线程中只有一把锁,并且每一次acquire之后都要release
# += -= *= /= ,多个线程对同一个文件进行写操作
# 队列
# 先进先出 Queue
# 后进先出 LifoQueue
# 优先级 PriorityQueue
# 池
# from concurrent.futrues import ThreadPoolExecutor
# 1.是单独开启线程进程还是池?
# 如果只是开启一个子线程做一件事情,就可以单独开线程
# 有大量的任务等待程序去做,要达到一定的并发数,开启线程池
# 根据你程序的io操作也可以判定是用池还是不用池?
# socket的server 大量的阻塞io recv recvfrom socketserver
# 爬虫的时候 池
# 2.回调函数add_done_callback
# 执行完子线程任务之后直接调用对应的回调函数
# 爬取网页 需要等待数据传输和网络上的响应高IO的 -- 子线程
# 分析网页 没有什么IO操作 -- 这个操作没必要在子线程完成,交给回调函数
# 3.ThreadPoolExecutor中的几个常用方法
# tp = ThreadPoolExecutor(cpu*5)
# obj = tp.submit(需要在子线程执行的函数名,参数)
# obj
# 1.获取返回值 obj.result() 是一个阻塞方法
# 2.绑定回调函数 obj.add_done_callback(子线程执行完毕之后要执行的代码对应的函数)
# ret = tp.map(需要在子线程执行的函数名,iterable)
# 1.迭代ret,总是能得到所有的返回值
# shutdown
# tp.shutdown()
# 进程 和 线程都有锁
# 所有在线程中能工作的基本都不能在进程中工作
# 在进程中能够使用的基本在线程中也可以使用
# 在多进程里启动多线程
# import os
# from multiprocessing import Process
# from threading import Thread
#
# def tfunc():
# print(os.getpid())
# def pfunc():
# print('pfunc-->',os.getpid())
# Thread(target=tfunc).start()
#
# if __name__ == '__main__':
# Process(target=pfunc).start()
36.GIL锁,线程,进程,协程
# 1.什么是GIL
# 全局解释器锁
# 由Cpython解释器提供的
# 导致了一个进程中多个线程同一时刻只能有一个线程访问CPU
# 2.在进程、线程中都需要用到锁的概念
# 互斥锁 在一个线程中不能连续acquire多次、效率高,产生死锁的几率大
# 递归锁 在一个线程中可以连续acquire多次、效率低,一把锁永远不死锁
# 3.进程 开销大 数据隔离 能利用多核 数据不安全 操作系统控制
# 线程 开销中 数据共享 cpython解释器下不能利用多核 数据不安全 操作系统控制
# 协程 开销小 数据共享 不能利用多核 数据安全 用户控制
# 在哪些地方用到了线程和协程(高并发场景)
# 1.自己用线程、协程完成爬虫任务
# 2.但是后来有了比较丰富的爬虫框架
# 了解到 scrapy /beautyful soup/aiogttp爬虫框架 哪些用到了线程,哪些用到了协程?
# 3.web框架中的并发是如何实现的
# 传统框架 : django 多线程
# flask 优先选用协程 其次使用线程
# socket server :多线程
# 异步框架 :tornado,sanic底层都是协程
# 4.IPC 进程之间的通信机制
# 内置的模块(基于文件) :Pipe Queue
# 第三方工具(基于网络): redis rabbitmq kafaka memcache 发挥的都是消息中间件的功能
# 5.协程爬取多个url
# import gevent
# import requests
# from gevent import monkey
# monkey.patch_all()
#
# def func(url):
# res = requests.get(url)
# return res.text
# url_l = []
# g_l = []
# for url in url_l:
# g = gevent.spawn(func,url)
# g_l.append(g)
# gevent.joinall(g_l)
# for g in g_l:
# print(g.value)
# 关于作业中的读代码
# 1.开启线程是几乎不需要事件的,start是一个异步非阻塞方法
# 2.对于整数的 += -= 来说 异步的多线程数据不安全,如果是同步的数据就安全了
# 3.对于列表的操作 无论是异步还是同步的 都是数据安全的
28.易错
传给a的不是值,而是参数a指向了1
-
-
-
线上操作系统:centos
-
py2和py3的区别?
-
每种数据类型,列举你了解的方法。
-
3 or 9 and 8 (运算符运算)
-
字符串的反转 切片【列表反转没有返回值】
-
is 和 == 的区别?
-
v1 = (1) / v2 = 1 元组v3=(1,)
-
深浅拷贝
-
文件操作,大文件如何读取内容 [ 50G的日志文件 ]
-
-
v = open(....)
for line in v:
print(line)
v.close()- 用生成器写
- 用游标
-
-
-
一行写出:9*9乘法表【不会】
-
生成斐波那契数列
-
*args **kwargs是什么?可以接受任意个位置参数、关键字参数
-
pass 是什么作用?占位,不执行任何操作
-
global 、nonlocal 【找到全局变量,找到上一级变量】
-
常用的内置函数有哪些?
-
filter/map/reduce是什么意思?
-
什么是匿名函数?
-
git流程
-
*args和**kwargs这俩参数是什么意思?我们为什么要用它。
-
为函数写一个装饰器,在函数执行之后输入 after
@wrapper def func(): print(123) func()
-
为函数写一个装饰器,把函数的返回值 +100 然后再返回。
@wrapper def func(): return 7 result = func() print(result)
-
为函数写一个装饰器,根据参数不同做不同操作。
- flag为True,则 让原函数执行后返回值加100,并返回。
- flag为False,则 让原函数执行后返回值减100,并返回。
@x(True) def f1(): return 11 @x(False) def f2(): return 22 r1 = f1()
-
写一个脚本,接收两个参数。
- 第一个参数:文件
- 第二个参数:内容
请将第二个参数中的内容写入到 文件(第一个参数)中。
# 执行脚本: python test.py oldboy.txt 你好
-
递归的最大次数是多少?
-
看代码写结果
print("你\n好") print("你\\n好") print(r"你\n好")
-
写函数实现,查看一个路径下所有的文件【所有】。
-
写代码
path = r"D:\code\test.pdf" # 请根据path找到code目录下所有的文件【单层】,并打印出来。
-
写代码实现【题目1】和【题目2】
-
看代码写结果
-
实现如下面试题
-
sys.path.append("/root/mods")的作用?
-
字符串如何进行反转?
-
不用中间变量交换a和b的值。
a = 1 b = 2
-
*args和**kwargs这俩参数是什么意思?我们为什么要用它。
-
函数的参数传递是地址还是新值?
-
看代码写结果:
my_dict = {'a':0,'b':1} def func(d): d['a'] = 1 return d func(my_dict) my_dict['c'] = 2 print(my_dict)
-
什么是lambda表达式
-
range和xrang有什么不同?
-
"1,2,3" 如何变成 ['1','2','3',]
-
['1','2','3'] 如何变成 [1,2,3]
-
def f(a,b=[]) 这种写法有什么陷阱?
-
如何生成列表 [1,4,9,16,25,36,49,64,81,100] ,尽量用一行实现。
-
python一行print出1~100偶数的列表, (列表推导式, filter均可)
-
把下面函数改成lambda表达式形式
def func(): result = [] for i in range(10): if i % 3 == 0: result.append(i) return result
-
如何用Python删除一个文件?
-
如何对一个文件进行重命名?
-
python如何生成随机数?
-
从0-99这100个数中随机取出10个数,要求不能重复,可以自己设计数据结构。
-
用Python实现 9*9 乘法表 (两种方式)
#1 for i in range(1,10): for j in range(1,i+1): print("{}*{}={:2} ".format(j,i,i*j),end="") print() #2 result= [ ["{}*{}={:2}".format(j,i,j*i) for j in range(1,i+1)]for i in range(1,10)] for i in result: print(*i)
-
请给出下面代码片段的输出并阐述涉及的python相关机制。
def dict_updater(k,v,dic={}): dic[k] = v print(dic) dict_updater('one',1) dict_updater('two',2) dict_updater('three',3,{})
-
写一个装饰器出来。
-
用装饰器给一个方法增加打印的功能。
-
as 请写出log实现(主要功能时打印函数名)
@log def now(): print "2013-12-25" now() # 输出 # call now() # 2013-12-25
-
向指定地址发送请求,将获取到的值写入到文件中。
import requests # 需要先安装requests模块:pip install requests response = requests.get('https://www.luffycity.com/api/v1/course_sub/category/list/') print(response.text) # 获取结构中的所有name字段,使用逗号链接起来,并写入到 catelog.txt 文件中。 """ [ {'id': 1, 'name': 'Python', 'hide': False, 'category': 1}, {'id': 2, 'name': 'Linux运维', 'hide': False, 'category': 4}, {'id': 4, 'name': 'Python进阶', 'hide': False, 'category': 1}, {'id': 7, 'name': '开发工具', 'hide': False, 'category': 1}, {'id': 9, 'name': 'Go语言', 'hide': False, 'category': 1}, {'id': 10, 'name': '机器学习', 'hide': False, 'category': 3}, {'id': 11, 'name': '技术生涯', 'hide': False, 'category': 1} ] """
-
请列举经常访问的技术网站和博客
-
请列举最近在关注的技术
-
请列举你认为不错的技术书籍和最近在看的书(不限于技术)
-
发红包