Python面试题目和难点解析

文章目录

  • Python 面试题目
    • Python面试基础
    • 编码风格
    • numpy
      • 基础操作
    • pandas
      • 基本介绍
    • argparse命令行参数
    • 列表排序
    • 队列
    • 匿名函数当做参数
    • 变量交换
    • +=
    • 文件的处理
      • open
    • 定位文件名后缀
    • import os
  • coding="utf-8"

Python 面试题目

在ipython状态下使用命令行可以使用,!+“shell命令”

  1. 查询包的属性:print(包.doc)
  2. 查询包的源代码:print(包.file)
  3. help(包)

Python面试基础

  1. 什么是PEP8
    1. pep8是一种编程规范,内容是一堆让你的程序更具有可读性的建议
  2. 什么是pickling和unpickling?
    1. pickl模块读取任何Python对象,将他们转化为字符,然后使用dump函数将其转储到一个文件中的过程叫做pickling
    2. 反之从存储的字符串文件中提取原始的Python对象的过程,叫做unpickling
  3. Python语言是一种解释性的语言,它的源代码可以直接被执行。python解释器会将源代码转化为中间语言,之后再翻译成机器码再执行。
  4. Python是如何管理内存的?
    1. Python的内存是有私有的heap空间管理的,所有的Python对象和数据结构都在一个私有heap中,程序员没有访问heap的权限,只有解释器才能进行操作。
    2. 为Python的heap空间分配内存是由Python的内存管理模块进行的,其核心API会提供一些访问该模块的方法供程序员使用。
    3. Python有自带的垃圾回收机制,它回收并释放没有被使用的内存,让他们能够被其他程序使用。
  5. 那些工具可以帮助Python做debug或者做静态分析?
    1. pychecker是一个静态分析工具,它不仅仅报告源代码的错误,并报告错误类型和复杂度。pylint是检验代码标准的另一个工具。
  6. Python解释器是Python中特定变化,可以使修改函数变得更容易。
  7. 字典推导式和列表推导:快速创建字典和列表的语法结构
  8. 什么是Python的命名空间?
    1. 在Python中,所有的名字都存在于一个空间中,他们在该空间中存在或者被操作就是命名空间。
    2. 它就像一个盒子,每一个变量名字都对应着一个对象。找变量的时候从盒子里查找。
  9. pass在Python中是一个占位符。
  10. 生成器:是实现迭代器的一种机制。依赖于yeild表达式。
  11. python 中的lambda是什么?这是一个常用于单个表达式的匿名函数。匿名函数lambda没有语句的原因是它常在代码中被执行的时候构建新的函数对象并返回。
    1. lambda 函数:首要用途是指点短小的回调函数
      lambda [arguments]:expression

    a=lambdax,y:x+y
    a(3,11)

  12. Python中的unittest是什么?
    1. 它拥有支持共享搭建、自动检测、自动测试的函数,在测试中暂停代码、将不同的测试迭代成一组,等等功能。
  13. Python中的docstring是什么?在Python中文档字符串被称为docstring,他在Python代码的中的作用是为函数模块和类做注释成文档。
  14. 将数字转化为字符串?
    1. str()函数
    2. 十进制转化为八进制或者十六进制:oct()或者hex()
  15. xrange和range的区别?
    1. xrange用于返回一个xrange对象,range返回一个数组
    2. xrange不管范围多大。都是占有固定的内存大小。
  16. Python中的模块和包是什么?
    1. 模块是搭建程序的一种方式,每一个Python代码文件都是一个模块,并可以引用其他的模块,比如对象和属性。
    2. 包是一个包含很多Python代码文件的文件夹,一个包里面可以包含模块和子文件夹。
  17. 如何用Python来进行查询和替换一个文本字符?
    1. 可以使用re模块的sub()函数或者subn()函数进行查询和替换。格式:sub(replacement, string[,count=0])(replacement 是被替换成的文本,string 是 需要被替换的文本,count 是一个可选参数,指最大被替换的数量)
    2. 82a683a8d6d07c734ba4e99baf780269.png
  18. Python里面match()和search()的区别?
    1. re模块中match(pattern,string[,flags]),检查 string 的开头是否与 pattern 匹配。re 模块中 re.search(pattern,string[,flags]),在 string 搜索 pattern 的第一个匹配值。
    2. 58bbf7dcafd39e11e199fb361ad0ba72.png
  19. Python中的随机数?
    1. f0147e7075aa062edf90daccab8557bc.png

编码风格

  • 每个级别缩进4个空格
  • 6b9a0dd265447d9482b17304a630292d.png
  • if 条件很多的时候,每个条件一行。并在条件结束额时候,加一条注释。
  • 54e4e35bf52e0ac006aac7fd07dedb0f.png
  • Python3中仅仅支持四个空格,不支持空格和tab键混用
  • 函数之间一个空格,函数内部,具有独立功能的块,一个空行
  • 类与函数之间是两行代码
  • 导入模块,一行一个模块
    • 先写标准库,第三方库,自己的库,各个组之间有一个空行
  • 逗号,分号,冒号前面避免写空格
  • 分号:一行代码有两条语句
  • 函数的左括号与函数的名字之间没有空格
  • 等号两边放空格
  • 默认的参数值赋值,等号两边没有空格
  • 函数变量名字:避免用l,o 0等混淆的字符。
  • 类的名字使用大驼峰,命名规范
  • 函数名字和变量的名字推荐使用含所下划线的名字
  • 中文PEP8中文文档

numpy

基础操作

  1. 转置
print ("x:\n", x)
print ("x.T:\n", x.T)

2.6810ffbfa82e966b120879e9ecb9f5b5.png

pandas

基本介绍

  1. pandas 是基于NumPy 的一种工具,该工具是为了解决数据分析任务而创建的。Pandas 纳入了大量库和一些标准的数据模型,提供了高效地操作大型数据集所需的工具。pandas提供了大量能使我们快速便捷地处理数据的函数和方法。你很快就会发现,它是使Python成为强大而高效的数据分析环境的重要因素之一。
  2. 1cb0bb6a5809d48b69237ab3be91e124.png
    1. 例子
    import pandas as pd
    df = pd.read_csv("titanic.csv", header=0)
    df.head()
    df.describe()
    df["age"].hist()
    

argparse命令行参数

#! /bin/python3
# -*-encoding="utf-8"-*-
# __Author__ ="ErrolYan"
# __Time__="2018.12.23"


import argparse

parser = argparse.ArgumentParser(description='Process some integers.')
parser.add_argument('integers', metavar='N', type=int, nargs='+',
                    help='an integer for the accumulator')
parser.add_argument('--sum', dest='accumulate', action='store_const',
                    const=sum, default=max,
                    help='sum the integers (default: find the max)')

args = parser.parse_args()
print(args.accumulate(args.integers))

列表排序

扩展的迭代解压语法是专门为解压不确定个数或任意个数元素的可迭代对象而设计的
8df5742368ae2b0a1c6572099ed66d54.png

列表排序:list.sort()
列表中有字典:list.sort(key=lambda,x:x[“name”] 仍然保存在列表中

队列

9a4d5f4a2ada50e5231ade55bfc2b678.png

  • 固定长度的队列是进来一个出去一个最早进来的。
  • 队列如果不设置固定大小的,则是无线长度的队列,可以在两端执行添加和删除除的操作
q = deque()
q.appendleft(4) #左侧添加4元素
q.pop(3) #右侧删除元素3
q.popleft(4) #左侧删除元素4

匿名函数当做参数

def test(a,b,func):
    return = func(a,b)
    return result
    
test(11,22 lambda x,y:x+Y)

变量交换

方法1:
a = a+b
b = a-b #已经交换a的值给b
a = a-b # 交换b的值给a
方法2:
a,b = b,a

+=

num +=a 如果num是可变的数据类型则直接的修改num,如果不是则新建一个变量指向那个数据。

文件的处理

open

  • 默认的打开方式是读取

    • 从第几个字节开始读,f.seek(2,0)#从第二个字节开始读取
    • f.tell() #获取当前的光标的位置,默认是字节数
  • open(“路径名字”,“r”)#文件必须存在

  • w,可以不存在,不存在就追加

  • a 追加文本

  • rb 以二进制文件格式打开(二进制文件是可以直接从硬盘读取直接应用,不用转换)图片 pdf 音频和视频都需要二进制文件读取

  • f.read()#一次性读取文件的所有内容 f.read(20) #一次读取20个字

  • f.readlines() #一次读取多行文件,将文件放在列表中

  • f.write(“内容”)

定位文件名后缀

position = filename.rfind(".") #数字位置
原文件名 = filename[0:postion]
原文件的后缀 = filename[postion+1:]

import os

* os.rename("old_name","new_name") #重新命名
* os.mkdir("dir_name") #创建文件夹
* os.rmdir("dir_name") #删除文件夹
* os.getcwd() #获取当前工作的路径
* os.chdir("../") #改变路径
* os.listdir("路径") #

## 批量重新命名
* os.listdir("路径") #
* os.rename("old_name","new_name") #重新命名

## 面向对象
* 类中的self是一个指针,指向对象。
* def __init__(self):  #传递变量
* def __str__(self):   # 解释
* * return 
* 私有方法:def __test1(self):一般是定义在类方法的内部,内部调用。
* def __del__(self):
    * print("删除前的挣扎”)#系统的对象没有人调用(引用基数)的时候自动删除
* 查看引用次数:import sys
*  sys.getrefcount()
## 装饰器
装饰器的输入参数是函数名字。其实就是对函数进行包装。
1.1xml文件的书写

#coding=utf-8
#定义函数:完成包裹数据
def makeBold(fn):
def wrapped():
print("----1—")
return “\n” + fn() + “\n”
return wrapped

#定义函数:完成包裹数据
def makeItalic(fn):
def wrapped():
print("----2—")
return “\n” + fn() + “\n”
return wrapped

@makeBold
@makeItalic
def test3():
print("----3—")
return “hello world-3\n”

ret = test3()
print(ret)

1.2.执行结果

----1—
----2—
----3—


hello world-3

2.装饰器在定义完之后就直接装饰了。@名字 等价 func = 函数(func)

#coding=utf-8
def w1(func):
print("—正在装饰1----")
def inner():
print("—正在验证权限1----")
func()
return inner

def w2(func):
print("—正在装饰2----")
def inner():
print("—正在验证权限2----")
func()
return inner

#只要python解释器执行到了这个代码,那么就会自动的进行装饰,而不是等到调用的时候才装饰的
@w1
@w2
def f1():
print("—f1—")

#在调用f1之前,已经进行装饰了
f1()

2.2 执行结果:装饰是从里往外装饰,执行是从外向里执行。

—正在装饰2----
—正在装饰1----
—正在验证权限1----
—正在验证权限2----
—f1—

3.对含有参数的函数进行装饰的时候,需要对装饰函数传入参数。
![f898264566a9eb14f8d1ecd16fc2f486.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1401)
4.对不定长参数的函数进行装饰

def func(functionName):
print("—func—1---")
def func_in(*args, kwargs):#采用不定长参数的方式满足所有函数需要参数以及不需要参数的情况
print("—func_in—1---")
functionName(args, **kwargs)#这个地方,需要写以及
,如果不写的话,那么args是元祖,而kwargs是字典
print("—func_in—2---")

print("---func---2---")
return func_in

@func
def test(a, b, c):
print("----test-a=%d,b=%d,c=%d—"%(a,b,c))

@func
def test2(a, b, c, d):
print("----test-a=%d,b=%d,c=%d,d=%d—"%(a,b,c,d))

test(11,22,33)

test2(44,55,66,77)

5.带有参数的装饰器,对函数进行装饰

def func_arg(arg):
def func(functionName):
def func_in():
print("—记录日志-arg=%s–"%arg)
if arg==“heihei”:
functionName()
functionName()
else:
functionName()
return func_in
return func

#1. 先执行func_arg(“heihei”)函数,这个函数return 的结果是func这个函数的引用
#2. @func
#3. 使用@func对test进行装饰
@func_arg(“heihei”)
def test():
print("–test–")

#带有参数的装饰器,能够起到在运行时,有不同的功能
@func_arg(“haha”)
def test2():
print("–test2–")

test()
test2()

## 作用域

* 什么是命名空间
* * 命名空间就是生效的范围,from test import *#把所有的函数都导入到当前的命名空间中
* * globals() #查看当前的全局变量
* * locals() #查看当前的局部变量
* 作用域:局部变量<闭包<全局变量
* LEGB:![82d9aabf2b2de7075a81c90f2a9e9d2d.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1402)
## Python是动态语言
* 静态语言:就是执行前必须先编译,再执行
* 动态语言:在运行的过程中可以修改代码
* * 实例添加属性:laowang.addr="山东"
* * 添加类属性:Person.name=100
* * 添加方法:![6a7fa61a78ea691b1b628f0fcfe9c9ec.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1403)
## 类的对象的属性
* ![4cb49b2bbe3689562db1764f8c2d1dce.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1404)
## 生成器

* 什么是生成器?
* * 生成你想要的列表和值,仅仅是得到需要计算值的公式。
* 第一种生成器:b =(x*2 for x in range(10))    bb=next(b)
* 第二种方式:![cf372ac26303854c9bc9e6a5e085d549.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1405)
* 含有yield 的函数,调用的时候需要有一个变量存取对象。
* next(a)
* a.__next__()
* ![192ee9a8bb9d8712f8400f714e2e85ee.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1406)
* t.sent("haha") 等价于a.next()
## 可迭代
* ![baa65f4fec8de4b1c79c7fbbe8e1dce8.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1407)

from colleactions import Iterable
isinstance(“abc”,Iterable)

## 迭代器(生成器一定是迭代器)

from colleactions import Iterator
isinstance(“abc”,Iterator)

## 日志调试
## 多任务
* 单核CPU
* * 2us循环执行各个程序:时间片轮转
* * 优先级调度:
* 多核CPU
* * 并发:任务数大于核数,就是并发,看上去是一起执行
* * 并行:多任务同时进行
## 多进程
* 进程和程序:程序是未运行的,进程是有生命的

import os
import time
ret = os.fork()#创建新的子进程。
if ret==0:
while True:
print(“1”)
time.sleep(1)
else:
while True:
print(“2”)
time.sleep(1)


## 获取 pid

* os.getpid() #子进程
* os.getppid() # 获取父进程
![2b93f08c00bf3db519bc4babcdd7ae84.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1410)
* 进程与进程之间是相互独立的,并且全局变量是独立的.
## 进程之间的通讯
* QQ1与 QQ2 通讯就是进程之间的通讯
* 遇到多进程就画线来理清楚
写个代码炸弹:

import os

os.fork()
os.fork()
while True:
os.fork()
print(“你完成不了!!,必须死机”)
print(“等待测试结果”)

## 跨平台的进程
![475af38a9750ef80f263f3a040b5b94e.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1411)

#!/usr/bin python

coding=“utf-8”

#author=“ErrolYan”

from multiprocessing import Process
import time

def test():
while True:
print(“test”)
time.sleep(1)

p = Process(target=test)
p.start()
p.join()#等待p 子进程结束的时候才运行主程序.
while True:
print(“main”)
time.sleep(1.5)

** 主进程是在子进程都运行完,主进程才可以运行完.

## time 模块
* from time
* time.ctime() #显示系统的时间
* time.time() #显示格林时间,距离现在的时间秒数
* time.time()可以用于统计程序运行的时间.
## 进程池
![f5d03b08fdee06ac04502d623fdf0ff3.png](evernotecid://1CCF25FA-AE21-4023-9DE3-19E31D49106E/appyinxiangcom/11012738/ENResource/p1412)
#主进程一般都是用来等待,真正的任务就是子进程来完成的.
阻塞式添加任务:就是一个执行完了添加另外一个任务.
## 进程之间的通信:Queue
1.队列:先进先出
2.栈:先进后出
3.队列可以添加任何的东西,对象/类/字符/字典/列表

q= Queue() #无限制的放进去
pw = Process(target=write,args(q,))
pr = Process(target=read,args(q,))

#启动子进程
pw.start()
pw.join()

1.进程之间是相互独立的,Queue
2.进程池:q = Manager().Queue(),其余和进程间的通信是完全一样的
3.

# 正则表达式
正则表达式:Match Tracer;RegexMagic 测试工具
## python 版本 re
. 默认是匹配出换行符意外的任何字符.
^ 匹配字符的开头
$ 匹配字符串的结尾或字符串末尾的换行符之前.foo 匹配'foo'和'foobar',而正则表达式foo$只匹配'foo'。
*使得到的RE匹配前面RE的0或更多次重复,尽可能多的重复。
+使得到的RE匹配前一个RE的1次或更多次重复。 ab+将匹配'a',后跟任何非零数字的'b'; 它不会只匹配'a'。
ab?将匹配'a'或'ab'。
## 多进程

import os
import time

ret = os.fork()
if ret ==0:
while True:
print("----1----")
time.sleep(1)
else:
while True:
print("—2---")
time.sleep(1)

import
ret = os.fork()
print(“haha”)
if ret >0:
print("—父进程----”)
else:
print(“----子进程----”)












你可能感兴趣的:(python小工具编写)