diff --git a/libwccl/parser/Parser.cpp b/libwccl/parser/Parser.cpp index 5c591e99f1d26290d4b6676e03112c5da49434e9..0464fe51571b720cfc1ceb3fc334cbe90cfaba44 100644 --- a/libwccl/parser/Parser.cpp +++ b/libwccl/parser/Parser.cpp @@ -47,7 +47,7 @@ boost::shared_ptr<ANTLRParserResult<Wccl::StrSet> > Parser::parseStringOperator( ANTLRLexer lexer(istr); ANTLRParser parser(lexer); - return parser.parse_string_operator(tagset_); + return parser.parse_strset_operator(tagset_); } // ---------------------------------------------------------------------------- @@ -77,7 +77,7 @@ boost::shared_ptr<ANTLRParserResult<Wccl::Bool> > Parser::parsePredicate( ANTLRLexer lexer(istr); ANTLRParser parser(lexer); - return parser.parse_predicates(tagset_); + return parser.parse_bool_operator(tagset_); } // ---------------------------------------------------------------------------- @@ -107,7 +107,7 @@ boost::shared_ptr<ANTLRParserResult<Wccl::TSet> > Parser::parseSymSetOperator( { ANTLRLexer lexer(istr); ANTLRParser parser(lexer); - return parser.parse_sym_set_operator(tagset_); + return parser.parse_symset_operator(tagset_); } // ---------------------------------------------------------------------------- @@ -176,7 +176,7 @@ boost::shared_ptr<ANTLRParserResultBase> Parser::parseAnyOperator( ANTLRLexer lexer(ss); ANTLRParser parser(lexer); try { - result = parser.parse_sym_set_operator(tagset_); + result = parser.parse_position_operator(tagset_); } catch (antlr::ANTLRException& e) { errors << "(as tset) " << e.getMessage() << "\n"; // ignore, try another type @@ -188,7 +188,7 @@ boost::shared_ptr<ANTLRParserResultBase> Parser::parseAnyOperator( ANTLRLexer lexer(ss); ANTLRParser parser(lexer); try { - result = parser.parse_string_operator(tagset_); + result = parser.parse_strset_operator(tagset_); } catch (antlr::ANTLRException& e) { errors << "(as strset) " << e.getMessage() << "\n"; // ignore, try another type @@ -200,7 +200,7 @@ boost::shared_ptr<ANTLRParserResultBase> Parser::parseAnyOperator( ANTLRLexer lexer(ss); ANTLRParser parser(lexer); try { - result = parser.parse_predicates(tagset_); + result = parser.parse_bool_operator(tagset_); } catch (antlr::ANTLRException& e) { errors << "(as predicate) " << e.getMessage() << "\n"; // ignore, try another type diff --git a/libwccl/parser/grammar.g b/libwccl/parser/grammar.g index 58f2468b6a870b2528ed88ea178035d6b320b1e2..e354413c8682082a69c0a5a1224258bbc910110e 100644 --- a/libwccl/parser/grammar.g +++ b/libwccl/parser/grammar.g @@ -117,77 +117,71 @@ private: } } -// TODO -// - base, orth - -// TEMPORARY CHANGES -> -// -> tymczasowo zakomentowalem wywoalnie regul condit_* -// -> tymczasowo zakomentowalem 2 reguly z equal - /////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// // "GLOBAL" RULES /////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// + // ---------------------------------------------------------------------------- -// Rules for parsing string operators in scope (variables). +// Rule for parsing string set operator with scope. // Returns boost::shared_ptr<Function<StrSet> > -parse_string_operator +parse_strset_operator [const Corpus2::Tagset &tagset] returns [boost::shared_ptr<ANTLRParserResult<StrSet> > res] { res.reset(new ANTLRParserResult<StrSet>()); boost::shared_ptr<Function<StrSet> > op; } - : op = string_operators [tagset, *res->variables.get()] { + : op = string_operator [tagset, *res->variables.get()] { res->op = op; } EOF ; // ---------------------------------------------------------------------------- -// Rules for parsing predicates in scope (variables). +// Rule for parsing bool operator with scope. // Returns boost::shared_ptr<Function<Bool> > -parse_predicates +parse_bool_operator [const Corpus2::Tagset &tagset] returns [boost::shared_ptr<ANTLRParserResult<Bool> > res] { res.reset(new ANTLRParserResult<Bool>()); boost::shared_ptr<Function<Bool> > op; } - : op = logical_predicates [tagset, *res->variables.get()] { + : op = bool_operator [tagset, *res->variables.get()] { res->op = op; } EOF ; // ---------------------------------------------------------------------------- -// Rules for parsing tagset (symbol set) operators +// Rule for parsing symbol set operator with scope. // Returns boost::shared_ptr<Function<TSet> > -parse_sym_set_operator +parse_symset_operator [const Corpus2::Tagset &tagset] returns [boost::shared_ptr<ANTLRParserResult<TSet> > res] { res.reset(new ANTLRParserResult<TSet>()); boost::shared_ptr<Function<TSet> > op; } - : op = sym_set_operators [tagset, *res->variables.get()] { + : op = symset_operator [tagset, *res->variables.get()] { res->op = op; } EOF ; // ---------------------------------------------------------------------------- -// Rules for parsing position operators +// Rule for parsing position operator with scope. // Returns boost::shared_ptr<Function<Position> > -parse_position_operator +parse_position_operator [const Corpus2::Tagset &tagset] returns [boost::shared_ptr<ANTLRParserResult<Position> > res] -{ +{ res.reset(new ANTLRParserResult<Position>()); boost::shared_ptr<Function<Position> > op; } - : op = position_operators [tagset, *res->variables.get()] { + : op = position_operator [tagset, *res->variables.get()] { res->op = op; } EOF @@ -198,45 +192,50 @@ parse_position_operator // VALUES /////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// + // ---------------------------------------------------------------------------- -// Single or muliple values in string set: -// [] ['a'] ['a', 'b'] ["a"] ["a", "b"] ['a', "b"] +// Single or muliple (comma separated) elements in string set, may be: +// 'a' "a" [] ['a'] ['a', 'b'] ["a"] ["a", "b"] ['a', "b"] +// Parsing strset literal and returning plain strset value. // Returns boost::shared_ptr<StrSet> -str_set_literal +strset_literal returns [boost::shared_ptr<StrSet> s_set] { s_set.reset(new StrSet()); } - : s0: STRING { + : s0: STRING { s_set->insert(token_ref_to_ustring(s0)); } - | LBRACKET - ( s1: STRING { - s_set->insert(token_ref_to_ustring(s1)); - } - ( COMMA s2: STRING { - s_set->insert(token_ref_to_ustring(s2)); - } - )* - )? - RBRACKET -; -// Constrant string set + | LBRACKET + ( + s1: STRING { + s_set->insert(token_ref_to_ustring(s1)); + } + ( + COMMA s2: STRING { + s_set->insert(token_ref_to_ustring(s2)); + } + )* + )? + RBRACKET +; +// String set value as constrant string set: // Returns boost::shared_ptr<Constant<StrSet> > -str_set_value +strset_value returns [boost::shared_ptr<Constant<StrSet> > val] { boost::shared_ptr<StrSet> set; } - : set = str_set_literal { + : set = strset_literal { val.reset(new Constant<StrSet>(*set.get())); } ; // ---------------------------------------------------------------------------- -// Element of sym set. This rule, inset element into set. -// Element may be: a or `a ` -sym_set_elem +// Element of sym set. This rule, inserts element into symbol set +// with corresponding tagset. +// WARNING! This rule can throw ParserException! Be careful! +symset_elem [const Corpus2::Tagset& tagset, boost::shared_ptr<TSet>& t_set] : s1: SYMBOL { try { @@ -248,45 +247,49 @@ sym_set_elem } ; -// sym set literal -// {} {sym_set_elem} {sym_set_elem, ..., sym_set_elem} +// Symset literal. Symset element may be: +// a, `a ` (this is guaranteed by lexer rule - SYMBOL) or {a} {`a`} {a, b} +// {`a`, `b`} {a, `b`} {`a`, b} +// Parsing symset literal and returning plain symset value. // Returns boost::shared_ptr<TSet> -sym_set_literal +symset_literal [const Corpus2::Tagset& tagset] returns [boost::shared_ptr<TSet> t_set] { t_set.reset(new TSet()); } - : sym_set_elem[tagset, t_set] + : symset_elem [tagset, t_set] | LCURLY - ( sym_set_elem[tagset, t_set] (COMMA sym_set_elem[tagset, t_set])* )? + ( + symset_elem [tagset, t_set] (COMMA symset_elem [tagset, t_set])* + )? RCURLY ; -// Constant symbol set +// Symset value, as constant symbol set // Returns boost::shared_ptr<Constant<TSet> > -sym_set_value +symset_value [const Corpus2::Tagset& tagset] returns [boost::shared_ptr<Constant<TSet> > val] { boost::shared_ptr<TSet> set; } - : set = sym_set_literal [tagset] { + : set = symset_literal [tagset] { val.reset(new Constant<TSet>(*set.get())); } ; // ---------------------------------------------------------------------------- -// boolean value: -// Literal bool value may be True or False +// Bool literal. May be True or False. Parsing bool literal and returning +// plain bool value. // Returns boost::shared_ptr<Bool> bool_literal returns [boost::shared_ptr<Bool> val] : "True" { val.reset(new Bool(Bool(true ))); } | "False" { val.reset(new Bool(Bool(false))); } ; -// Constat bool Value +// Bool value, as constat bool Value // Returns boost::shared_ptr<Constant<Bool> > -boolean_value +bool_value returns [boost::shared_ptr<Constant<Bool> > val] { boost::shared_ptr<Bool> bool_lit; @@ -297,8 +300,9 @@ boolean_value ; // ---------------------------------------------------------------------------- -// position value: -// Position literal may be (+|-)?(0-9)+ or begin or end or nowhere +// Position literal may be: +// (+|-)?(0-9)+ or begin or end or nowhere +// Parsing position literal and returning plain position value. // returns boost::shared_ptr<Position> position_literal returns [boost::shared_ptr<Position> val] @@ -318,7 +322,8 @@ position_literal val.reset(new Position(Position(Position::Nowhere))); } ; -// Constant position value + +// Position as constant position value // Returns boost::shared_ptr<Constant<Position> > position_value returns [boost::shared_ptr<Constant<Position> > val] @@ -331,8 +336,9 @@ position_value ; // ---------------------------------------------------------------------------- -// Number may be unsigned or signed -number returns [int ret] +// Number may be unsigned or signed: 1, +1, -1 +number + returns [int ret] { ret = 0; } @@ -345,8 +351,10 @@ number returns [int ret] // VARIABLES /////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// + // ---------------------------------------------------------------------------- -// Position: $name +// Position: $Name +// Get position variable (however, before put into) from variables // Returns boost::shared_ptr<VariableAccessor<Position> > position_variable_acc [Variables& vars] @@ -360,7 +368,8 @@ position_variable_acc pos_acc.reset(new VariableAccessor<Position>(acc)); } ; -// Position vargetter + +// VarGetter for Position variable. This rule wrapped position_variable_acc. // Returs boost::shared_ptr<VarGetter<Position> > position_variable [Variables& vars] @@ -373,55 +382,42 @@ position_variable } ; -// ---------------------------------------------------------------------------- -// realtive position -relpos - [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Position> > ret] -{ - int n = 0; - boost::shared_ptr<Function<Position> > pos; -} - : "relpos" LPAREN pos = op_position [tagset, vars] COMMA n = number RPAREN { - ret.reset(new RelativePosition(pos, n)); - } -; - // ---------------------------------------------------------------------------- // String set, $s:name -// This expression gets variable of the type StrSet from string-named variable +// This expression gets (however, before put into) variable of the type StrSet +// from scope -- variables. // Returns boost::shared_ptr<VariableAccessor<StrSet> > -str_set_variable_acc +strset_variable_acc [Variables& vars] returns [boost::shared_ptr<VariableAccessor<StrSet> > strset_acc] : STR_PREFIX n: SYMBOL { - // get/put variable to variables vars.get_put<StrSet>(str_token_rem_grav(n)); - // makes accessor for value VariableAccessor<StrSet> acc = vars.create_accessor<StrSet>(str_token_rem_grav(n)); strset_acc.reset(new VariableAccessor<StrSet>(acc)); } ; -// Vargetter for StrSet variable + +// Vargetter for StrSet variable. This rule wrapped strset_variable_acc. // Returns boost::shared_ptr<VarGetter<StrSet> > -str_set_variable +strset_variable [Variables& vars] returns [boost::shared_ptr<VarGetter<StrSet> > op] { boost::shared_ptr<VariableAccessor<StrSet> > strset_acc; } - : strset_acc = str_set_variable_acc [vars] { + : strset_acc = strset_variable_acc [vars] { op.reset(new VarGetter<StrSet>(*strset_acc.get())); } ; // ---------------------------------------------------------------------------- // Symbol set: $t:name +// Get symset variable (however, before put into) from variables // Returns boost::shared_ptr<VariableAccessor<TSet> > -sym_set_variable_acc +symset_variable_acc [Variables& vars] returns [boost::shared_ptr<VariableAccessor<TSet> > symset_acc] : TST_PREFIX n: SYMBOL { @@ -433,23 +429,25 @@ sym_set_variable_acc symset_acc.reset(new VariableAccessor<TSet>(acc)); } ; -// Vargetter for symbol set variable + +// Vargetter for symbol set variable. This rule wrapped symset_variable_acc // Returns boost::shared_ptr<VarGetter<TSet> > -sym_set_variable +symset_variable [Variables& vars] returns [boost::shared_ptr<VarGetter<TSet> > op] { boost::shared_ptr<VariableAccessor<TSet> > symset_acc; } - : symset_acc = sym_set_variable_acc [vars] { + : symset_acc = symset_variable_acc [vars] { op.reset(new VarGetter<TSet>(*symset_acc.get())); } ; // ---------------------------------------------------------------------------- // Bool: $b:name +// Get bool variable (however, before put into) from variables // Returns boost::shared_ptr<VariableAccessor<Bool> > -boolean_variable_acc +bool_variable_acc [Variables& vars] returns [boost::shared_ptr<VariableAccessor<Bool> > bool_acc] : BOOL_PREFIX n: SYMBOL { @@ -461,15 +459,16 @@ boolean_variable_acc bool_acc.reset(new VariableAccessor<Bool>(acc)); } ; -// Vargetter for bool variable + +// Vargetter for bool variable. It is only wrapper for bool_variable_acc // Returns boost::shared_ptr<VarGetter<Bool> > -boolean_variable +bool_variable [Variables& vars] returns [boost::shared_ptr<VarGetter<Bool> > op] { boost::shared_ptr<VariableAccessor<Bool> > bool_acc; } - : bool_acc = boolean_variable_acc [vars] { + : bool_acc = bool_variable_acc [vars] { op.reset(new VarGetter<Bool>(*bool_acc.get())); } ; @@ -479,116 +478,43 @@ boolean_variable // OPERATORS /////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// -// ---------------------------------------------------------------------------- -// ---------------------------------------------------------------------------- -// Setvar operator -// Returns boost::shared_ptr<Function<Bool> > -// ---------------------------------------------------------------------------- -setvar_op - [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Bool> > ret] - : "setvar" LPAREN - ( - ret = setvar_body_pos [tagset, vars] - | ret = setvar_body_bool [tagset, vars] - | ret = setvar_body_sset [tagset, vars] - | ret = setvar_body_tset [tagset, vars] - ) - RPAREN -; -// Implementations of setvar: -// ---------------------------------------------------------------------------- -setvar_body_pos - [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Bool> > op] -{ - boost::shared_ptr<Function<Position> > ret_op; - boost::shared_ptr<VariableAccessor<Position> > ret_acc; -} - : ret_acc = position_variable_acc [vars] - COMMA - ret_op = op_position [tagset, vars] { - op.reset(new VarSetter<Position>(*ret_acc.get(), ret_op)); - } -; - -// ---------------------------------------------------------------------------- -setvar_body_bool - [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Bool> > op] -{ - boost::shared_ptr<Function<Bool> > ret_op; - boost::shared_ptr<VariableAccessor<Bool> > ret_acc; -} - : ret_acc = boolean_variable_acc [vars] - COMMA - ret_op = logical_predicates [tagset, vars] { - op.reset(new VarSetter<Bool>(*ret_acc.get(), ret_op)); - } -; - -// ---------------------------------------------------------------------------- -setvar_body_sset - [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Bool> > op] -{ - boost::shared_ptr<Function<StrSet> > ret_op; - boost::shared_ptr<VariableAccessor<StrSet> > ret_acc; -} - : ret_acc = str_set_variable_acc [vars] - COMMA ret_op = string_operators [tagset, vars] { - op.reset(new VarSetter<StrSet>(*ret_acc.get(), ret_op)); - } -; - -// ---------------------------------------------------------------------------- -setvar_body_tset - [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Bool> > op] -{ - boost::shared_ptr<Function<TSet> > ret_op; - boost::shared_ptr<VariableAccessor<TSet> > ret_acc; -} - : ret_acc = sym_set_variable_acc [vars] - COMMA - ret_op = sym_set_operators [tagset, vars] { - op.reset(new VarSetter<TSet>(*ret_acc.get(), ret_op)); - } -; -// ---------------------------------------------------------------------------- -// ---------------------------------------------------------------------------- -// Symbol set (tagset) operators +/////////////////////////////////////////////////////////////////////////////// +// Symbol set (tagset) operators // Returns boost::shared_ptr<Function<TSet> > -// ---------------------------------------------------------------------------- -sym_set_operators +/////////////////////////////////////////////////////////////////////////////// +symset_operator [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<TSet> > ret] - : ret = op_sym_set [tagset, vars] - | ret = condit_sym [tagset, vars] + : ret = symset_var_val [tagset, vars] + | ret = symset_condition [tagset, vars] + // + | LPAREN ret = symset_operator [tagset, vars] RPAREN ; -// Implementations of symbol set operators: + // ---------------------------------------------------------------------------- -op_sym_set +// It's wrapper for symset variable and symset value. +symset_var_val [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<TSet> > op] - : op = sym_set_variable [vars] - | op = sym_set_value [tagset] + : op = symset_variable [vars] + | op = symset_value [tagset] ; // ---------------------------------------------------------------------------- -// if (Bool, TSet, TSet) -// ? TSet ? Bool : {} -condit_sym +// Condition of the symset value: +// if (Bool, TSet, TSet) +// ? TSet ? Bool : {} +symset_condition [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<TSet> > op] { boost::shared_ptr<Function<Bool> > test; boost::shared_ptr<Function<TSet> > p_true, p_false; } - : "if" LPAREN test = logical_predicates [tagset, vars] COMMA - p_true = sym_set_operators [tagset, vars] - (COMMA p_false = sym_set_operators [tagset, vars])? + : "if" LPAREN test = bool_operator [tagset, vars] COMMA + p_true = symset_operator [tagset, vars] + (COMMA p_false = symset_operator [tagset, vars])? RPAREN { if (p_false) { op.reset(new Conditional<TSet>(test, p_true, p_false)); @@ -598,64 +524,114 @@ condit_sym } } | Q_MARK - (p_true = sym_set_operators [tagset, vars]) + (p_true = symset_operator [tagset, vars]) Q_MARK - (test = logical_predicates [tagset, vars]) { + (test = bool_operator [tagset, vars]) { op.reset(new Conditional<TSet>(test, p_true)); } ; -// ---------------------------------------------------------------------------- -// ---------------------------------------------------------------------------- -// Position operators + +/////////////////////////////////////////////////////////////////////////////// +// Position operator // Returns boost::shared_ptr<Function<Position> > +/////////////////////////////////////////////////////////////////////////////// +position_operator + [const Corpus2::Tagset& tagset, Variables& vars] + returns [boost::shared_ptr<Function<Position> > ret] + : ret = position_var_val [vars] + | ret = position_relpos [tagset, vars] + | ret = position_condition [tagset, vars] + // + | LPAREN ret = position_operator [tagset, vars] RPAREN +; + +// ---------------------------------------------------------------------------- +// Wrapper for position variable and position value +position_var_val + [Variables& vars] + returns [boost::shared_ptr<Function<Position> > ret] + : ret = position_value + | ret = position_variable [vars] +; + // ---------------------------------------------------------------------------- -position_operators +// Realtive position operator. +// TODO 2+2, actually relative gets position is possible only as relpos(...,...) +position_relpos [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Position> > ret] - : ret = op_position [tagset, vars] +{ + int n = 0; + boost::shared_ptr<Function<Position> > pos; +} + : "relpos" LPAREN pos = position_operator [tagset, vars] COMMA n = number RPAREN { + ret.reset(new RelativePosition(pos, n)); + } ; -// Implementations of symbol set operators: // ---------------------------------------------------------------------------- -op_position +// Condition of the position value +// if (Bool, Position, Position) +// ? Position ? Bool : 0 +position_condition [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Position> > op] - : op = position_variable [vars] - | op = position_value - | op = relpos [tagset, vars] - | op = condit_position [tagset, vars] +{ + boost::shared_ptr<Function<Bool> > test; + boost::shared_ptr<Function<Position> > p_true, p_false; +} + : "if" LPAREN test = bool_operator [tagset, vars] COMMA + p_true = position_operator [tagset, vars] + (COMMA p_false = position_operator [tagset, vars])? + RPAREN { + if (p_false) { + op.reset(new Conditional<Position>(test, p_true, p_false)); + } + else { + op.reset(new Conditional<Position>(test, p_true)); + } + } + | Q_MARK + p_true = position_operator [tagset, vars] + Q_MARK + test = bool_operator [tagset, vars] { + op.reset(new Conditional<Position>(test, p_true)); + } ; -// ---------------------------------------------------------------------------- -// ---------------------------------------------------------------------------- -// Stiring operators +/////////////////////////////////////////////////////////////////////////////// +// Stiring operator // Returns boost::shared_ptr<Function<StrSet> > -// ---------------------------------------------------------------------------- -string_operators - [const Corpus2::Tagset& tagset, Variables& vars] +/////////////////////////////////////////////////////////////////////////////// +string_operator [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > ret] - : ret = op_orth [tagset, vars] - | ret = op_base [tagset, vars] - | ret = op_lower [tagset, vars] - | ret = op_upper [tagset, vars] - | ret = op_affix [tagset, vars] - | ret = op_str_set [tagset, vars] - | ret = condit_str [tagset, vars] -; -// Implementations of string operators: + : ret = strset_orth [tagset, vars] + | ret = strset_base [tagset, vars] + | ret = strset_lower [tagset, vars] + | ret = strset_upper [tagset, vars] + | ret = strset_affix [tagset, vars] + | ret = strset_var_val [tagset, vars] + | ret = strset_condition [tagset, vars] + // + | LPAREN ret = string_operator [tagset, vars] RPAREN +; + // ---------------------------------------------------------------------------- -op_orth +// Orth operator. +strset_orth [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > ret] { boost::shared_ptr<Function<Position> > pos; } - : "orth" LBRACKET pos = op_position [tagset, vars] RBRACKET { + : "orth" LBRACKET pos = position_operator [tagset, vars] RBRACKET { ret.reset(new GetOrth(pos)); } ; + // ---------------------------------------------------------------------------- -op_base +// Base operator. +strset_base [const Corpus2::Tagset& /*tagset*/, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > ret] { @@ -665,30 +641,36 @@ op_base // ret = TODO } ; + // ---------------------------------------------------------------------------- -op_lower +// Lower operator. +strset_lower [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > ret] { boost::shared_ptr<Function<StrSet> > o_ret; } - : "lower" LPAREN o_ret = string_operators[tagset, vars] RPAREN { + : "lower" LPAREN o_ret = string_operator [tagset, vars] RPAREN { ret.reset(new ToLower(o_ret)); } ; + // ---------------------------------------------------------------------------- -op_upper +// Upper operator. +strset_upper [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > ret] { boost::shared_ptr<Function<StrSet> > o_ret; } - : "upper" LPAREN o_ret = string_operators[tagset, vars] RPAREN { + : "upper" LPAREN o_ret = string_operator [tagset, vars] RPAREN { ret.reset(new ToUpper(o_ret)); } ; + // ---------------------------------------------------------------------------- -op_affix +// Affix operator. +strset_affix [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > ret] { @@ -696,31 +678,35 @@ op_affix boost::shared_ptr<Function<StrSet> > o_ret; } : "affix" LPAREN - o_ret = string_operators[tagset, vars] COMMA offset = number - RPAREN { - ret.reset(new Affix(o_ret, offset)); - } + o_ret = string_operator [tagset, vars] COMMA offset = number + RPAREN { + ret.reset(new Affix(o_ret, offset)); + } ; + // ---------------------------------------------------------------------------- -op_str_set +// Wrapper ofr strset value and strset variable +strset_var_val [const Corpus2::Tagset& /*tagset*/, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > op] - : op = str_set_variable [vars] - | op = str_set_value + : op = strset_value + | op = strset_variable [vars] ; + // ---------------------------------------------------------------------------- +// Condition of the strset value // if (Bool, StrSet, StrSet) // ? StrSet ? Bool : [] -condit_str +strset_condition [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<StrSet> > op] { boost::shared_ptr<Function<Bool> > test; boost::shared_ptr<Function<StrSet> > p_true, p_false; } - : "if" LPAREN test = logical_predicates [tagset, vars] COMMA - p_true = string_operators [tagset, vars] - (COMMA p_false = string_operators [tagset, vars])? + : "if" LPAREN test = bool_operator [tagset, vars] COMMA + p_true = string_operator [tagset, vars] + (COMMA p_false = string_operator [tagset, vars])? RPAREN { if (p_false) { op.reset(new Conditional<StrSet>(test, p_true, p_false)); @@ -730,198 +716,267 @@ condit_str } } | Q_MARK - p_true = string_operators [tagset, vars] + p_true = string_operator [tagset, vars] Q_MARK - test = logical_predicates [tagset, vars] { + test = bool_operator [tagset, vars] { op.reset(new Conditional<StrSet>(test, p_true)); } ; -// ---------------------------------------------------------------------------- -// ---------------------------------------------------------------------------- -// Logical predicates +/////////////////////////////////////////////////////////////////////////////// +// Boool operator // Returns boost::shared_ptr<Function<Bool> > -// ---------------------------------------------------------------------------- -logical_predicates +/////////////////////////////////////////////////////////////////////////////// +bool_operator [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > ret] - : ret = lpred_and [tagset, vars] - | ret = lpred_or [tagset, vars] - | ret = lpred_nor [tagset, vars] - | ret = lpred_bool [tagset, vars] - | ret = lpred_in [tagset, vars] - | ret = lpred_inter [tagset, vars] - | ret = lpred_eq [tagset, vars] - | ret = lpred_regex [tagset, vars] - | ret = setvar_op [tagset, vars] - | ret = lpred_inout [tagset, vars] - | ret = condit_bool [tagset, vars] + : ret = bool_and [tagset, vars] + | ret = bool_or [tagset, vars] + | ret = bool_nor [tagset, vars] + | ret = bool_var_val [tagset, vars] + | ret = bool_regex [tagset, vars] + | ret = bool_inout [tagset, vars] + | ret = bool_condition [tagset, vars] + // setvar: + | ret = setvar_operator [tagset, vars] + // equal/in/inter: + | ret = equal_operator [tagset, vars] + | ret = in_operator [tagset, vars] + | ret = inter_operator [tagset, vars] + // + | LPAREN ret = bool_operator [tagset, vars] RPAREN ; + // ---------------------------------------------------------------------------- -// comma-separated predicates -logical_predicates_comma_sep +// comma-separated predicates (bool operators) +bool_operator_comma_sep [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr< - std::vector<boost::shared_ptr<Function<Bool> > > - > ret_v] + returns + [boost::shared_ptr<std::vector<boost::shared_ptr<Function<Bool> > > > ret_v] { boost::shared_ptr<Function<Bool> > pred; ret_v.reset( new std::vector<boost::shared_ptr<Function<Bool> > > ); } - : pred = logical_predicates [tagset, vars] { + : pred = bool_operator [tagset, vars] { ret_v->push_back(pred); - } ( - COMMA pred = logical_predicates [tagset, vars] { - ret_v->push_back(pred); - })* + } + ( + COMMA pred = bool_operator [tagset, vars] { + ret_v->push_back(pred); + } + )* ; + // ---------------------------------------------------------------------------- -lpred_and +// And operator. +bool_and [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr< - std::vector<boost::shared_ptr<Function<Bool> > > - > ret_v; + boost::shared_ptr<std::vector<boost::shared_ptr<Function<Bool> > > > ret_v; } - : "and" LPAREN ret_v = logical_predicates_comma_sep [tagset, vars] RPAREN { + : "and" LPAREN ret_v = bool_operator_comma_sep [tagset, vars] RPAREN { op.reset(new And(ret_v)); } ; + // ---------------------------------------------------------------------------- -lpred_or +// Or operator +bool_or [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr< - std::vector<boost::shared_ptr<Function<Bool> > > - > ret_v; + boost::shared_ptr<std::vector<boost::shared_ptr<Function<Bool> > > > ret_v; } - : "or" LPAREN ret_v = logical_predicates_comma_sep [tagset, vars] RPAREN { + : "or" LPAREN ret_v = bool_operator_comma_sep [tagset, vars] RPAREN { op.reset(new Or(ret_v)); } ; + // ---------------------------------------------------------------------------- -lpred_nor +// Nor/Not operator +bool_nor [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr< - std::vector<boost::shared_ptr<Function<Bool> > > - > ret_v; + boost::shared_ptr<std::vector<boost::shared_ptr<Function<Bool> > > > ret_v; } - : "not" LPAREN ret_v = logical_predicates_comma_sep [tagset, vars] RPAREN { + : "not" LPAREN ret_v = bool_operator_comma_sep [tagset, vars] RPAREN { op.reset(new Nor(ret_v)); } ; + // ---------------------------------------------------------------------------- -lpred_bool +// Wrapper for bool value and bool variable +bool_var_val [const Corpus2::Tagset& /*tagset*/, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] - : op = boolean_variable [vars] - | op = boolean_value + : op = bool_value + | op = bool_variable [vars] +; + +// ---------------------------------------------------------------------------- +// Regex operator +bool_regex + [const Corpus2::Tagset& tagset, Variables& vars] + returns [boost::shared_ptr<Function<Bool> > op] +{ + boost::shared_ptr<Function<StrSet> > expr; +} + : "regex" + LPAREN + expr = string_operator [tagset, vars] COMMA reg: STRING + RPAREN { + op.reset(new Regex(expr, token_ref_to_ustring(reg))); + } +; + +// ---------------------------------------------------------------------------- +// Input/output operator +bool_inout + [const Corpus2::Tagset& tagset, Variables& vars] + returns [boost::shared_ptr<Function<Bool> > op] +{ + boost::shared_ptr<Function<Position> > ret_pos; +} + : "inside" LPAREN ret_pos = position_operator [tagset, vars] RPAREN { + op.reset(new IsInside(ret_pos)); + } + | "outside" LPAREN ret_pos = position_operator [tagset, vars] RPAREN { + op.reset(new IsOutside(ret_pos)); + } +; + +// ---------------------------------------------------------------------------- +// if (Bool, Bool, Bool) +// ? Bool ? Bool : False +bool_condition + [const Corpus2::Tagset& tagset, Variables& vars] + returns [boost::shared_ptr<Function<Bool> > op] +{ + boost::shared_ptr<Function<Bool> > test, p_true, p_false; +} + : "if" LPAREN test = bool_operator [tagset, vars] COMMA + p_true = bool_operator [tagset, vars] + (COMMA p_false = bool_operator [tagset, vars])? + RPAREN { + if (p_false) { + op.reset(new Conditional<Bool>(test, p_true, p_false)); + } + else { + op.reset(new Conditional<Bool>(test, p_true)); + } + } + | Q_MARK + p_true = bool_operator [tagset, vars] + Q_MARK + test = bool_operator [tagset, vars] { + op.reset(new Conditional<Bool>(test, p_true)); + } ; + // ---------------------------------------------------------------------------- -lpred_in +// Equal operator +equal_operator [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { boost::shared_ptr<Function<TSet> > t1, t2; - boost::shared_ptr<Function<StrSet> > s1, s2; + boost::shared_ptr<Function<Bool> > b1, b2; + boost::shared_ptr<Function<StrSet> > s1, s2; + boost::shared_ptr<Function<Position> > p1, p2; } -: - "in" LPAREN + : "equal" LPAREN ( - (sym_set_operators [tagset, vars]) => + (position_operator [tagset, vars]) => ( - t1 = sym_set_operators [tagset, vars] COMMA - t2 = sym_set_operators [tagset, vars] { - op.reset(new IsSubsetOf<TSet>(t1, t2)); + p1 = position_operator [tagset, vars] COMMA + p2 = position_operator [tagset, vars] { + op.reset(new Equals<Position>(p1, p2)); } ) - | + | + (symset_operator [tagset, vars]) => ( - s1 = string_operators [tagset, vars] COMMA - s2 = string_operators [tagset, vars] { - op.reset(new IsSubsetOf<StrSet>(s1, s2)); + t1 = symset_operator [tagset, vars] COMMA + t2 = symset_operator [tagset, vars] { + op.reset(new Equals<TSet>(t1, t2)); + } + ) + | + (string_operator [tagset, vars]) => + ( + s1 = string_operator [tagset, vars] COMMA + s2 = string_operator [tagset, vars] { + op.reset(new Equals<StrSet>(s1, s2)); + } + ) + | + ( + b1 = bool_operator [tagset, vars] COMMA + b2 = bool_operator [tagset, vars] { + op.reset(new Equals<Bool>(b1, b2)); } ) ) RPAREN - ; // ---------------------------------------------------------------------------- -lpred_inter +// In operator +in_operator [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { boost::shared_ptr<Function<TSet> > t1, t2; boost::shared_ptr<Function<StrSet> > s1, s2; } - : - "inter" LPAREN +: + "in" LPAREN ( - (sym_set_operators [tagset, vars]) => + (symset_operator [tagset, vars]) => ( - t1 = sym_set_operators [tagset, vars] COMMA - t2 = sym_set_operators [tagset, vars] { - op.reset(new Intersects<TSet>(t1, t2)); + t1 = symset_operator [tagset, vars] COMMA + t2 = symset_operator [tagset, vars] { + op.reset(new IsSubsetOf<TSet>(t1, t2)); } ) - | + | ( - s1 = string_operators [tagset, vars] COMMA - s2 = string_operators [tagset, vars] { - op.reset(new Intersects<StrSet>(s1, s2)); + s1 = string_operator [tagset, vars] COMMA + s2 = string_operator [tagset, vars] { + op.reset(new IsSubsetOf<StrSet>(s1, s2)); } ) ) RPAREN ; - // ---------------------------------------------------------------------------- -lpred_eq +// Inter operator +inter_operator [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { boost::shared_ptr<Function<TSet> > t1, t2; - boost::shared_ptr<Function<Bool> > b1, b2; - boost::shared_ptr<Function<StrSet> > s1, s2; - boost::shared_ptr<Function<Position> > p1, p2; + boost::shared_ptr<Function<StrSet> > s1, s2; } - : "equal" LPAREN + : + "inter" LPAREN ( - (position_operators [tagset, vars]) => - ( - p1 = position_operators [tagset, vars] COMMA - p2 = position_operators [tagset, vars] { - op.reset(new Equals<Position>(p1, p2)); - } - ) - | - (sym_set_operators [tagset, vars]) => - ( - t1 = sym_set_operators [tagset, vars] COMMA - t2 = sym_set_operators [tagset, vars] { - op.reset(new Equals<TSet>(t1, t2)); - } - ) - | - (string_operators [tagset, vars]) => + (symset_operator [tagset, vars]) => ( - s1 = string_operators [tagset, vars] COMMA - s2 = string_operators [tagset, vars] { - op.reset(new Equals<StrSet>(s1, s2)); + t1 = symset_operator [tagset, vars] COMMA + t2 = symset_operator [tagset, vars] { + op.reset(new Intersects<TSet>(t1, t2)); } ) | ( - b1 = logical_predicates [tagset, vars] COMMA - b2 = logical_predicates [tagset, vars] { - op.reset(new Equals<Bool>(b1, b2)); + s1 = string_operator [tagset, vars] COMMA + s2 = string_operator [tagset, vars] { + op.reset(new Intersects<StrSet>(s1, s2)); } ) ) @@ -929,86 +984,83 @@ lpred_eq ; // ---------------------------------------------------------------------------- -lpred_regex +// Setvar operator +// Returns boost::shared_ptr<Function<Bool> > +// ---------------------------------------------------------------------------- +setvar_operator + [const Corpus2::Tagset& tagset, Variables& vars] + returns [boost::shared_ptr<Function<Bool> > ret] + : "setvar" LPAREN + ( + ret = position_setvar [tagset, vars] + | ret = bool_setvar [tagset, vars] + | ret = strset_setvar [tagset, vars] + | ret = symset_setvar [tagset, vars] + ) + RPAREN +; + +// ---------------------------------------------------------------------------- +// Setvar for position +position_setvar [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr<Function<StrSet> > expr; + boost::shared_ptr<Function<Position> > ret_op; + boost::shared_ptr<VariableAccessor<Position> > ret_acc; } - : "regex" LPAREN expr = string_operators [tagset, vars] COMMA reg: STRING RPAREN { - op.reset(new Regex(expr, token_ref_to_ustring(reg))); - } + : ret_acc = position_variable_acc [vars] + COMMA + ret_op = position_operator [tagset, vars] { + op.reset(new VarSetter<Position>(*ret_acc.get(), ret_op)); + } ; // ---------------------------------------------------------------------------- -lpred_inout +// Setvar for bool +bool_setvar [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr<Function<Position> > ret_pos; + boost::shared_ptr<Function<Bool> > ret_op; + boost::shared_ptr<VariableAccessor<Bool> > ret_acc; } - : "inside" LPAREN ret_pos = position_operators [tagset, vars] RPAREN { - op.reset(new IsInside(ret_pos)); - } - | "outside" LPAREN ret_pos = position_operators [tagset, vars] RPAREN { - op.reset(new IsOutside(ret_pos)); - } + : ret_acc = bool_variable_acc [vars] + COMMA + ret_op = bool_operator [tagset, vars] { + op.reset(new VarSetter<Bool>(*ret_acc.get(), ret_op)); + } ; // ---------------------------------------------------------------------------- -// if (Bool, Bool, Bool) -// ? Bool ? Bool : False -condit_bool +// Setvar for strset +strset_setvar [const Corpus2::Tagset& tagset, Variables& vars] returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr<Function<Bool> > test, p_true, p_false; + boost::shared_ptr<Function<StrSet> > ret_op; + boost::shared_ptr<VariableAccessor<StrSet> > ret_acc; } - : "if" LPAREN test = logical_predicates [tagset, vars] COMMA - p_true = logical_predicates [tagset, vars] - (COMMA p_false = logical_predicates [tagset, vars])? - RPAREN { - if (p_false) { - op.reset(new Conditional<Bool>(test, p_true, p_false)); - } - else { - op.reset(new Conditional<Bool>(test, p_true)); - } - } - | Q_MARK - p_true = logical_predicates [tagset, vars] - Q_MARK - test = logical_predicates [tagset, vars] { - op.reset(new Conditional<Bool>(test, p_true)); + : ret_acc = strset_variable_acc [vars] + COMMA + ret_op = string_operator [tagset, vars] { + op.reset(new VarSetter<StrSet>(*ret_acc.get(), ret_op)); } ; // ---------------------------------------------------------------------------- -// if (Bool, Position, Position) -// ? Position ? Bool : 0 -condit_position +// Setvar for symset +symset_setvar [const Corpus2::Tagset& tagset, Variables& vars] - returns [boost::shared_ptr<Function<Position> > op] + returns [boost::shared_ptr<Function<Bool> > op] { - boost::shared_ptr<Function<Bool> > test; - boost::shared_ptr<Function<Position> > p_true, p_false; + boost::shared_ptr<Function<TSet> > ret_op; + boost::shared_ptr<VariableAccessor<TSet> > ret_acc; } - : "if" LPAREN test = logical_predicates [tagset, vars] COMMA - p_true = position_operators [tagset, vars] - (COMMA p_false = position_operators [tagset, vars])? - RPAREN { - if (p_false) { - op.reset(new Conditional<Position>(test, p_true, p_false)); - } - else { - op.reset(new Conditional<Position>(test, p_true)); - } - } - | Q_MARK - p_true = position_operators [tagset, vars] - Q_MARK - test = logical_predicates [tagset, vars] { - op.reset(new Conditional<Position>(test, p_true)); + : ret_acc = symset_variable_acc [vars] + COMMA + ret_op = symset_operator [tagset, vars] { + op.reset(new VarSetter<TSet>(*ret_acc.get(), ret_op)); } ; @@ -1202,15 +1254,17 @@ options { loop iteration, so it's OK. This is exactly how they do it all over the web - just turn off the warning for this particular token.*/ - options { generateAmbigWarnings=false; } + options { + generateAmbigWarnings = false; + } : { LA(2)!='/' }? '*' | '\r' '\n' { newline(); } | '\r' { newline(); } | '\n' { newline(); } | ~('*'|'\n'|'\r') - )* + )* "*/" - {$setType(antlr::Token::SKIP);} + { $setType(antlr::Token::SKIP); } ; HASH diff --git a/libwccl/values/position.cpp b/libwccl/values/position.cpp index 5be0a85b2be1d03e3b48cbad9ff35801e4302899..f1cadf25c45e8b9dece29211949bece6fd09caaa 100644 --- a/libwccl/values/position.cpp +++ b/libwccl/values/position.cpp @@ -43,4 +43,9 @@ bool Position::is_inside(const SentenceContext& context) const return context.is_inside(abs_position); } +bool Position::equals(const Position& other, const SentenceContext& context) const +{ + return context.get_abs_position(*this) == context.get_abs_position(other); +} + } /* end ns Wccl */ diff --git a/libwccl/values/position.h b/libwccl/values/position.h index fed7a414ed5369acf13a6c909b4e714db93ef26d..ca3f7a1e790df02833add568363d34d2f514a843 100644 --- a/libwccl/values/position.h +++ b/libwccl/values/position.h @@ -50,7 +50,8 @@ public: /** * @returns True if underlying position values are equal, false otherwise. * @note This version does not take into account sentence context, only - * the raw value of position. + * the raw value of position. In practice it means that the special positions + * Begin, End, Nowhere are equal only to a coresponding special position. */ bool equals(const Position& other) const { return val_ == other.val_; @@ -58,13 +59,13 @@ public: /** * @returns True if positions are equal in context of a sentence, false otherwise. - * @note This version determines if position values point outside of a sentence, - * and if both of them do, they are considered to be equal as well (both "nowhere"). + * @note The equality is determined by absolute value of the Position in context + * of a sentence (this means pointing to the same absolute position regardless + * if it lies inside or outside of the sentence). + * Nowhere is only equal to another Nowhere, but Begin or End may be equal to + * a nonspecial position depending on the value of current position in the context. */ - bool equals(const Position& other, const SentenceContext& context) const - { - return equals(other) || (is_outside(context) && other.is_outside(context)); - } + bool equals(const Position& other, const SentenceContext& context) const; private: int val_; diff --git a/tests/values.cpp b/tests/values.cpp index c39115e7cbbe63ea41660a8b1843e762c7d46c56..6f9e5c391c56d3a61c65d43ab741d7748aa0fce8 100644 --- a/tests/values.cpp +++ b/tests/values.cpp @@ -2,6 +2,7 @@ #include <boost/bind.hpp> #include <libcorpus2/tagsetmanager.h> +#include <libwccl/sentencecontext.h> #include <libwccl/variables.h> #include <iostream> @@ -26,6 +27,14 @@ BOOST_AUTO_TEST_CASE(tsetz) BOOST_CHECK_EQUAL(v.get_type_name(), TSet::type_name); } +BOOST_AUTO_TEST_CASE(positionz) +{ + Position p; + BOOST_CHECK(p.get_value() == Position::Nowhere); + Value& v = p; + BOOST_CHECK_EQUAL(v.get_type_name(), Position::type_name); +} + BOOST_AUTO_TEST_CASE(strset_ops) { StrSet s1, s2; @@ -85,4 +94,67 @@ BOOST_AUTO_TEST_CASE(tset_ops) BOOST_CHECK(s1.intersects(s2)); } +BOOST_AUTO_TEST_CASE(position_ops) +{ + boost::shared_ptr<Corpus2::Sentence> s(boost::make_shared<Corpus2::Sentence>()); + SentenceContext sc(s); + Corpus2::Token* a_token = new Corpus2::Token("ZZ", PwrNlp::Whitespace::ManySpaces); + Corpus2::Tag t1(Corpus2::mask_t(0)); + Corpus2::Lexeme l1("aaa", t1); + Corpus2::Lexeme l2("bbb", t1); + a_token->add_lexeme(l1); + a_token->add_lexeme(l2); + s->append(a_token); + s->append(a_token->clone()); + Position begin(Position::Begin); + Position end(Position::End); + Position nowhere(Position::Nowhere); + Position zero(0); + Position one(1); + Position minus_one(-1); + Position minus_two(-2); + + std::vector<Position> v; + v.push_back(begin); + v.push_back(end); + v.push_back(nowhere); + v.push_back(zero); + v.push_back(one); + v.push_back(minus_one); + v.push_back(minus_two); + + for(int i = 0; i < v.size(); ++i) { + for(int j = 0; j < v.size(); ++j) { + BOOST_CHECK_EQUAL(i == j, v[i].equals(v[j])); + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i])); + if(i >= 2 && j >= 2) { //nowhere, zero, one, minus_one, minus_two + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i], sc)); + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i], sc)); + sc.advance(); + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i], sc)); + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i], sc)); + sc.advance(); + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i], sc)); + BOOST_CHECK_EQUAL(i == j, v[j].equals(v[i], sc)); + sc.goto_start(); + } + } + } + sc.goto_start(); + BOOST_CHECK(begin.equals(zero, sc)); + BOOST_CHECK(zero.equals(begin, sc)); + BOOST_CHECK(one.equals(end, sc)); + BOOST_CHECK(end.equals(one, sc)); + sc.advance(); + BOOST_CHECK(begin.equals(minus_one, sc)); + BOOST_CHECK(minus_one.equals(begin, sc)); + BOOST_CHECK(zero.equals(end, sc)); + BOOST_CHECK(end.equals(zero, sc)); + sc.advance(); + BOOST_CHECK(begin.equals(minus_two, sc)); + BOOST_CHECK(minus_two.equals(begin, sc)); + BOOST_CHECK(minus_one.equals(end, sc)); + BOOST_CHECK(end.equals(minus_one, sc)); +} + BOOST_AUTO_TEST_SUITE_END()