一、三种SyntaxError:
- invalid syntax(无效语法)
- invalid character in identifier(标识符中有无效字符)
- EOL while scanning string literal(检查到不完整的字符串)
(1)SyntaxError: invalid syntax(无效语法),这是语法错误中最常见的一种,通常是由下面几种情况引起的。
- 遗漏了标点符号,比如漏了冒号,混用中英文符号等;
- 关键字拼写错误或遗漏,比如while写成了whlie,for…in…中的关键字in忘写了等;
- 变量名或函数名使用了关键字
(2)SyntaxError: invalid character in identifier(标识符中有无效字符);
在运行代码的时候出现这个错误有可能是你在写代码时频繁地切换中英文输入法所造成的,修改为对应的英文符号即可。
(3)SyntaxError: EOL while scanning string literal(检查到不完整的字符串);
这种情况通常是因为遗漏了字符串两边的引号,或者混用了引号(即字符串两边的引号不统一)。
语法错误(syntax errors)是初学者最容易犯的错误,简单来说就是代码不符合Python的基本语法规范而导致程序出了问题。
二、下面讲讲SyntaxError异常和回溯:
当解释器在Python代码中遇到无效语法时,它将抛出一个SyntaxError异常,并提供一个带有一些有用信息的回溯,以便调试错误。
回溯是一个堆栈追踪,从异常处理程序的点一直到调用链中的异常引发点,还可以从调用的角度(没有错误的上下文)向上使用当前调用堆栈,这对于查找函数所遵循的路径非常有用。
来看一个Python中包含无效语法的代码:
在第4行字典的文字中可以看到无效的语法:第二个词条“jim”漏掉了一个逗号,这段代码如果照常运行,则会得到下面的回溯结果:
注意:traceback消息定位的错误在第5行,而不是第4行。当获得一个SyntaxError traceback,并且traceback所指向的代码看起来很好时,可开始向后移动代码,直到能确定哪里出了问题。
在上面的例子中,根据后面的内容,省略逗号是没有问题的,例如第5行“michael”后面缺少逗号是没有问题的。
有几个元素的SyntaxError回溯,可以帮助确定代码的无效语法:
遇到无效语法的 文件名;
遇到问题的 行号和代码的复写行;
在复制代码下面的行中有一个 插入符号(^),它向显示代码中有问题的那一点;
异常类型SyntaxError之后的 错误消息,可以提供帮助确定问题的信息;
在上面的例子中,给出的文件名是theofficefacts,行号为5,插入符号指向字典键michael的结束引用。
三、常见的语法问题
1、误用赋值运算符(=)
看看下面的代码示例及由此产生的SyntaxError回溯:
示例一
示例一尝试将值5分配给len()调用,在这种情况下,SyntaxError消息非常有用,它告诉你不能给函数调用赋值。
示例二
示例二尝试将字符串和整数分配给文字,同样的规则也适用于其他文字值。回溯消息表明当试图将一个值赋给一个文字时,问题就会发生。
注意:上面的示例缺少重复的代码行和指向回溯中的问题的插入符号(^),当在REPL中尝试从文件中执行这段代码时,所看到的异常和回溯是不同的。如果这个代码在一个文件中,则会得到重复的代码行和指向问题的插入符号。
很可能你的目的不是给文字或函数调用赋值,比如不小心省略了额外的等号(=),就会发生这种情况,这会将赋值转换为比较。如下所示,比较是有效的:
大多数情况下,当Python告诉你正在对无法赋值的东西进行赋值时,首先可能需要检查确保语句不应该是布尔表达式。当试图为Python关键字赋值时,也可能会遇到这个问题。
新手小白对Python表达式、变量赋值、关键字等这部分基础语法理解的还有点迷糊的,语法详解可戳这里↓↓↓
<Python核心基础语法详解 点击获取>
2、拼写错误、缺少或误用Python关键字
Python关键字在代码中不能用作标识符、变量或函数名,只能在Python允许的上下文中使用。
python3中的内置关键字:and,as,assert,break,class,continue,def,del,elif,else,except,False,finally,for,from,global,if,import,in,is,lambda,None,not,nonlocal,or,pass,raise,return,True,try,while,with,yield
1)如果在Python代码中拼错了关键字,得到一个SyntaxError。如例:
消息将读取SyntaxError无效语法,但这没有多大帮助,回溯指向Python可以检测到错误的第一个地方,要修复这类错误,请正确拼写所有Python关键字。
2)另一个关于关键字的常见问题是你完全忽略了它们:
如果从插入符号返回,则可以看到for循环语法中缺少关键字in;
3)误用受保护的Python关键字,一个常见的例子是在循环外使用continue或break。这在开发过程中很容易发生,当你在实现一些东西的时候,碰巧把逻辑移出了一个循环:
在这里”'break' outside loop和'continue' not exactly in loop“这两个信息可以帮助你明确地知道该怎么做。
另一个例子是如果你尝试给一个变量分配一个Python关键字,或者使用一个关键字来定义一个函数:
当你试图为pass分配一个值或者试图定义一个名为pass的新函数时,你会再次看到“无效语法”的消息。
在Python代码中解决这种类型的无效语法可能会稍微困难一些,因为代码从外部看起来没什么问题,仍然会得到一个SyntaxError,可考虑检查你想要使用的变量名或函数名与你正在使用的Python版本的关键字列表。
受保护的关键字列表随着Python的每个新版本而改变,比如print,它在python2和python3中有所不同:
你可以运行以下代码来查看关键字列表,无论你运行的Python版本是什么:
keyword提供了有用的keyword.iskeyword();如果你只是需要一个快速的方法来检查通过变量,那么你可以使用这段代码,可快速告诉你要使用的标识符是否是关键字:
3、缺少括号、方括号和引号
1)缺少或不匹配的右括号、方括号或引号等都会引发无效语法,在嵌套圆括号的很长行或更长的多行块中很难发现这些,可通过Python的回溯来发现不匹配或缺失的引用,如例:
这里回溯指向无效代码,其中在结束单引号后有一个t'。要解决这个问题,可进行以下两种更改:
- 用反斜杠转义单引号('don\t')
- 将整个字符串用双引号括起来(“don't”)
2)另一个常见的错误是忘记关闭字符串,对于双引号和单引号字符串,情况和回溯是相同的:
traceback中的插入符号指向问题代码,SyntaxError消息“在扫描字符串文字时的EOL”更具体一些,有助于确定问题。这意味着Python解释器在一个开放字符串关闭之前到达该行(EOL)的末尾。要解决这个问题,请使用与开始时匹配的引号关闭字符串,上例将使用双引号(")。
3)在f-string语句中缺少引号也会导致Python中无效的语法:
打印的f-string中对ages字典的引用缺少关键引用的双引号,得到的回溯结果如下:
Python识别问题并告诉你存在于f-string中,消息“未终止字符串”也指出了问题所在,本例中的插入符号仅指向f-string的开头,可能没那么有用,但缩小了查找问题的范围,在 f 字串的某个地方有一个未终止的字符串,你只需要找到在哪里。
要修复此问题,就要确保所有内部f-string引号和方括号都已存在。
4)缺少括号和方括号,情况大致相同。
第一种是把列表中的右括号去掉:
当运行这段代码时,会被告知调用print()有一个问题:
这里发生的是Python认为列表包含三个元素:1、2和3 print(foo())。Python使用空格从逻辑上对事物进行分组,因为从print(foo())中没有逗号或括号分隔3,所以Python将它们集中在一起作为列表的第三个元素。
另一种是在列表的最后一个元素后面添加一个逗号,同时仍然去掉右方括号:
现在你得到了一个不同的回溯:
在前面的例子中,3和print(foo())被集中在一起作为一个元素,但是这里可以看到一个逗号将两者分开。现在print(foo())的调用被添加为列表的第四个元素,Python到达了文件的末尾,但没有使用右括号。
缺少括号和方括号是Python很难识别的。有时能做的就是从插入符号开始向后移动,直到能够识别出缺失或错误的地方。
Python小白在尝试运行代码的过程中多少都有碰过到SyntaxError错误,看着突然跳出来的报错是一脸懵,在理解回溯消息以及在Python中可能遇到的无效语法形式,下一次出现SyntaxError时,就可以更好地修复这个问题了!
关注博主账号,交流探讨可私信。