|
Программирование >> Инициализация объектов класса, структура
template < typename Type, typename Comp > const Type& min( const Type *p, int size, Comp comp ) { Type minval = p[ 0 ]; for ( int ix = 1; ix < size; ++ix ) if ( Comp( p[ ix ] < minval )) minval = p[ ix ]; return minval; допускает также и передачу указателя на функцию, но без проверки прототипа): Как правило, обобщенн1е алгоритма: поддерживают обе форм: применения операции: как использование встроенного (или перегруженного) оператора, так и применение указателя на функцию либо объекта-функции. Есть три источника появления объектов-функций: 1. из набора предопределенных арифметических, сравнительных и логических объектов-функций стандартной библиотеки; 2. из набора предопределенных адаптеров функций, позволяющих специализировать или расширять предопределенные (или любые другие) объекты-функции; 3. определенные нами собственные объекты-функции для передачи обобщенным алгоритмам. К ним можно применять и адаптеры функций. В этом разделе мы рассмотрим все три источника объектов-функций. 12.3.1. Предопределенные объекты - функции Предопределенные объекты-функции подразделяются на арифметические, логические и сравнительные. Каждый объект - это шаблон класса, параметризованный типами операндов. Для использования любого из них необходимо включить заголовочный файл: #include <functional> Например, объект-функция, поддерживающий сложение, - это шаблон класса с именем plus. Для определения экземпляра, способного складывать два целых числа, нужно #include <functional> написать: plus< int > intAdd; Для выполнения операции сложения мы применяем перегруженный оператор вызова к intAdd точно так же, как и к классу AddImage в предыдущем разделе: количество дополнительных данных, например кэш или информацию, полезную для выполнения текущей операции. Ниже приведена измененная реализация шаблона min() (отметим, что это объявление int ival1 = 10, ival2 = 20; эквивалентно int sum = ival1 + ival2; int sum = intAdd( ival1, ival2 ); Реализация шаблона класса plus вызывает оператор сложения, ассоциированный с типом своего параметра - int. Этот и другие предопределенные объекты-функции применяются прежде всего в качестве аргументов обобщенных алгоритмов и обычно замещают подразумеваемую по умолчанию операцию. Например, по умолчанию алгоритм sort() располагает элементы контейнера в порядке возрастания с помощью оператора меньше базового типа. Для сортировки по убыванию мы передаем vector< string > svec; ... предопределенный шаблон класса greater, который вызывает оператор больше : sort( svec.begin(), svec.end(), greater<string>() ); Предопределенные объекты-функции перечислены в следующих разделах и разбиты на категории: арифметические, логические и сравнительные. Применение каждого из них иллюстрируется как в качестве именованного, так и в качестве безымянного объекта, передаваемого функции. Мы пользуемся следующими определениями объектов, включая и определение простого класса (перегрузка операторов подробно рассматривается в главе class Int { public: Int( int ival = 0 ) : val( ival ) {} int operator-() { return - val; } int operator%(int ival) { return - val % ival; } bool operator<(int ival) { return - val < ival; } bool operator!() { return - val == 0; } private: int val; vector< string > svec; string sval1, sval2, sres; complex cval1, cval2, cres; int ival1, ival2, ires; Int Ival1, Ival2, Ires; 15): double dval1, dval2, dres; Кроме того, мы определяем два шаблона функций, которым передаем различные безымянные объекты-функции: template <class FuncObject, class Type> Type UnaryFunc( FuncObject fob, const Type &val return fob( val ); template <class FuncObject, class Type> Type BinaryFunc( FuncObject fob, const Type &val1, const Type &val2 ) { return fob( val1, val2 ); } 12.3.2. Арифметические объекты-функции Предопределенные арифметические объект:-функции поддерживают операции сложения, вычитания, умножения, деления, взятия остатка и вычисления противоположного по знаку значения. Вызываемый оператор - это экземпляр, ассоциированный с типом Type. Если тип является классом, предоставляющим перегруженную реализацию оператора, то именно эта реализация и вызывается. plus<string> stringAdd; вызывается string::operator+() sres = stringAdd( sval1, sval2 ); Сложение: plus<Type> dres = BinaryFunc( plus<double>(), dval1, dval2 ); minus<int> intSub; ires = intSub( ival1, ival2 ); Вычитание: minus<Type> dres = BinaryFunc( minus<double>(), dval1, dval2 ); multiplies<complex> complexMultiplies; cres = complexMultiplies( cval1, cval2 ); Умножение: multiplies<Type> dres = BinaryFunc( multiplies<double>(), dval1, dval2 ); divides<int> intDivides; ires = intDivides( ival1, ival2 ); Деление: divides<Type> dres = BinaryFunc( divides<double>(), dval1, dval2 ); Взятие остатка: modulus<Type>
|
© 2006 - 2025 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки. |