title: 记住变量类型的三种方式

date: 2017-06-11 15:25:03

tags: ['Python']

category: ['Python']

toc: true

comments: true

Python作为一门动态语言,其变量的类型可以自由变化。这个特性提高了代码的开发效率,却也增加了阅读代码和维护代码的难度。

假设有一个变量is_request_finished,从名字上来看,这个变量的值应该为True或者False,在写代码的时候,最初也确实是这样定义的。但是可能由于某些原因,在某一次赋值的时候,is_request_finished = 'True'。此时,如果代码的单元测试不够完善,那么if is_request_finished在 is_request_finished = True 和 is_request_finished = 'True'的时候都成立,问题被隐藏了。但是当is_request_finished = 'False'的时候,由于'False'作为一个非空字符串,就会使得 if is_request_finished 依然成立,从而使程序的行为发现异常。

单个变量的类型异常也许还容易发现,但是如果变量是放在字典或者列表里面,那就比较麻烦了。假设需要保存一段个人信息,于是创建了下面这样一个列表套字典的数据结构:

person_list = [{
'name': 'kingname',
'age': 23,
'sex': 'male'
'detail': {
'address': 'xxx',
'work': 'engineer',
'salary': 100000
}
},
{
'name': 'xiaoming',
'age': 65,
'sex': 'male'
'detail': {
'address': 'yyy',
'work': 'pm',
'salary': 0.5
}
}]

这种方式开发起来非常的快速而方便,但是其他人甚至是开发者自己在一段时间以后读代码,都会有一种想抽死自己的冲动。因为根本不知道这个变量里面保存的是什么东西。

针对以上问题,常见的解决办法有三种。

Type Hints 与 Variable Annotations

在PEP 484中,引入了Type Hints,在PEP 526中引入了Variable Annotations。它使得Python 3.6及以后的Python 代码拥有了“声明”变量类型的能力。这里的“声明”之所以会打引号,是因为这个声明是给IDE和人看的。这个声明对 Python 的解释器无效。

Type Hints

PyCharm现在已经可以比较好地支持Type Hints了。例如下面这一段代码:

def upload(url):
print(f'now upload a file to {url}')
return True

模拟一段上传文件的函数,上传成功以后返回True。接收一个参数url。在正常情况下,这个url应该是一个字符串。于是,使用Type Hints,代码可以变为:

def upload(url: str) -> bool:
print(f'now upload a file to {url}')
return True

如果直接运行,其运行效果如下图所示:

现在假设传递一个不是字符串的变量给upload函数,此时PyCharm就会提示类型有问题,如下图所示:



但提示归提示,强行运行也是没有问题的。这就说明Type Hints主要是给IDE和人用的,解释器并不会关心类型正不正确。

如果修改这个函数的返回值,让它不返回True 或者False,PyCharm 也会发出警告:

Type Hints的官方文档,可以参阅:typing — Support for type hints

Variable Annotations

对于Variable Annotations,如下图所示,虽然目前PyCharm还不能很好地提示变量类型不对,但是人在读代码的时候,还是会起到一定的帮助。

除了这种写法外,Variable Annotations还支持把类型写在注释中,如下图所示:

虽然PyCharm不能起到很好的提示作用,但是可以使用一个第三方库mypy来对代码做静态检查,其运行效果如下图所示,可以发现赋值的类型与声明的类型不一致(expression has type "str", variable has type "bool", 表达式的类型为“str”,变量的类型是“bool”)。

关于Variable Annotations的更多用法,可以参阅:Syntax for Variable Annotations

关于Mypy,可以参阅它的官方文档:Mypy documentation

docstring

在docstring来标注变量的类型,如下图所示:



这种写法可以用来提示一个函数,或者一个类它里面的各个变量的情况。但是详细程度需要看开发者有没有耐心把这个注释写清楚。

Bean

这种方法来自与Java Bean的思想,它主要用来解决列表套字典,字典套字典,字典套列表,列表套列表这种深层的嵌套关系。关于这个方法,请参阅另一篇文章:可爱的豆子——使用Beans思想让Python代码更易维护

记住 Python 变量类型的三种方式的更多相关文章

  1. python实现单例模式的三种方式及相关知识解释

    python实现单例模式的三种方式及相关知识解释 模块模式 装饰器模式 父类重写new继承 单例模式作为最常用的设计模式,在面试中很可能遇到要求手写.从最近的学习python的经验而言,singlet ...

  2. Python格式化输出的三种方式

    Python格式化输出的三种方式 一.占位符 程序中经常会有这样场景:要求用户输入信息,然后打印成固定的格式比如要求用户输入用户名和年龄,然后打印如下格式:My name is xxx,my age ...

  3. Python实现定时执行任务的三种方式简单示例

    本文实例讲述了Python实现定时执行任务的三种方式.分享给大家供大家参考,具体如下: 1.定时任务代码 import time,os,sched schedule = sched.scheduler ...

  4. python 字符串换行的三种方式

    if __name__ == '__main__': #第一种: 三个单引号 print ''' aaaaaaaaaaaaaaaa         bbbbbbbbbbbbbb''' #第二种: 三个 ...

  5. python实现进程的三种方式及其区别

    在python中有三种方式用于实现进程 多进程中, 每个进程中所有数据( 包括全局变量) 都各有拥有⼀份, 互不影响 1.fork()方法 ret = os.fork() if ret == 0: # ...

  6. Python—创建进程的三种方式

    方式一:os.fork() 子进程是从os.fork得到的值,然后赋值开始执行的.即子进程不执行os.fork,从得到的值开始执行. 父进程中fork之前的内容子进程同样会复制,但父子进程空间独立,f ...

  7. Python输出内容的三种方式:print输出 python脚本执行 linux直接执行

    1.  在linux中安装python后,在linux命令行中输入python即可切换到Python命令行下 退出python命令行的命令: 老版本:ctrl+D 新版本:quit();或exit() ...

  8. python反转列表的三种方式

    1.内建函数reversed() li =[1, 2, 3, 4, 5, 6] a = list(reversed(li)) print (a) 注意:reversed()函数返回的是一个迭代器,而不 ...

  9. C++利用宏实现变量交换的三种方式

    #include <iostream> using namespace std; //引入中间变量 #define SWAP1(a,b) {int tmp=a;a=b;b=tmp;} // ...

随机推荐

  1. HDU 3948 不同回文子串个数

    集训队论文中有求不同子串个数的做法,就是扫一遍height数组,过程中根据height数组进行去重.对于本题也是雷同的,只是每一次不是根据与排名在上一位的LCP去重,而是与上一次统计对答案有贡献的后缀 ...

  2. effective c++ 思维导图

    历时两个多月的时间,终于把effective c++又复习了一遍,比较慢,看的是英文版,之前看的时候做过一些笔记,但不够详细,这次笔者是从头到尾的翻译了一遍,加了一些标题,先记录到word里面,然后发 ...

  3. Atom打造 c/c++编译环境(忙了一个上午)

    众所周知 Atom是一款非常酷炫的编辑器.因为它就像上古卷轴一样,玩家可以开发各种dlc补丁,实现自己想要的效果.所以Atom 可以被你改造成自己想要的东西,可以用来写算法竞赛题目,可以开发网页,可以 ...

  4. LeetCode 322. Coin Change

    原题 You are given coins of different denominations and a total amount of money amount. Write a functi ...

  5. Websphere(was)与Weblogic部署EJB的注意项

    复杂的故事简单说,复杂的问题简单做. EJB容器 简介 本节讲解EJB项目在Weblogic和Was上的部署需要注意设置的一些内容.不同的中间件对EJB支持方式不一样,所以配置的原理也略有差异. 关键 ...

  6. IntelliJ-项目配置,解决no artifacts的warnings

    1.名词解释 artifacts:是maven中的一个概念,表示项目/modules如何打包,比如jar,war,war exploded,ear等打包形式, 一个项目或者说module有了artif ...

  7. bzoj4827 [Hnoi2017]礼物

    Description 我的室友最近喜欢上了一个可爱的小女生.马上就要到她的生日了,他决定买一对情侣手 环,一个留给自己,一个送给她.每个手环上各有 n 个装饰物,并且每个装饰物都有一定的亮度.但是在 ...

  8. Java中的增强 for 循环 foreach

    foreach 是 Java 中的一种语法糖,几乎每一种语言都有一些这样的语法糖来方便程序员进行开发,编译期间以特定的字节码或特定的方式来对这些语法进行处理.能够提高性能,并减少代码出错的几率.在 J ...

  9. React入门---属性(state)-7

    state------>虚拟dom------>dom 这个过程是自动的,不需要触发其他事件来调用它. state中文理解:页面状态的的一个值,可以存储很多东西. 学习state的使用: ...

  10. 区块链入门(1):搭建(Ubuntu系统)Truffle v3.2.1 开发和测试环境

    本文主要讲解ubuntu 16.04下, truffle开发测试环境的搭建.  第一步:安装nodejs 和 npm,有两种比较常见的方法. 方法1:直接在nodejs官网下载nodejs-v6.10 ...