最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

c++17 - Is there a way to parse a std::chrono::duration with a string literal as a field in an XML file using boost::property_tr

programmeradmin4浏览0评论

I would like to be able to write my config file as:

<?xml version="1.0" encoding="UTF-8"?>
<Config>  
  <DurationValue>20ns</DurationValue>
</Config>

or as:

<?xml version="1.0" encoding="UTF-8"?>
<Config>  
  <DurationValue>15s</DurationValue>
</Config>

Then parse the DurationValue field the same way in both cases. I'm running into an issue where I don't know what type to tell boost::property_tree that the field is. Internally, the value is stored as a std::chrono::nanoseconds.

My attempt at parsing:

boost::property_tree::ptree property_tree;
boost::property_tree::read_xml("config.xml", property_tree);
auto config = property_tree.get_child("Config");
std::chrono::nanoseconds duration_value = std::chrono::duration_cast<std::chrono::nanoseconds>(config.get<std::common_type<std::chrono::duration>>("DurationValue"));

Is there a way to do this that I am missing? I want to be flexible enough to support using any std::chrono literal. Thanks in advance.

I would like to be able to write my config file as:

<?xml version="1.0" encoding="UTF-8"?>
<Config>  
  <DurationValue>20ns</DurationValue>
</Config>

or as:

<?xml version="1.0" encoding="UTF-8"?>
<Config>  
  <DurationValue>15s</DurationValue>
</Config>

Then parse the DurationValue field the same way in both cases. I'm running into an issue where I don't know what type to tell boost::property_tree that the field is. Internally, the value is stored as a std::chrono::nanoseconds.

My attempt at parsing:

boost::property_tree::ptree property_tree;
boost::property_tree::read_xml("config.xml", property_tree);
auto config = property_tree.get_child("Config");
std::chrono::nanoseconds duration_value = std::chrono::duration_cast<std::chrono::nanoseconds>(config.get<std::common_type<std::chrono::duration>>("DurationValue"));

Is there a way to do this that I am missing? I want to be flexible enough to support using any std::chrono literal. Thanks in advance.

Share Improve this question asked Mar 17 at 14:56 SeedlessKiwiSeedlessKiwi 474 bronze badges
Add a comment  | 

1 Answer 1

Reset to default 2

How about telling boost::property_tree to parse the field as a string and then pass that string off to a custom post-processor to turn it into the desired duration?

std::chrono::nanoseconds
parse_duration(std::string s)
{
    using namespace std;
    using namespace chrono;
    istringstream in{std::move(s)};
    in.exceptions(ios::failbit);
    int v;
    string unit;
    in >> v >> unit;
    if (unit == "h")
        return hours{v};
    else if (unit == "min")
        return minutes{v};
    else if (unit == "s")
        return seconds{v};
    else if (unit == "ms")
        return milliseconds{v};
    else if (unit == "us")
        return microseconds{v};
    else if (unit == "ns")
        return nanoseconds{v};
    throw std::runtime_error("bad unit");
}

与本文相关的文章

发布评论

评论列表(0)

  1. 暂无评论