Python刷题-5

1、当一个嵌套函数在其外部区域引用了一个值时,该嵌套函数就是一个闭包,以下代码输出值为:16
def adder(x):            
    def wrapper(y):           # 第二步
        return (x + y)        # 第五步
    return (wrapper)          # 第三步

# adder5是对wrapper的引用   此时x等于5

adder5 = adder(5)   #返回了 wrapper ,且x=5;  第一步 
print(adder5(adder5(6)))       # 第四步


闭包:如果一个函数内部又定义了一个函数,就把外部的函数称为外函数,内部的函数称为内函数。如果内函数引用了外函数的变量,而外函数返回内函数(引用),就把这种形式称之为 闭包。并且当外函数结束时会将变量绑定给内函数。

adder(5) = wrapper(x=5, y)
adder5 = wrapper(x=5, y)
adder5(6) = wrapper(x=5, 6) = 5 + 6 = 11
adder5(adder5(6)) = adder(11) = wrapper (x =5, 11) = 5 + 11 = 16

# 外部函数确定了x的值为5,内部函数的值为6,所以第一次计算结果为11,第二次计算,还是在x为5的前提下,需要在11的基础上再加5
那什么是闭包呢,一言以蔽之:一个持有外部环境变量的函数就是闭包。

因为wrapper是闭包 所以adder5返回的是wrapper函数 接下来adder5(6) 返回的是11=5+6 同理 再调用一次就是16 = 11+5
2、如下程序会打印多少个数:
# python2:9个
# python3:10个

k = 1000
sum = 0
while k > 1:
    sum += 1
    print(k)
    k = k/2
print(sum)

python2 整数除法/时,会取整的,所以应该是9个。
python3 除法/,结果是浮点的,所以是10个
# 1000
# 500.0
# 250.0
# 125.0
# 62.5
# 31.25
# 15.625
# 7.8125
# 3.90625
# 1.953125

# 10
# 代码运行应该是10个,python是不会自动取整的
3、What gets printed?   6  
kvps = { '1' : 1, '2' : 2 }
theCopy = kvps.copy()
kvps['1'] = 5
sum = kvps['1'] + theCopy['1']
print sum

# object.copy()和copy.copy(object)一样是浅拷贝,深拷贝只有copy.deepcopy(object)

# 在 Python2 和 Python3 中,copy() 方法的意义相同,均为返回一个浅复制的 dict 对象,而浅复制是指只拷贝父对象,不会拷贝对象的内部的子对象,即两个 dict 父对象 kvps 与 theCopy 相互独立,但对它们内部子对象的引用却是共享的,所以 kvps['1'] 的改变不影响 theCopy['1'] 的值(因为改变的是父对象的值)。

顺便一提,深复制是指完全拷贝父对象与子对象,即都相互独立。

注意,这里的子对象不是子类的对象,而是在父对象中的二级对象。

4、What gets printed?   4  

counter = 1
def doLotsOfStuff():
    global counter
    for i in (1, 2, 3):
        counter += 1
doLotsOfStuff()
print(counter)


# 当内部作用域想修改外部变量时,需要使用global声明。
# 考察 global 的意义,即在局部作用域 doLotsOfStuff() 函数中,声明对全局作用域中的 counter 变量的引用。
在变量前加global代表修改的是全局变量, 原counter=1,三次循环+1故=4, 函数执行完,全局变量被修改=4
5、有如下函数定义,执行结果正确的是?   foo(3)=18;foo(2)=12

def dec(f):
    n = 3
    def wrapper(*args,**kw):
        return f(*args,**kw) * n
    return wrapper

@dec                # 先执行dec,将 @dec 下面的 函数 作为dec()的参数
def foo(n):
    return n * 2
foo(2)

解析:
装饰器(Decorator)本身是一个函数,目的是在不改变待装饰函数代码的情况下,增加额外的功能,装饰器的返回值是已装饰的函数对象。

以foo(2)语句为例,上述代码等价于:
def dec(f):
    n = 3
    def wrapper(*args,**kw):
        return f(*args,**kw) * n
    return wrapper

def foo(n):
    return n * 2

foo=dec(foo)
foo(2)


由此可见,@dec的作用是把原foo函数(待装饰函数)赋值给dec函数(装饰器),然后将返回值wrapper函数(已装饰函数)重新赋值给foo函数。因此,foo(2)语句实际执行情况是:
def wrapper (2):
	return foo(2) * 3
注:以上代码是为了方便理解,直接将实参n=2代入函数定义中,语法上并无实际意义。
显然,用数学符号表示的话,函数执行结果为foo(2)= wrapper(2)= foo(2)*3= 2*2*3=12,其中前面的foo函数是已装饰函数,后面的foo函数是原来的待装饰函数。By the way,函数参数中的*args代表可变参数,**kw代表关键字参数。

@dec 装饰器,先执行dec(), 并将 @dec 下面的 函数 作为dec()的参数。 (装饰器的作用:为已经存在的对象添加额外的功能)
foo(n) = n * 2 * 3

foo(2) == (2*2)*3 == 12
foo(3) == (3*2)*3 == 18
6、下列Python语句正确的是:D

A、min = x  if  x < y   = y   
B、max = x > y ? x : y
C、if (x > y)        print x
D、while True : pass

A、三元运算符的使用。基本语法为:a if condition else b
上述语句当 condition 为真时等于 a,为假时等于 b。因此 A 选项改为下列语句则正确:min = x if x<y else y

B、还是三元运算符的使用,只不过 B 选项的用法在 C、Java 等语言中成立,在 Python 中没有此用法,正确用法参见选项 A。

C、if 语句缺少冒号,并且正确用法如下:if (x>y): print x
D、while 语句与 pass 语句的使用。pass语句为空语句,意义只是为了保持程序结构的完整性。该选项写法正确,故选 D。
7、下列表达式的值为True的是:C

A、5+4j > 2-3j
B、3>2>2
C、(3,2)< ('a','b')
D、’abc’ > ‘xyz’

选项 A:Python2 与 Python3 均不支持复数比较大小;
ASCII码中小写字母>大写字母>数字
字母:
A-Z:65-90
a-z:97-122


1、复数是不可以比较大小的。
2、元组是可以比较大小的。tuple 的比较是从两者的第一个元素的 ASCII 码开始,直至两个元素不相等为止,若前面元素都相等,则元素个数多的 tuple 较大。
3、字符串是可以比较大小的。字符串的比较是从两者的第一个字符的ASCII码开始,直至两个元素不相等为止,若前面字符都相等,则字符个数多的字符串较大。
字母与数字的ASCII 码大小范围是 "a-z" > "A-Z" > "0-9"
8、有一段python的编码程序如下:urllib.quote(line.decode("gbk").encode("utf-16")),请问经过该编码的字符串的解码顺序是(D)
A、gbk	     utf16	    url解码
B、gbk        url解码     utf16
C、url解码     gbk	       utf16
D、url解码	    utf16	   gbk

解析:
字符串编译的过程:gbk==>unicode==>utf16==>url解码
字符串解码顺序为:url解码==>utf16==>unicode==>gbk
9、Python中函数是对象,描述正确的是? (ABCD)
A、函数可以赋值给一个变量
B、函数可以作为元素添加到集合对象中
C、函数可以作为参数值传递给其它函数
D、函数可以当做函数的返回值

解析:在 Python 中万物皆为对象,函数也不例外,函数作为对象可以赋值给一个变量、可以作为元素添加到集合对象中、可作为参数值传递给其它函数,还可以当做函数的返回值,这些特性就是第一类对象所特有的。
10、Python中单下划线_foo与双下划线__foo与__foo__的成员,下列说法正确的是?(ABC)

A、_foo 不能直接用于’from module import *’
B、__foo解析器用_classname__foo来代替这个名字,以区别和其他类相同的命名
C、__foo__代表python里特殊方法专用的标识
D、__foo 可以直接用于’from module import *’

_xxx 不能用’from module import *’导入  (相当于protected) 
__xxx__ 系统定义名字   (系统内置的,比如关键字)
__xxx 类中的私有变量名  (privated),所以更加不能使用from module import进行导入了

链接:https://www.nowcoder.com/questionTerminal/1c4b55a530ee499c986efe82c173b645
来源:牛客网

python中主要存在四种命名方式:
1、object #公用方法
2、_object #半保护
                 #被看作是“protect”,意思是只有类对象和子类对象自己能访问到这些变量,
                  在模块或类外不可以使用,不能用’from module import *’导入。
                 #__object 是为了避免与子类的方法名称冲突, 对于该标识符描述的方法,父
                  类的方法不能轻易地被子类的方法覆盖,他们的名字实际上是
                  _classname__methodname。
3、_ _ object    #全私有,全保护
                       #私有成员“private”,意思是只有类对象自己能访问,连子类对象也不能访
                          问到这个数据,不能用’from module import *’导入。
4、_ _ object_ _     #内建方法,用户不要这样定义
posted @ 2020-09-30 09:06  喵哥解说  阅读(873)  评论(0编辑  收藏  举报