这些 Python 高效率技巧,一般人都不会
off999 2024-10-15 12:08 38 浏览 0 评论
作者:Martin Heinz
翻译:EarlGrey
原文:https://martinheinz.dev/blog/1
你估计已经看了不少关于 Python 技巧的文章,里面可能会提到变量拆包(unpacking)、局部函数等,但是 Python 还有很多不为人知的高效用法,等待着被人发现。本文将介绍作者纵观全网之后,都属于很少没提及的技巧。
清理字符串输入
清理用户输入的问题,几乎适用于我们可能编写的每个程序。通常将字符转换为小写或大写就足够了,这时只需要使用正则即可,但是对于复杂的情况,有一种更好的方法:
user_input = "This\nstring has\tsome whitespaces...\r\n"
character_map = {
ord('\n') : ' ',
ord('\t') : ' ',
ord('\r') : None
}
user_input.translate(character_map) # This string has some whitespaces... "
在上述示例中,可以看到空格符“ \ n”和“ \ t”已被单个空格替换,而“ \ r”已被完全删除。这是一个简单的示例,但是我们可以更进一步,使用 unicodedata包及其combining函数生成范围更广的映射表,从字符串中删除所有重音符号。
迭代器切片
如果您尝试获取迭代器的切片,系统会报 TypeError,提示生成器对象不可下标,但是解决方案很简单:
import itertools
s = itertools.islice(range(50),10,20) # <itertools.islice object at 0x7f70fab88138>
for val in s:
...
使用 itertools.islice,我们可以创建一个islice对象,该对象是产生所需元素的迭代器。不过,请务必注意,这会消耗所有生成器项,直到切片开始为止,而且还会消耗我们的“ islice”对象中的所有项。
Using itertools.islicewe can create aisliceobject which is an iterator that produces desired items. It's important to note though, that this consumes all generator items up until the start of slice and also all the items in ourisliceobject.
跳过可迭代对象的开始
有时候需要处理的文件里,明确存在一些不需要的数据行,但是我们不确定数量,比如说代码中的注释。这时, itertools再次为我们提供了简洁的方案:
string_from_file = """
// Author: ...
// License: ...
//
// Date: ...
Actual content...
"""
import itertools
for line in itertools.dropwhile(lambda line: line.startswith("//"), string_from_file.split("\n")):
print(line)
这段代码仅在初始注释部分之后,才会产生数据行。如果我们只想在迭代器的开头丢弃数据,而又不知道有具体数量时,这个方法很有用。
仅带关键字参数(kwargs)的函数
有时候,使用仅支持关键字参数的函数可以让代码更加清晰易懂:
def test(*, a, b):
pass
test("value for a", "value for b") # TypeError: test takes 0 positional arguments...
test(a="value", b="value 2") # Works...
只需要在关键字参数前面再加一个 *参数,就可以轻松实现了。当然,如果还希望再加上位置参数,可以在*参数前面再增加。
创建支持 with语句的对象
我们都知道如何打开文件或使用 with语句获取锁,但是怎样自己可以实现类似的功能呢?一般来说,我们可以使用__enter__和__exit__方法来实现上下文管理器协议:
classConnection:
def __init__(self):
...
def __enter__(self):
# Initialize connection...
def __exit__(self, type, value, traceback):
# Close connection...
withConnection as c:
# __enter__ executes
...
# conn.__exit__ executes
上面是最常见的实现方式,但是还有一种更简单的方法:
from contextlib import contextmanager
@contextmanager
def tag(name):
print(f"<{name}>")
yield
print(f"")
with tag("h1"):
print("This is Title.")
上面的代码段使用 contextmanager管理器装饰器实现了内容管理协议。进入“ with”块时,执行“ tag”函数的第一部分(在“ yield”之前),然后执行yield,最后执行其余部分。
用 __slots__节省内存
如果程序需要创建大量的类实例,我们会发现程序占用了大量内存。这是因为 Python 使用字典来表示类实例的属性,这样的话创建速度很快,但是很耗内存。如果内存是你需要考虑的一个问题,那么可以考虑使用 __slots__:
classPerson:
__slots__ = ["first_name", "last_name", "phone"]
def __init__(self, first_name, last_name, phone):
self.first_name = first_name
self.last_name = last_name
self.phone = phone
当我们定义 __slots__属性时,Python会使用固定大小的数组(占用内存少)来存储属性,而不是字典,这大大减少了每个实例所需的内存。不过使用__slots__还有一些缺点:无法声明任何新属性,我们只能使用__slots__中的那些属性。同样,带有__slots__的类不能使用多重继承。
限制CPU和内存使用量
如果不是想优化程序内存或CPU使用率,而是想直接将其限制为某个数值,那么Python也有一个可以满足要求的库:
import signal
import resource
import os
# To Limit CPU time
def time_exceeded(signo, frame):
print("CPU exceeded...")
raiseSystemExit(1)
def set_max_runtime(seconds):
# Install the signal handler and set a resource limit
soft, hard = resource.getrlimit(resource.RLIMIT_CPU)
resource.setrlimit(resource.RLIMIT_CPU, (seconds, hard))
signal.signal(signal.SIGXCPU, time_exceeded)
# To limit memory usage
def set_max_memory(size):
soft, hard = resource.getrlimit(resource.RLIMIT_AS)
resource.setrlimit(resource.RLIMIT_AS, (size, hard))
在这里,我们可以设置了最大cpu运行时间以及最大内存使用限制的两个选项。对于cpu限制,我们首先获得该特定资源( RLIMIT_CPU)的软限制和硬限制,然后使用参数指定的秒数和先前获取的硬限制来设置。
最后,我们注册了一个在超过CPU时间后,让系统退出的信号。至于内存,我们再次获取软限制和硬限制,并使用带有大小参数的 setrlimit和硬限制完成配置
控制导入的内容
某些语言提供了导出成员(变量,方法,接口)的显式机制,例如Golang,它仅导出以大写字母开头的成员。但是在Python中,所有对象都会导出,除非我们使用 __all__:
def foo:
pass
def bar:
pass
__all__ = ["bar"]
上面的代码段中,只会导出 bar函数。另外,如果__all__的值为空,那么不会导出任何函数,而且在导入该模块时系统会报AttributeError。
实现比较运算符
如果我们要逐一为某个类实现所有的比较运算符,你肯定会觉得很麻烦,因为要实现的方法还不少,有 __lt__,__le__,__gt__,和__ge__。
其实,Python 提供了一种便捷的实现方式,就是通过 functools.total_ordering装饰器。
from functools import total_ordering
@total_ordering
classNumber:
def __init__(self, value):
self.value = value
def __lt__(self, other):
returnself.value < other.value
def __eq__(self, other):
returnself.value == other.value
print(Number(20) >Number(3))
print(Number(1) <Number(5))
print(Number(15) >=Number(15))
print(Number(10) <=Number(2))
这是怎么实现的呢? total_ordering可以用来简化实现类排序的过程。我们只需要定义__lt__和__eq__(这是映射剩余操作的最低要求),然后就交给装饰器去完成剩余的工作了。
结语
在日常Python编程时,上述特性并非都是必不可少的和有用的,但是其中某些功能可能会不时派上用场,并能简化冗长且令人讨厌的任务。
还要指出的是,所有这些功能都是Python标准库的一部分,而在我看来,其中一些功能似乎不像是应该在标准库中的功能。
因此,每当你决定要用Python实现某些功能时,都请先在标准库中找一找,如果找不到合适的库,那么可能是因为查找的姿势不对。而且即使标准库里没有,有很大的概率已经存在一个第三方库了!
签到送书计划
自律改变自我!第①期打卡送书活动启动!
相关推荐
- 笔记本电脑开机密码怎么关闭
-
1、用户账户密码取消 取消用户账户密码的方法比较简单,在“控制面板”中的“用户账户”中,选择你要修改的账户,然后点“删除我的密码”的选项,选择“删除密码”即可,也可以在选择更改密码时,把新密码留空,...
- 鼠标usb设备无法识别(鼠标usb设备无法识别win10)
-
1.前置USB线接错。当主板上的USB线和机箱上的前置USB接口对应相接时把正负接反就会发生这类故障,这也是相当危险的,因为正负接反很可能会使得USB设备烧毁。所以尽量采用机箱后置的USB接口,也少...
-
- 腾讯游戏实名认证中心官网(腾讯游戏实名制平台)
-
腾讯游戏实名认证非常的简单,首先,打开腾讯游戏实名注册网址:jkyx.qq.com打开jkyx.qq.com,登陆你的QQ账号,如果你的QQ账号已经实名注册了,该网站就能看到已注册的信息的。如果还未实名注册的玩家,就可以在该网站按照要求填...
-
2025-12-24 19:03 off999
- 电脑城照片(电脑照的相片在哪里找)
-
开平的电脑城在市府文化广场旁边那条桥的桥头(光明路),美媛电脑城,不过好像很破烂,此外曙光路很多电脑店。有三家电子/电脑城,其中最大两家在107国道沙井上南加油站路段两旁,那里有很多电子零件和电脑...
- kali linux安装教程(kali linux最新版安装教程)
-
KaliLinux官方正确安装方法为先从官网下载最新版本的ISO镜像文件,然后使用软件如Rufus将ISO文件写入U盘或DVD,接着在计算机启动时选择U盘或DVD作为启动设备,进入KaliLinu...
- asus电脑开不了机怎么办(华硕电脑开不机怎么办)
-
1、检查电源和电源适配器如果华硕笔记本无法开机,首先要排查电源和电源适配器是否正常工作。可以检查电源适配器是否插紧,是否有松动或断裂。另外,可以更换电源适配器或更换电池,看是否可以开机。2、检查硬件连...
- bios硬盘启动项是哪个(电脑bios硬盘启动)
-
1、开机按F2(具体按键看开机屏幕提示)进入BIOS系统,打开Boot选项卡;2、在Boot页面下找到IDE1,一般这个表示的就是电脑硬盘,按键盘上的F6将该启动项向上移至第一位,也就是将硬盘设为第一...
- 虚拟机ubuntu安装教程(ubuntu 虚拟机安装)
-
在虚拟机Ubuntu下安装MATLAB的步骤如下:1.下载MATLAB安装包:访问MATLAB官网,选择适合你的Ubuntu版本的MATLAB安装包,并下载到本地计算机。2.安装虚拟机软件:在Ub...
- bootmgrismissing开机不了怎么办
-
你是不是没打全?大概意思就是启动的东西缺失!重装系统或者是补充装修复系统引导bootmgr丢失无法开机的解决方法:1、重新启动计算机,如果遇到“BOOTMGRismissing”错误,可以尝试的第...
- 手机上怎么改路由器密码(手机上怎么改路由器密码wifi密码)
-
输入地址打开手机浏览器后在地址栏输入路由器地址,打开路由器登录界面。2/4点击常用设置输入路由器管理员密码后进入路由器主界面,点击上方的常用设置。3/4找到密码在窗口中分别找到2.4G和5Gwifi...
- windowsserver2016(windowsserver2016激活密钥)
-
WindowsServer2016代表着微软发布的一款服务器操作系统。它是2016年推出的,为企业提供了强大的功能和稳定性,支持大规模的数据中心和云计算环境。WindowsServer2016...
- 联想手机官网查询真伪入口(联想手机正品查询)
-
官方查询页面http://support1.lenovo.com.cn/lenovo/wsi/我认为联想本本一旦出厂就自然就可以查询号码了。因为我们单位订购的一批联想本本,直接从上海生产基地把本本...
- 中国电信官方测网速(网络测速 中国电信)
-
你好,你可以下载一个第三方软件进行测速,如果你手机自带测速软件直接可以测速的,也可以下载电信测速软件。1.进入中国电信官方测速网站。 说明:中国电信宽带测速是根据网络行业网速标准制定的专业测速工具,...
- sony官网中国官方网站(索尼官方app下载安装)
-
网址是https://www.sony.com.cn/索尼的中文官网不仅可以有售后服务等信息,也会有新品发布消息。对于索尼的粉丝来说,官网是必不可少的。您可以按照以下步骤在索尼官网上查找产品的序列号:...
- 路由器登陆账号密码(路由器登陆账号密码忘了)
-
1、一般路由器的账号为admin,密码也是admin;还有路由器产品出厂时默认登录密码是guest,有点路由器产品的出厂时初始登录密码为【空】,也就是没有登录密码,直接就可以进入设置界面的; 2、您...
欢迎 你 发表评论:
- 一周热门
-
-
抖音上好看的小姐姐,Python给你都下载了
-
全网最简单易懂!495页Python漫画教程,高清PDF版免费下载
-
Python 3.14 的 UUIDv6/v7/v8 上新,别再用 uuid4 () 啦!
-
飞牛NAS部署TVGate Docker项目,实现内网一键转发、代理、jx
-
python入门到脱坑 输入与输出—str()函数
-
宝塔面板如何添加免费waf防火墙?(宝塔面板开启https)
-
Python三目运算基础与进阶_python三目运算符判断三个变量
-
(新版)Python 分布式爬虫与 JS 逆向进阶实战吾爱分享
-
失业程序员复习python笔记——条件与循环
-
系统u盘安装(win11系统u盘安装)
-
- 最近发表
- 标签列表
-
- python计时 (73)
- python安装路径 (56)
- python类型转换 (93)
- python进度条 (67)
- python吧 (67)
- python的for循环 (65)
- python格式化字符串 (61)
- python静态方法 (57)
- python列表切片 (59)
- python面向对象编程 (60)
- python 代码加密 (65)
- python串口编程 (77)
- python封装 (57)
- python写入txt (66)
- python读取文件夹下所有文件 (59)
- python操作mysql数据库 (66)
- python获取列表的长度 (64)
- python接口 (63)
- python调用函数 (57)
- python多态 (60)
- python匿名函数 (59)
- python打印九九乘法表 (65)
- python赋值 (62)
- python异常 (69)
- python元祖 (57)
