为何通过插值将字符串变量转为raw字符串失败?求解答
问题
我查阅过若干通过插值将字符串变量转换为raw字符串的示例,但该方法在我的场景中无法生效。测试代码如下:
import json j = '{"value": "{\"foo\": \"bar\"}"}' print(j) print(fr"{j}") print(r'{"value": "{\"foo\": \"bar\"}"}') # Works print(json.loads(r'{"value": "{\"foo\": \"bar\"}"}')) try: print(json.loads(fr"{j}")) # Doesn't work except Exception as e: print(e)
直接使用r前缀的字符串可正常完成JSON解析,但使用fr"{j}"的方式却无法成功,请问我哪里操作有误?
原因与解决方法
- r前缀的作用阶段理解错了:
r前缀只在定义字符串字面量时生效,它是告诉Python不要转义字面量里的\等特殊字符。但fr"{j}"里的j是已经定义好的字符串变量,r前缀对j的内容没有任何转义处理能力——j在定义时已经把\"解析成了实际的"字符,所以fr"{j}"的结果和直接打印j完全一样。 - 实际存储的内容差异:
- 直接写
r'{"value": "{\"foo\": \"bar\"}"}'时,r让\"保留为\+",所以实际存储的字符串是{"value": "{\"foo\": \"bar\"}"},这符合JSON格式(内部引号被正确转义)。 - 而
j = '{"value": "{\"foo\": \"bar\"}"}'在定义时,Python会把\"解析成",所以j实际存储的内容是{"value": "{"foo": "bar"}"}——这里面的内部引号没有转义,JSON解析器会判定结构错误。
- 直接写
- 解决办法:
- 如果是自己定义字符串,直接用
r前缀定义j即可:j = r'{"value": "{\"foo\": \"bar\"}"}' print(json.loads(j)) # 正常解析 - 如果
j是从外部获取的字符串,需要确保它的内部引号已经被正确转义,或者对其进行转义处理后再解析。
- 如果是自己定义字符串,直接用
内容的提问来源于stack exchange,提问作者Roman Newaza
相关产品推荐
相关产品推荐

