You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

解析YAML文件转字典遇TypeError,求问题排查与解决方法

问题:YAML解析后环境项为长字符串,无法通过键名访问

我想把下面定义的YAML内容转换成字典:

development: user:dev_uid pass:dev_pwd host:127.0.0.1 database:dev_db production: user:uid pass:pwd host:127.0.0.2 database:db

我用YAML库加载数据后,发现字典里的环境项是长字符串。执行了这段代码:

#!/usr/bin/python3
import yaml
config = yaml.load(open('database.conf', 'r'))
print(config['development'])

输出结果是:

user:dev_uid pass:dev_pwd host:127.0.0.1 database:dev_db

根本没法通过键名访问条目,后来我尝试用yaml.load加载这个字符串也不行,执行print(config['development']['user'])的时候直接报错:

TypeError: string indices must be integers

我理想的情况是解析函数返回字典(或者可通过键名访问的结构),这样就能用print(config['development']['user'])甚至config.user这种方式访问内容了。请问我哪里出错了?


解答

嘿,这问题其实出在你的YAML格式完全不规范!YAML对缩进、冒号后的空格还有层级结构要求很严格,你把所有内容挤在一行,键值对之间既没换行也没正确分隔,导致YAML解析器直接把development后面的内容当成了一整段字符串,而不是嵌套的字典结构。

第一步:修正YAML文件格式

把database.conf改成符合规范的结构,每个键值对单独换行,冒号后必须加空格,子层级要缩进(一般用2个空格):

development:
  user: dev_uid
  pass: dev_pwd
  host: 127.0.0.1
  database: dev_db
production:
  user: uid
  pass: pwd
  host: 127.0.0.2
  database: db

第二步:使用安全的加载方式

另外提醒下,yaml.load()是不安全的(可能执行恶意代码),推荐用yaml.safe_load()替代。修正后的Python代码:

#!/usr/bin/python3
import yaml

# 用safe_load替代load,避免安全风险
with open('database.conf', 'r') as f:
    config = yaml.safe_load(f)

# 现在就能正常通过键名访问了
print(config['development']['user'])  # 输出 dev_uid

额外:实现dot运算符访问(可选)

如果想要用config.development.user这种dot方式访问,可以把字典转换成对象,比如用types.SimpleNamespace:

#!/usr/bin/python3
import yaml
from types import SimpleNamespace

def dict_to_namespace(d):
    if isinstance(d, dict):
        return SimpleNamespace(**{k: dict_to_namespace(v) for k, v in d.items()})
    return d

with open('database.conf', 'r') as f:
    config_dict = yaml.safe_load(f)
    config = dict_to_namespace(config_dict)

print(config.development.user)  # 输出 dev_uid

这样就能完全满足你的需求啦!

内容的提问来源于stack exchange,提问作者Shawn Taylor

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 09:27:22