Модификаторы фильтрации являются дополнительными модификаторами, которые работают с некоторыми общими макросами, чтобы указать тип данных для применения к функциональности макроса. Сам фильтрующий модификатор является необязательным параметром, указанным как v-тип. Любой тип v, указанный в качестве дополнительного параметра, может использоваться в качестве модификатора фильтрации.
Макросы равенства, BOOST_VMD_EQUAL и BOOST_VMD_NOT_EQUAL, в общем тестируют, равны ли каждый из двух требуемых входов друг другу.
Каждый из этих макросов использует один дополнительный параметр, модификатор фильтрации, чтобы сузить фокус своего тестирования на равенство до определенного типа v.
Для макро-BOOST_VMD_EQUAL этот необязательный параметр означает, что равенство означает не только то, что два требуемых входных параметра равны, но и то, что они относятся к типу или подтипу третьего необязательного параметра. Число и v-тип являются подтипами идентификаторов, в то время как непустой список и массив являются подтипами кортежей.
И наоборот, BOOST_VMD_NOT_EQUAL с дополнительным третьим параметром v-типа возвращает 1, если либо первые два параметра не равны, либо если тип первых двух параметров не является типом или подтипом третьего параметра. В противном случае он возвращается Он реализован как дополнение BOOST_VMD_EQUAL так, что всякий раз, когда BOOST_VMD_EQUAL возвращается 1, BOOST_VMD_NOT_EQUAL возвращается 0 и наоборот.
Вот пример использования BOOST_VMD_EQUAL с модификатором фильтрации. BOOST_VMD_NOT_EQUAL - это просто дополнение результатов в нашем примере для каждого результата, и было бы избыточно указывать каждый раз ниже.
#include <boost/vmd/equal.hpp>
#define BOOST_VMD_REGISTER_AN_ID1 (AN_ID1)
#define BOOST_VMD_REGISTER_AN_ID2 (AN_ID2)
#define BOOST_VMD_DETECT_AN_ID1_AN_ID1
#define BOOST_VMD_DETECT_AN_ID2_AN_ID2
#define AN_IDENTIFIER1 AN_ID1
#define AN_IDENTIFIER2 AN_ID2
#define AN_IDENTIFIER3 AN_ID1
#define A_NUMBER1 33
#define A_NUMBER2 145
#define A_NUMBER3 33
#define A_TUPLE1 (AN_IDENTIFIER1,A_NUMBER1)
#define A_TUPLE2 (AN_IDENTIFIER1,A_NUMBER2)
#define A_TUPLE3 (AN_IDENTIFIER3,A_NUMBER3)
#define A_LIST1 (A_NUMBER1,(A_NUMBER3,BOOST_PP_NIL))
#define A_LIST2 (A_NUMBER1,(A_NUMBER2,BOOST_PP_NIL))
#define A_LIST3 (A_NUMBER1,(A_NUMBER3,BOOST_PP_NIL))
#define A_LIST4 BOOST_PP_NIL
#define A_LIST5 BOOST_PP_NIL
BOOST_VMD_EQUAL(AN_IDENTIFIER1,AN_IDENTIFIER2,BOOST_VMD_TYPE_IDENTIFIER) will return 0
BOOST_VMD_EQUAL(AN_IDENTIFIER1,AN_IDENTIFIER3,BOOST_VMD_TYPE_IDENTIFIER) will return 1
BOOST_VMD_EQUAL(AN_IDENTIFIER1,AN_IDENTIFIER3,BOOST_VMD_TYPE_TYPE) will return 0 because the type does not match
BOOST_VMD_EQUAL(A_NUMBER1,A_NUMBER2,BOOST_VMD_TYPE_NUMBER) will return 0
BOOST_VMD_EQUAL(A_NUMBER1,A_NUMBER3,BOOST_VMD_TYPE_NUMBER) will return 1
BOOST_VMD_EQUAL(A_NUMBER1,A_NUMBER3,BOOST_VMD_TYPE_IDENTIFIER) will return 1 because a number is an identifier
BOOST_VMD_EQUAL(A_NUMBER1,A_NUMBER3,BOOST_VMD_TYPE_EMPTY) will return 0 because the type does not match
BOOST_VMD_EQUAL(A_TUPLE1,A_TUPLE2,BOOST_VMD_TYPE_TUPLE) will return 0
BOOST_VMD_EQUAL(A_TUPLE1,A_TUPLE3,BOOST_VMD_TYPE_TUPLE) will return 1
BOOST_VMD_EQUAL(A_TUPLE1,A_TUPLE3,BOOST_VMD_TYPE_ARRAY) will return 0 because the type does not match
BOOST_VMD_EQUAL(A_LIST1,A_LIST2,BOOST_VMD_TYPE_LIST) will return 0
BOOST_VMD_EQUAL(A_LIST1,A_LIST3,BOOST_VMD_TYPE_LIST) will return 1
BOOST_VMD_EQUAL(A_LIST1,A_LIST3,BOOST_VMD_TYPE_IDENTIFIER) will return 0 because the type does not match
BOOST_VMD_EQUAL(A_LIST1,A_LIST3,BOOST_VMD_TYPE_TUPLE) will return 1 because a non-empty list is also a tuple
BOOST_VMD_EQUAL(A_LIST4,A_LIST5,BOOST_VMD_TYPE_LIST) will return 1
BOOST_VMD_EQUAL(A_LIST4,A_LIST5,BOOST_VMD_TYPE_IDENTIFIER) will return 1 because an empty list is also an identifier
BOOST_VMD_EQUAL(A_LIST4,A_LIST5,BOOST_VMD_TYPE_TUPLE) will return 0 because an empty list is not a tuple
Как и в случае с макросами равенства BOOST_VMD_ELEM позволяет выполнять фильтрацию для результата. Необязательный параметр v-типа может быть использован таким образом, что BOOST_VMD_ELEM возвращает свой результат только в том случае, если элемент последовательности относится к указанному v-типу, в противном случае он не может найти элемент таким же образом, как номер элемента, который находится за пределами последовательности.
#include <boost/vmd/elem.hpp>
#define BOOST_VMD_REGISTER_ANAME (ANAME)
#define A_SEQUENCE (1,2,3) 46 (list_data1,(list_data2,BOOST_PP_NIL)) BOOST_VMD_TYPE_SEQ ANAME
BOOST_VMD_ELEM(0,A_SEQUENCE) will return (1,2,3)
BOOST_VMD_ELEM(0,A_SEQUENCE,BOOST_VMD_TYPE_TUPLE) will return (1,2,3)
BOOST_VMD_ELEM(0,A_SEQUENCE,BOOST_VMD_TYPE_SEQ) will return emptiness
BOOST_VMD_ELEM(1,A_SEQUENCE) will return 46
BOOST_VMD_ELEM(1,A_SEQUENCE,BOOST_VMD_TYPE_NUMBER) will return 46
BOOST_VMD_ELEM(1,A_SEQUENCE,BOOST_VMD_TYPE_IDENTIFIER) will return 46 since a number is also an identifier
BOOST_VMD_ELEM(1,A_SEQUENCE,BOOST_VMD_TYPE_LIST) will return emptiness
BOOST_VMD_ELEM(2,A_SEQUENCE) will return (list_data1,(list_data2,BOOST_PP_NIL))
BOOST_VMD_ELEM(2,A_SEQUENCE,BOOST_VMD_TYPE_LIST) will return (list_data1,(list_data2,BOOST_PP_NIL))
BOOST_VMD_ELEM(2,A_SEQUENCE,BOOST_VMD_TYPE_TUPLE) will return (list_data1,(list_data2,BOOST_PP_NIL)) since a list is also a tuple
BOOST_VMD_ELEM(2,A_SEQUENCE,BOOST_VMD_TYPE_TYPE) will return emptiness
BOOST_VMD_ELEM(3,A_SEQUENCE) will return BOOST_VMD_TYPE_SEQ
BOOST_VMD_ELEM(3,A_SEQUENCE,BOOST_VMD_TYPE_TYPE) will return BOOST_VMD_TYPE_SEQ
BOOST_VMD_ELEM(3,A_SEQUENCE,BOOST_VMD_TYPE_IDENTIFIER) will return BOOST_VMD_TYPE_SEQ since a type is also an identifier
BOOST_VMD_ELEM(3,A_SEQUENCE,BOOST_VMD_TYPE_TUPLE) will return emptiness
BOOST_VMD_ELEM(4,A_SEQUENCE) will return ANAME
BOOST_VMD_ELEM(4,A_SEQUENCE,BOOST_VMD_TYPE_IDENTIFIER) will return ANAME
BOOST_VMD_ELEM(4,A_SEQUENCE,BOOST_VMD_TYPE_NUMBER) will return emptiness
BOOST_VMD_ELEM(0,BOOST_PP_NIL) will return BOOST_PP_NIL
BOOST_VMD_ELEM(0,BOOST_PP_NIL,BOOST_VMD_TYPE_LIST) will return BOOST_PP_NIL since it is an empty list
BOOST_VMD_ELEM(0,BOOST_PP_NIL,BOOST_VMD_TYPE_IDENTIFIER) will return BOOST_PP_NIL since it a registered identifier
BOOST_VMD_ELEM(0,BOOST_PP_NIL,BOOST_VMD_TYPE_TUPLE) will return emptiness
Если в качестве модификатора фильтрации для BOOST_VMD_ELEM указать более одного v-типа, то последний v-тип становится фильтром.
Фильтрация с помощью BOOST_VMD_ELEM обозначает тип данных, ожидаемых при обнаружении конкретного элемента. Поскольку фильтрация представляет тип запрашиваемых данных, модификаторы фильтрации и модификаторы типа возврата являются взаимоисключающими, и любой модификатор фильтрации означает, что указанные модификаторы типа возврата игнорируются.