未定义名称逐行读取文件时出现错误python
因此,我对python非常陌生,我不确定我的代码是否最有效,但如果有人能向我解释为什么我的脚本在运行时返回“name not defined”错误,我将非常感激。在一个单独的文件中,我有一个300个基因名称的列表,每行一个名称,我要读取,并将每行存储为字符串变量 在脚本中,我有一个600个变量的列表。300个标记为name_bitscore的变量和300个标记为name_长度的变量。 我想根据条件筛选列表。我的脚本如下所示:未定义名称逐行读取文件时出现错误python,python,loops,variables,io,Python,Loops,Variables,Io,因此,我对python非常陌生,我不确定我的代码是否最有效,但如果有人能向我解释为什么我的脚本在运行时返回“name not defined”错误,我将非常感激。在一个单独的文件中,我有一个300个基因名称的列表,每行一个名称,我要读取,并将每行存储为字符串变量 在脚本中,我有一个600个变量的列表。300个标记为name_bitscore的变量和300个标记为name_长度的变量。 我想根据条件筛选列表。我的脚本如下所示: #!/usr/bin/python with open("seqnam
#!/usr/bin/python
with open("seqnames-test1-iso-legal-temp.txt") as f:
for line in f:
exec("b="+line+"_bitscore")
exec("l="+line+"_length")
if 0.5*b <= 2*1.05*l and 0.5*b >= 2*0.95*l:
print line
ham_pb_length=2973
ham_pb_bitscore=2165
g2225_ph_length=3303
cg2225_ph_bitscore=2278
#!/usr/pin/python
name="string"
string_value=4
exec("b="+name+"_value")
print(name)
print(b)
这将返回:
string
4
所以,我知道我可以使用exec在变量声明中包含一个字符串变量,因为b按预期返回4。所以,我不知道为什么我的第一个脚本中会出现错误
我通过输入
#!/usr/bin/python
with open("seqnames-test1-iso-legal-temp.txt") as f:
for line in f:
print type(line)
它还回了电话
<type 'str'>
300次,所以我知道每个变量行都是一个字符串,这就是为什么我不明白为什么我的测试脚本可以工作,但这一个没有
任何帮助都将不胜感激
行
是文本文件迭代器生成的,它为读取的每一行发出一个换行符
你的表情是:
exec("b="+line+"_bitscore")
作为以下内容传递给执行机构:
b=ham_pb
_bitscore
去掉输出,这样就行了
exec("b="+line.rstrip()+"_bitscore")
前提是在循环之前移动以下行,以便声明变量:
ham_pb_length=2973
ham_pb_bitscore=2165
g2225_ph_length=3303
cg2225_ph_bitscore=2278
更好的方法:停止使用exec
,使用字典避免动态定义变量。put#/usr/bin/env python
作为第一行。更多解释请参见问题
正如Jean所指出的,exec不是这项工作的合适工具。您应该使用字典,因为它们不太危险(搜索代码注入),而且字典更容易阅读。下面是一个如何使用python文档中的字典的示例:
>>> tel = {'jack': 4098, 'sape': 4139}
>>> tel['guido'] = 4127
>>> tel
{'sape': 4139, 'guido': 4127, 'jack': 4098}
>>> tel['jack']
4098
>>> del tel['sape']
>>> tel['irv'] = 4127
>>> tel
{'guido': 4127, 'irv': 4127, 'jack': 4098}
>>> list(tel.keys())
['irv', 'guido', 'jack']
>>> sorted(tel.keys())
['guido', 'irv', 'jack']
>>> 'guido' in tel
True
>>> 'jack' not in tel
False
我可以想出一个方法来实现你的目标:
with open("seqnames-test1-iso-legal-temp.txt") as f:
gene_data = {'ham_pb_length':2973, 'am_pb_bitscore':2165,
'g2225_ph_length':3303, 'cg2225_ph_bitscore':2278}
'''maybe you have more of these gene data things. If so,
just append them to the end of the above dictionary literal'''
for line in f:
if not line.isspace():
bitscore = gene_data[line.rstrip()+'_bitscore']
length = gene_data[line.rstrip()+'_bitscore']
if (0.95*length <= bitscore/4 <= 1.05*length):
print line
打开(“seqnames-test1-iso-legal-temp.txt”)作为f:
基因数据={'ham_pb_length':2973,'am_pb_bitscore':2165,
'g2225_ph_length':3303,'cg2225_ph_bitscore':2278}
''也许你有更多的基因数据。如果是,,
只需将它们附加到上述字典文本“”的末尾即可
对于f中的行:
如果不是line.isspace():
bitscore=gene_数据[line.rstrip()+''u bitscore']
长度=基因数据[line.rstrip()+''位分数']
如果(0.95*lengthline
包含行终止符。您必须使用line.rstrip()
因此,为了澄清,是否应该将f
中line.rstrip()的第2行替换为?否。请参阅我的答案(如果它对您有效,请接受)我现在只得到一个错误NameError:name'ham\u pb\u bitscore'没有定义
。这可能是因为它是在代码块之后定义的吗?如果不是,我将尝试使用字典重写它,因为我在别处读到,以这种方式使用exec不是最佳做法。是的,将代码块移到上面。但是,使用exec不是最佳做法。而且它相当不安全(如果不控制文件中的内容,可能会导致代码注入)这似乎在很大程度上是有效的,因为它打印了4个预期结果,但随后给了我一个错误:KeyError:“\u bitscore”
您的文件结尾可能有一些空格。KeyError
表示您尝试了字典查找,但失败了。在bitscore=gene\u data[line.rstrip()+“\u bitscore']
,line.rstrip()
是某次迭代中的空字符串。Python然后将其作为bitscore=gene_data['''+'''''.\u bitscore'.]
运行,这与bitscore=gene_data['''.\u bitscore'.]相同。要修复它,请将如果不是line.isspace():
放在for循环之后和赋值语句之前(并相应地更改缩进)。这将检查该行是否都是空白字符。为了演示,我更改了原始答案。
with open("seqnames-test1-iso-legal-temp.txt") as f:
gene_data = {'ham_pb_length':2973, 'am_pb_bitscore':2165,
'g2225_ph_length':3303, 'cg2225_ph_bitscore':2278}
'''maybe you have more of these gene data things. If so,
just append them to the end of the above dictionary literal'''
for line in f:
if not line.isspace():
bitscore = gene_data[line.rstrip()+'_bitscore']
length = gene_data[line.rstrip()+'_bitscore']
if (0.95*length <= bitscore/4 <= 1.05*length):
print line