python面试题总结_2019(有解释答案) --3

                                             

目录

50.Python 交换两个变量的值

51.在读文件操作的时候会使用 read、readline 或者 readlines,简述它们各自的作用

52.json序列化时,可以处理的数据类型有哪些?如何定制支持 datetime 类型?

53.json 序列化时,默认遇到中文会转换成 unicode,如果想要保留中文怎么办?

54.有两个磁盘文件 A 和 B,各存放一行字母,要求把这两个文件中的信息合并,输出到一个新文件 C 中

55.如果当前的日期为 20190530,要求写一个函数输出 N 天后的日期,(比如 N 为 2,则输出 20190601)。

56.写一个函数,接收整数参数 n,返回一个函数,函数的功能是把函数的参数和 n 相乘并把结果返回。

57.下面代码会存在什么问题,如何改进?

58.一行代码输出 1-100 之间的所有偶数

59.with 语句的作用,写一段代码?

60.python字典和 json字符串相互转化方法

61.请写一个 Python 逻辑,计算一个文件中的大写字母数量

62.函数装饰器有什么作用?请列举说明?

63.Python 垃圾回收机制?

64.魔法函数 __call__怎么使用?

65.如何判断一个对象是函数还是方法?

66.@classmethod 和@staticmethod 用法和区别

67.Python 中的接口如何实现?

68.Python 中的反射了解么?

69.metaclass 作用?以及应用场景?

70.hasattr() getattr() setattr()的用法

71.请列举你知道的 Python 的魔法方法及用途。

72.如何知道一个 Python 对象的类型?

73.Python 的传参是传值还是传址?

74.Python中的元类(metaclass)使用举例

75.简述any()和all()方法

76.filter方法求出列表所有奇数并构造新列表,a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

77.什么是猴子补丁?

78.在 Python 中是如何管理内存的?

79.当退出 Python 时是否释放所有内存分配?

80.使用正则表达式匹配出

81.a="张明98分",用re.sub,将98替换为100

82.正则表达式匹配中(.*)和(.*?)匹配区别?

83.写一段匹配邮箱的正则表达式


                                                                                 ****************操作类****************

50.Python 交换两个变量的值

(1) temp做中间量

temp = a

a = b

a = temp

(2) a,b = b,a

51.在读文件操作的时候会使用 read、readline 或者 readlines,简述它们各自的作用

read 读取整个文件

readline 读取下一行,for循环中经常用

readlines 读取整个文件到一个迭代器,for中也可以

52.json序列化时,可以处理的数据类型有哪些?如何定制支持 datetime 类型?

(1)

可以处理的数据类型是 string、int、list、tuple、dict、bool、null

json.dumps()   将Python中的对象转换为JSON中的字符串对象
json.loads()   将JSON中的字符串对象转换为Python中的对象

(2)自定义时间序列化转换器

import json
from json import JSONEncoder
from datetime import datetime
class ComplexEncoder(JSONEncoder):
    def default(self, obj):
        if isinstance(obj, datetime):
            return obj.strftime('%Y-%m-%d %H:%M:%S')
        else:
            return super(ComplexEncoder,self).default(obj)
d = { 'name':'alex','data':datetime.now()}
print(json.dumps(d,cls=ComplexEncoder))
# {"name": "alex", "data": "2018-05-18 19:52:05"}

53.json 序列化时,默认遇到中文会转换成 unicode,如果想要保留中文怎么办?

import json
a=json.dumps({"ddf":"你好"},ensure_ascii=False)
print(a) #{"ddf": "你好"}

54.有两个磁盘文件 A 和 B,各存放一行字母,要求把这两个文件中的信息合并,输出到一个新文件 C 中

(1)

import os

import shutil

outfile = open('C','w')

infile1 = open('A','r')

infile2 = open('B','r')

shutil.copyfileobj(infile1,outfile)

outfile.write('\n')

shutil.copyfileobj(infile2,outfile)

infile1.close()

infile2.close()

outfile.close()

(2)

import os

import shutil

with open(‘C’,’w’) as c, open(‘A’,’r’) as a, open(‘B’,’r’) as b:

       shutil.copyfileobj(a,c)

shutil.copyfileobj(b,c)

55.如果当前的日期为 20190530,要求写一个函数输出 N 天后的日期,(比如 N 为 2,则输出 20190601)。

import datetime

def getday(n):

    y = 2019

    m = 5

    d = 30

    #datetime.datetime指定日期

    the_date = datetime.datetime(y,m,d)

    #datetime.timedelta,时间差

    result_date = the_date + datetime.timedelta(days = n)

    target_date = result_date.strftime('%Y%m%d')

    return target_date

print(getday(2))

56.写一个函数,接收整数参数 n,返回一个函数,函数的功能是把函数的参数和 n 相乘并把结果返回。

(1)这种形式的函数称为闭包

def func01(n):

    def func02(m):

        return n * m

    return func02

zw = func01(7)

print(zw(9));

57.下面代码会存在什么问题,如何改进?

def strappend(num):
    str='first'
    for i in range(num):
        str+=str(i)
    return str

该错误TypeError: 'str' object is not callable字面上意思:就是str不可以被系统调用,其实原因就是:你正在调用一个不能被调用的变量或对象,具体表现就是你调用函数、变量的方式错误.

将str(i)修改成str[i]

58.一行代码输出 1-100 之间的所有偶数

(1) print([i*2 for i in range(1,51)])

(2)print(list(x for x in range(1,101) if x%2==0))

或者print([x for x in range(1,101) if x%2==0])

关于加list或者[]这里解释一下,如果不加运行的话会出现<generator object <genexpr> at 0x0000000002945360>这里的意思是生成了一个迭代器(python generator object)对象,加list或者[]则创建了一个list对象,因此这样才可以打印出想要的数据

59.with 语句的作用,写一段代码?

with语句使用于对资源进行访问的场合。确保使用过程中不管是否发生异常,都会执行必要的“清理”操作,并释放资源。比如文件使用后自动关闭,线程中锁的自动获取和释放。

见53(2)

60.python字典和 json字符串相互转化方法

json.dumps()   将Python中的对象转换为JSON中的字符串对象
json.loads()   将JSON中的字符串对象转换为Python中的对象

上述函数对字典使用

61.请写一个 Python 逻辑,计算一个文件中的大写字母数量

(1)

import os

with open(‘file_name’) as file:

       count = 0

       file_o = file.read()

       for i in file_o:

              if i.isupper():

                     count +=1

print(count)

(2)

import re

with open('file_name') as file:

    file_o = file.read()

    len_capital = len(re.compile(r'[A-Z]').findall(file_o))

print(len_capital)

 

                                                             ****************python的进阶问题****************

62.函数装饰器有什么作用?请列举说明?

当程序使用“@函数”(比如函数 A)装饰另一个函数(比如函数 B)时,实际上完成如下两步

1.将被修饰的函数(函数 B)作为参数传给@符号引用的函数(函数 A)。

2.将函数B替换(装饰)成第 1 步的返回值。

例如:

def funA(fn):

print('A')

fn() # 执行传入的fn参数

return 'end'

 

@funA

def funB():

print('B')

print(funB) # end

上面程序的执行结果是

A

B

end

修改函数funA后会在执行print(funB)时,先返回修改的函数funA(),则会打印A,fn()执行传入的funB(),则会打印B,然后打印返回的参数end

63.Python 垃圾回收机制?

主要以引用计数为主,分代回收为辅

详细来说是一个比较麻烦的问题,链接如下:

https://blog.csdn.net/xiongchengluo1129/article/details/80462651

64.魔法函数 __call__怎么使用?

所谓的魔法方法就是增加一些特殊功能,__call__就是使不可调用对象可以被调用

函数可以被调用,但是类不可以被调用,例如

class test():

  def method(self):

    return 1

a = test()

callable(a)是flase,这种情况修改成:

class test():

  def __call__(self):

    return 1

a = test()

callable(a)是true

目前还有个疑惑的地方,可不可调用只是通过callable验证的,其实print(a.method())和print(a.__call__())都可以输出1,所以是否可调用有什么用呢?

65.如何判断一个对象是函数还是方法?

首先,从分类的角度来分析

(1)函数的分类:

内置函数:python内嵌的一些函数。

匿名函数:一行代码实现一个函数功能。

递归函数

自定义函数:根据自己的需求,来进行定义函数。

(2)方法的分类:

普通方法:直接用self调用的方法。

私有方法:__函数名,只能在类中被调用的方法。

属性方法:@property,将方法伪装成为属性,让代码看起来更合理。

特殊方法(双下划线方法):以__init__为例,是用来封装实例化对象的属性,只要是实例化对象就一定会执行__init方法,如果对象子类中没有则会寻找父类(超类),如果父类(超类)也没有,则直接继承object(python 3.x)类,执行类中的__init__方法。

类方法:通过类名的调用去操作公共模板中的属性和方法。

静态方法:不用传入类空间、对象的方法, 作用是保证代码的一致性,规范性,可以完全独立类外的一个方法,但是为了代码的一致性统一的放到某个模块(py文件)中

其次,从作用域的角度来分析

(1)函数作用域:从函数调用开始至函数执行完成,返回给调用者后,在执行过程中开辟的空间会自动释放,也就是说函数执行完成后,函数体内部通过赋值等方式修改变量的值不会保留,会随着返回给调用者后,开辟的空间会自动释放。

(2)方法作用域:通过实例化的对象进行方法的调用,调用后开辟的空间不会释放,也就是说调用方法中对变量的修改值会一直保留。

最后,调用的方式不同。

(1) 函数:通过“函数名( )”的方式进行调用。

(2) 方法:通过“对象.方法名”的方式进行调用。

class Foo(object):

    def func(self):

        pass

#实例化

obj = Foo()

# 执行方式一:调用的func是方法

obj.func() #func 方法

# 执行方式二:调用的func是函数

Foo.func(123) # 函数

检测是函数还是方法可以通过内置的isinstance来判断:

from types import MethodType,FunctionType

print(isinstance(obj.func, MethodType)) #true

print(isinstance(Foo.func, FunctionType)) #true

66.@classmethod 和@staticmethod 用法和区别

Python中3种方式定义类方法, 常规方式, @classmethod修饰方式, @staticmethod修饰方式,例如:

class A(object):

def foo(self, x):

print("executing foo(%s,%s)" % (self, x))

print('self:', self)

@classmethod

def class_foo(cls, x):

print("executing class_foo(%s,%s)" % (cls, x))

print('cls:', cls)

cls.foo(‘hello’) #这是@classmethod与@staticmethod的区别

@staticmethod

def static_foo(x):

print("executing static_foo(%s)" % x)

a = A()

普通的类方法foo()需要通过self参数隐式的传递当前类对象的实例。 @classmethod修饰的方法class_foo()需要通过cls参数传递当前类对象。@staticmethod修饰的方法定义与普通函数是一样的。

self和cls的区别不是强制的,只是PEP8中一种编程风格,slef通常用作实例方法的第一参数,cls通常用作类方法的第一参数。即通常用self来传递当前类对象的实例,cls传递当前类对象。

要使用某个类的方法,需要先实例化一个对象再调用方法。而使用@staticmethod或@classmethod,就可以不需要实例化,直接类名.方法名()来调用,如下:

foo可通过实例a调用,通过类对象调用(A.foo(1))会出错

a.foo(1)

class_foo通过类对象或者对象实例调用

static_foo通过类对象或者对象实例调用

@staticmethod和@classmethod的区别是有两点:

从它们的使用上来看,

@staticmethod不需要表示自身对象的self和自身类的cls参数,就跟使用函数一样。

@classmethod也不需要self参数,但第一个参数需要是表示自身类的cls参数。

如果在@staticmethod中要调用到这个类的一些属性方法,只能直接类名.属性名或类名.方法名。而@classmethod因为持有cls参数,可以来调用类的属性,类的方法,实例化对象等,避免硬编码。

67.Python 中的接口如何实现?

https://blog.csdn.net/weixin_41762173/article/details/82783723

68.Python 中的反射了解么?

https://www.cnblogs.com/benric/p/5069205.html

https://www.cnblogs.com/iexperience/p/9206485.html

69.metaclass 作用?以及应用场景?

http://blog.jobbole.com/21351/

70.hasattr() getattr() setattr()的用法

见76

71.请列举你知道的 Python 的魔法方法及用途。

魔法方法还是挺多的,参考下面链接:

https://blog.csdn.net/koko66/article/details/42709279

72.如何知道一个 Python 对象的类型?

print(type(object))

73.Python 的传参是传值还是传址?

Python是不允许程序员选择采用传值还是传址的。Python参数传递采用的肯定是“传对象引用”的方式。实际上,这种方式相当于传值和传址的一种综合。

如果函数收到的是一个可变对象(比如字典或者列表)的引用,就能修改对象的原始值——相当于传址。如果函数收到的是一个不可变对象(比如数字、字符或者元组)的引用(其实也是对象地址!!!),就不能直接修改原始对象——相当于传值。

所以python的传值和传址是比如根据传入参数的类型来选择的

https://blog.csdn.net/github_39261590/article/details/74002290

74.Python中的元类(metaclass)使用举例

见77

75.简述any()和all()方法

any(x)判断x对象是否为空对象,如果都为空、0、False,则返回False,如果不都为空、0、False,则返回True

all(x)如果all(x)参数x对象的所有元素不为0''False或者x为空对象,则返回True,否则返回False

76.filter方法求出列表所有奇数并构造新列表,a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

(1)

a = [1,2,3,4,5,6,7,8,9,10]

def fn(a):

       return a%2==1

newlist = filter(fn,a)

newlist = [i for i in newlist]

print(newlist)

(2)

a = [1,2,3,4,5,6,7,8,9,10]

res = [i for i in a if i%2==1]

print(res)

关于为什么在(1)中有newlist = [i for i in newlist]这一句,或者(2)中res = [i for i in a if i%2==1]

用中括号,解释见57

77.什么是猴子补丁?

monkey patch指的是在执行时动态替换,通常是在startup的时候.用过gevent就会知道,会在最开头的地方gevent.monkey.patch_all();把标准库中的thread/socket等给替换掉.这样我们在后面使用socket的时候能够跟寻常一样使用,无需改动不论什么代码,可是它变成非堵塞的了.
之前做的一个游戏server,非常多地方用的import json,后来发现ujson比自带json快了N倍,于是问题来了,难道几十个文件要一个个把import json改成import ujson as json吗?
事实上仅仅须要在进程startup的地方monkey patch即可了.是影响整个进程空间的.

同一进程空间中一个module仅仅会被执行一次

78.在 Python 中是如何管理内存的?

内存分配方式有四种:

(1)从静态存储区域分配。内存在程序编译的时候就已经分配好,存放全局变量和静态变量,这些内存在程序运行期间都存在。

(2)在栈上创建。由编译器自动分配自动释放,用于存放局部变量和参数,栈内的对象先进后出,所以先创建的对象会后析构。栈由于是编译器自动管理的,所以栈内的对象不会存在内存泄露问题,并且效率很高,但是分配的内存容量有限。

(3)从堆上分配,亦称动态内存分配。程序员自己负责在何时用free或delete释放内存。动态内存的生存期由我们决定,使用非常灵活,但问题也最多。

(4)常量区:存放常量字符串,程序结束后由系统释放

python的内存管理是由私有的heap空间管理的,所有的python对象和数据结构都在一个专有的heap(堆),程序员没有访问该heap的权限,只有解释器才能对他进行操作。而python的heap空间分配是由内存管理模块进行的,其核心API会提供一些访问该模块的方法提供程序员使用。

python自带的垃圾回收系统,它会回收并释放没有被使用的内存,让她们能够被其他程序使用(内存池。被释放后先回到内存池然后再被别的程序所运用)

79.当退出 Python 时是否释放所有内存分配?

循环引用其他对象或引用自全局命名空间的对象的模块,在python退出时并非完全释放

另外,也不会释放c库保留的内存部分

 

                                                            ****************正则表达式****************

说明下r的作用,加上r表示原生字符串,如果没有r需要表示\则需要4个\才可以,具体情况看以下示例:

>>> mm = "c:\\a\\b\\c"

>>> mm

'c:\\a\\b\\c'

>>> print(mm)

c:\a\b\c

>>> re.match("c:\\\\",mm).group()

'c:\\'

>>> ret = re.match("c:\\\\",mm).group()

>>> print(ret)

c:\

>>> ret = re.match("c:\\\\a",mm).group()

>>> print(ret)

c:\a

>>> ret = re.match(r"c:\\a",mm).group()

>>> print(ret)

c:\a

再说一个( )与[ ]的区别:

( )内是以字符串形式匹配的,例如(abs)则是匹配abs整个字符串,(abs|asb)则是匹配abs或者asb,[ ]内部是以单个字符进行匹配,[a-z]则是匹配a到z的任意一个字符

80.使用正则表达式匹配出<html><h1>www.baidu.com</html>中的地址

(1)

import re

string = "<html><h1>www.baidu.com</html>"

regular_expression = re.compile('www\..+\.com')    #www.任意字符.com

print(regular_expression.search(string).group(0))

(2) 这种方式也可以进行匹配,不同的地方是正则表达式更精确

import re

string = "<html><h1>www.baidu.com</html>"

print(re.search('(www\..+\.com)( www\..+\.html)',string).groups())

 

81.a="张明98分",用re.sub,将98替换为100

import re

a = "张明98分"

print(re.sub('98','100',a))

82.正则表达式匹配中(.*)和(.*?)匹配区别?

加?会将贪婪模式改成懒惰模式,如果没有括号的话,则表示匹配0个或1个问号前面的表达式,非贪婪模式

83.写一段匹配邮箱的正则表达式

(1)

import re

mail_string = '5dasdfAA5@soho.net'

print(re.search('[0-9a-zA-Z_]*@.+\.(com|cn|net)$',mail_string).group())

(2)

import re

mail_string = '5dasdfAA5@soho.net,123456@126.com'

print(re.findall('[0-9a-zA-Z_]+@[0-9a-zA-Z_]+\.(?:com|cn|net)',mail_string))

 

  • 2
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值