[xpressive] Accessing named capture from another scope in the semantic action

Hi! Is it possible access captured group from another scope in the semantic action? Can I write a lazy function somehow and access another scope? The following code results in ”bad_lexical_cast” exception, likely due to the named capture "Year" is an empty string in the "outer scope". const sregex yyyymmdd = (Year=_d>>_d>>_d>>_d) >> (Month= _d>>_d)
(Day= _d>>_d);
sregex rx = yyyymmdd [ tm_year(t) = as<int>(Year) - 1900 /*, … */ ] // bad lexical cast: source type value could not be interpreted as target >> hhmmss [ tm_hour(t) = as<int>(Hour) /*, …*/ ] ; In my case the regex has no recursion, no captured repeated groups, so I can't understand really why I got nested result set. Dumping the nested result tree indicates that the values are captured in another ”scope”. But this is in the match_result<> set, and I can't figure out if there is any equivalent set available inside the semantic action. 20140119190000 #rx day = hour = minute = month = second = year = 20140119 #yyyymmdd day = 19 hour = minute = month = 01 second = year = 2014 190000 #hhmmss day = hour = 19 minute = 00 month = second = 00 year = I’m asking mostly for educational reason. Thanks for any hints! perrog Code: mark_tag Year(1),Month(2),Day(3),Hour(4),Minute(5),Second(6), Micro(7); const sregex yyyymmdd = (Year=_d>>_d>>_d>>_d) >> (Month= _d>>_d) >> (Day= _d>>_d); const sregex hhmmss = (Hour=_d>>_d)>>(Minute=_d>>_d)>>(Second=_d>>_d); bool is_datetime(std::string const& input) { // …don’t need any semantic actions when validating… smatch ignore; sregex rx = yyyymmdd >> hhmmss; return regex_match(input, ignore, rx); } bool get_datetime(std::string const& input, struct tm *time) { local<struct tm*> t(time); function<int tm::*>::type tm_year = { &tm::tm_year }; function<int tm::*>::type tm_hour = { &tm::tm_hour }; // … sregex rx = yyyymmdd [ tm_year(t) = as<int>(Year) - 1900 /*, … */ ] // bad lexical cast: source type value could not be interpreted as target >> hhmmss [ tm_hour(t) = as<int>(Hour) /*, …*/ ] ; smatch ignore; return regex_match(input, ignore, rx); }

On 1/19/2014 11:23 AM, Roger wrote:
Hi!
Is it possible access captured group from another scope in the semantic action? Can I write a lazy function somehow and access another scope? The following code results in ”bad_lexical_cast” exception, likely due to the named capture "Year" is an empty string in the "outer scope".
const sregex yyyymmdd = (Year=_d>>_d>>_d>>_d) >> (Month= _d>>_d)
(Day= _d>>_d);
sregex rx = yyyymmdd [ tm_year(t) = as<int>(Year) - 1900 /*, … */ ] // bad lexical cast: source type value could not be interpreted as target
hhmmss [ tm_hour(t) = as<int>(Hour) /*, …*/ ] ;
In my case the regex has no recursion, no captured repeated groups, so I can't understand really why I got nested result set.
A nested regex *always* results in nested match results. Xpressive can't know in general that the regex currently being defined is non-recursive, and any other behavior would lead to inconsistencies.
Dumping the nested result tree indicates that the values are captured in another ”scope”. But this is in the match_result<> set, and I can't figure out if there is any equivalent set available inside the semantic action.
20140119190000 #rx day = hour = minute = month = second = year = 20140119 #yyyymmdd day = 19 hour = minute = month = 01 second = year = 2014 190000 #hhmmss day = hour = 19 minute = 00 month = second = 00 year =
I’m asking mostly for educational reason. Thanks for any hints!
I don't think there's a general way to do what you're trying to do. That's a bummer. But since your regex is non-recursive, you can use the following hack to flatten your regex out and get the behavior you want: const auto yyyymmdd = boost::proto::deep_copy( (Year=_d>>_d>>_d>>_d) >> (Month= _d>>_d) >> (Day= _d>>_d)); const auto hhmmss = boost::proto::deep_copy( (Hour=_d>>_d)>>(Minute=_d>>_d)>>(Second=_d>>_d)); Notice the "auto" and the "deep_copy". HTH, -- Eric Niebler Boost.org http://www.boost.org
participants (2)
-
Eric Niebler
-
Roger