1

我正在尝试使用 PyYaml 在我的 python 代码中加载用户定义的标签。对 pyYaml 加载器、构造器、表示器解析器、解析器和转储器没有太多经验。

下面是我能想出的代码:

import yaml, os 
from collections import OrderedDict

root = os.path.curdir

def construct_position_object(loader, suffix, node):
    return loader.construct_yaml_map(node)

def construct_position_sym(loader, node):
    return loader.construct_yaml_str(node)

yaml.add_multi_constructor(u"!Position", construct_position_object)
yaml.add_constructor(u"!Position", construct_position_sym)


def main():
    file = open('C:\calcWorkspace\\13.3.1.0\PythonTest\YamlInput\Exception_V5.yml','r')
    datafile = yaml.load_all(file) 
    for data in datafile:          


        yaml.add_representer(literal, literal_presenter)
        yaml.add_representer(OrderedDict, ordered_dict_presenter)
        d = OrderedDict(l=literal(data))
        print yaml.dump(data,  default_flow_style=False)

    print datafile.get('abcd').get('addresses')

    yaml.add_constructor('!include', include)

def include(loader, node):
    """Include another YAML file."""

    global root
    old_root = root

    filename = os.path.join(root, loader.construct_scalar(node))
    root = os.path.split(filename)[0]

    data = yaml.load(open(filename, 'r'))
    root = old_root

    return data


class literal(str): pass

def literal_presenter(dumper, data):
    return dumper.represent_scalar('tag:yaml.org,2002:str', data, style='|')


def ordered_dict_presenter(dumper, data):
    return dumper.represent_dict(data.items())


if __name__ == '__main__':
    main()

这是我的 Yaml 文件:

#sid: Position[SIK,sourceDealID,UTPI] 
sid: Position[1232546, 0634.10056718.0.1096840.0,]
ASSET_CLASS: "Derivative"
SOURCE_DEAL_ID: "0634.10056718.0.1096840.0"
INSTR_ID: "UKCM.L"
PRODUCT_TYPE_ID: 0
SOURCE_PRODUCT_TYPE: "CDS"
NOTIONAL_USD: 14.78
NOTIONAL_CCY: 
LOB:
PRODUCT_TYPE:
#GIM
UNDERLIER_INSTRUMENT_ID:
MTM_USD: 
MTM_CCY:
TRADER_SID:
SALES_PERSON_SID:
CLIENT_SPN:
CLIENT_UCN:
CLIENT_NAME:
LE: 
---
sid: Position[1258642, 0634.10056718.0.1096680.0,]
#sid: Position[1]
ASSET_CLASS: "Derivative"
SOURCE_DEAL_ID: "0634.10056718.0.1096840.0"
INSTR_ID: "UKCM.L"
PRODUCT_TYPE_ID: 0
SOURCE_PRODUCT_TYPE: "CDS"
NOTIONAL_AMT: 18.78
NOTIONAL_CCY: "USD"
LOB:
PRODUCT_TYPE:
UNDERLIER_INSTRUMENT_ID:
MTM_AMT: 
MTM_CCY:
TRADER_SID:
SALES_PERSON_SID:
CLIENT_SPN:
CLIENT_UCN:
CLIENT_NAME:
LE: 
--- 
# Excption documents to follow from here!!!

Exception:
  src_excp_id: 100001
  # CONFIGURABLE OBJECT, VALUE TO BE POPULATED RUNTIME (impact_obj COMES FROM CONFIG FILE)
  # VALUE STARTS FROM "!POSITION..." A USER DEFINED DATATYPE
  impact_obj: !Position [1232546, 0634.10056718.0.1096840.0,]
  # CONFIGURABLE OBJECT, VALUE TO BE POPULATED RUNTIME (rsn_obj COMES FROM CONFIG FILE)
  # VALUE STARTS FROM "_POSITION..." AN IDENTIFIER FOR CONFIGURABLE OBJECTS
  rsn_obj:    !Position [1258642, 0634.10056718.0.1096680.0,]
  exception_txt: "Invalid data, NULL value provided"
  severity: "High"   

看起来我的代码无法识别!Position用户定义的数据类型。

任何帮助都会得到帮助

问候。

4

1 回答 1

2

需要改变:

def construct_position_sym(loader, node):
    return loader.construct_yaml_str(node)

到 :

def construct_position_sym(loader, node):
    return loader.construct_yaml_seq(node)

因为位置对象是一个序列:

!Position [something, something]

所以构造函数必须是序列类型。完美运行!!!

于 2013-09-03T14:52:59.180 回答